Ansible не работает с /bin/sh: 1:/usr/bin/python: не найден

Я сталкиваюсь с ошибкой, которую я никогда раньше не видел. Вот команда и ошибка:

$ ansible-playbook create_api.yml

PLAY [straw] ******************************************************************

GATHERING FACTS ***************************************************************
failed: [104.55.47.224] => {"failed": true, "parsed": false}
/bin/sh: 1: /usr/bin/python: not found


TASK: [typical | install required system packages] *****************************
FATAL: no hosts matched or all hosts have already failed -- aborting


PLAY RECAP ********************************************************************
           to retry, use: --limit @/Users/john/create_api.retry

104.55.47.224               : ok=0    changed=0    unreachable=0    failed=1

Вот файл create_api.yml:

---

- hosts: api
  remote_user: root
  roles:
    - api

И вот файл hosts:

[api]
104.55.47.224

Я могу удалить раздел ролей, и он не перейдет к первой задаче, вместо этого он сделает это только для строки /bin/sh: 1: /usr/bin/python: not found. Что здесь может быть?


ПРИМЕЧАНИЕ. Если кто-то сканирует IP-адрес и не получает ответа, вы должны знать, что я изменил IP-адрес с момента вставки кода.

ИЗМЕНИТЬ python был установлен локально, проблема заключалась в том, что он не был установлен на удаленном компьютере, на котором запущен Ubuntu 15.04

Ответ 1

Я наткнулся на эту ошибку при запуске ansible на сервере Ubuntu 15.10, потому что он поставляется с Python 3.4.3, а ansible требует Python 2.

Вот как сейчас выглядит мой provision.yml:

- hosts: my_app
  sudo: yes
  remote_user: root
  gather_facts: no
  pre_tasks:
    - name: 'install python2'
      raw: sudo apt-get -y install python

  tasks:
    - name: 'ensure user {{ project_name }} exists'
      user: name={{ project_name }} state=present
  • Не забудьте опцию -y (отвечает "да" на все вопросы) с помощью apt-get (иначе модуль raw будет зависать молча)

  • gather_facts: no строка также не критична (потому что мы не можем собрать факты без python)

Ответ 2

Ansible 2.2 показывает технический обзор поддержки Python 3. Чтобы воспользоваться этим (так вам не нужно устанавливать Python 2 на Ubuntu 16.04), просто установите для параметра ansible_python_interpreter config значение /usr/bin/python3. Это можно сделать на основе каждого узла в вашем файле инвентаря:

[db]
123.123.123.123 ansible_python_interpreter=/usr/bin/python3

Ответ 3

Решение 1:

Если вы используете Ansible >2.2.0, вы можете установить ansible_python_interpreter конфигурации ansible_python_interpreter в /usr/bin/python3:

ansible my_ubuntu_host -m ping -e 'ansible_python_interpreter=/usr/bin/python3'

или в вашем инвентарном файле:

[ubuntu_hosts]
<xxx.xxx.xxx.xxx>

[ubuntu_hosts:vars]
ansible_python_interpreter=/usr/bin/python3

Решение 2:

Если вы используете Ansible <2.2.0 тогда вы можете добавить эти pre_tasks в свою pre_tasks:

gather_facts: False
pre_tasks:
  - name: Install python for Ansible
    raw: test -e /usr/bin/python || (apt -y update && apt install -y python-minimal)
    register: output
    changed_when: output.stdout != ""
    tags: always
  - setup: # aka gather_facts

ОБНОВЛЕНИЕ С ansible 2.8.x вам не нужно об этом беспокоиться, это работает из коробки для python> 3.5 как для контроллера, так и для целевой машины (ей)

Ответ 4

Вы можете использовать необработанный модуль для установки Python на удаленных хостах:

- raw: sudo apt-get install python-simplejson

Ответ 5

Чтобы обобщить все остальные ответы, вот комбинированные настройки, которые работали для меня:

 - hosts: all
   become: true
   gather_facts: false

   # Ansible requires python2, which is not installed by default on Ubuntu Xenial
   pre_tasks:
     - raw: sudo apt-get -y install python-simplejson
     # action: setup will gather facts after python2 has been installed
     - action: setup

Ответ 6

Вам нужен Python 2.7 для запуска Ansible. В Ubuntu 16.04 вы можете установить его с помощью этой команды:

sudo apt-get install python-minimal

После этого я мог бежать

ansible-playbook -i inventories/staging playbook.yml

Run ansible successfully

Пожалуйста, проверьте больше на Использование ansible в Ubuntu 16.04

Ответ 7

Что я использовал, чтобы заставить это работать на ubuntu 15.10 на новой капли Digital Ocean:

# my-playbook.yml
- name: python2
  hosts: test
  gather_facts: no
  pre_tasks:
    - raw: sudo apt-get -y install python-simplejson

$ ansible-playbook path/to/my-playbook.yml

Для Ubuntu 16.04 на новом OVH SSD мне пришлось apt-get обновить до того, как были доступны пакеты python2.

Ответ 8

Я лично нашел 3 возможных решения этой проблемы, которые хорошо работают в разных ситуациях:

Вариант 1 - Установите ansible_python_interpreter: /usr/bin/python3 для хостов, на которых по умолчанию установлен python3

Я думаю, что это лучший метод для решения проблемы, если у вас есть способ сгруппировать ваши хосты по python3 установлен ли по умолчанию python3. Насколько я знаю, python3 доступен во всех выпусках Ubuntu 16.04 и выше.

  • Если все ваши хосты определенно имеют python3, вы можете добавить переменную в ваш group_vars/all.yml (или эквивалентный):
# group_vars/all.yml

ansible_python_interpreter: /usr/bin/python3
  • Если у некоторых из ваших хостов нет python3 и у вас есть возможность пометить их при использовании динамического инвентаря (например, AWS-тегирование для ec2.py), вы можете применить переменную к определенным хостам, например так:
# group_vars/tag_OS_ubuntu1804.yml

ansible_python_interpreter: /usr/bin/python3
  • Если вы используете статический инвентарь и можете группировать хосты в зависимости от того, есть ли у них python3, вы можете сделать что-то вроде этого:
# inventory/hosts

[python2_hosts]
centos7_server

[python3_hosts]
u1804_server

[python3_hosts:vars]
ansible_python_interpreter=/usr/bin/python3

Мне больше нравится эта опция, потому что она не требует никаких изменений на удаленном хосте и только незначительные изменения переменных, в отличие от опций 2 и 3, которые требуют дополнений к каждой пьесе.

Вариант 2 - установить Python 2, используя raw

Эта опция требует поставить play в начале каждой книги gather_facts: false с gather_facts: false который использует raw для установки python:

- name: install python2 on all instances
  hosts: "*"
  gather_facts: false
  tasks:
    - name: run apt-get update and install python
      raw: "{{ item }}"
      loop:
        - sudo apt-get update
        - sudo apt-get -y install python
      become: true
      ignore_errors: true

ignore_errors: true требуется, если вы планируете запускать игру на хостах, на которых не установлена apt-get (например, на основе RHEL), в противном случае они выдадут ошибку в первой игре.

Это решение работает, но является самым низким в моем списке по нескольким причинам:

  1. Нужно идти вверху каждой пьесы (в отличие от варианта 1)
  2. Предполагается, что apt находится в системе и игнорирует ошибки (в отличие от варианта 3).
  3. Команды apt-get медленные (в отличие от варианта 3)

Вариант 3 - Symlink /usr/bin/python ->/usr/bin/python3 с использованием raw

Я не видел такого решения, предложенного кем-либо еще. Это не идеал, но я думаю, что он превосходит вариант 2 во многих отношениях. Я предлагаю использовать raw для запуска команды оболочки для symlink /usr/bin/python ->/usr/bin/python3 если python3 находится в системе, а python - нет:

- name: symlink /usr/bin/python -> /usr/bin/python3
  hosts: "*"
  gather_facts: false
  tasks:
    - name: symlink /usr/bin/python -> /usr/bin/python3
      raw: |
        if [ -f /usr/bin/python3 ] && [ ! -f /usr/bin/python ]; then
          ln --symbolic /usr/bin/python3 /usr/bin/python; 
        fi
      become: true

Это решение аналогично варианту 2 в том смысле, что нам нужно ставить его в начале каждой книги, но я думаю, что оно превосходит несколько:

  • Создает только символическую ссылку в конкретном случае, python3 присутствует python3 а python нет - он не будет переопределять Python 2, если он уже установлен
  • Не предполагает, что apt установлен
  • Может работать на всех хостах без специальной обработки ошибок
  • Это супер быстро по сравнению с чем-либо с apt-get

Очевидно, что если вам нужен Python 2, установленный в /usr/bin/python, это решение не требуется, и вариант 2 лучше.

Заключение

  • Я предлагаю использовать вариант 1 во всех случаях, если вы можете.
  • Я предлагаю использовать вариант 3, если ваш инвентарь действительно большой/сложный, и у вас нет возможности легко сгруппировать хосты с python3, что делает вариант 1 намного более сложным и подверженным ошибкам.
  • Я предлагаю только вариант 2 вместо варианта 3, если вам нужен Python 2, установленный в /usr/bin/python.

источники

Ответ 9

Я узнал, что на самом деле возможно иметь несколько пьес в одной пьесе, поэтому моя настройка теперь содержит игру "заработка по зависимостям", которая выполняется на всех хостах и ​​другие игры для определенных хостов. Поэтому не более pre_tasks.

Например:

- name: dependency provisioning
  hosts: all
  become: yes
  become_method: sudo
  gather_facts: false
  tasks:
    - name: install python2
      raw: sudo apt-get -y install python-simplejson

- name: production
  hosts: production_host
  roles:
    - nginx
  tasks:
    - name: update apt cache
      apt: update_cache=yes cache_valid_time=3600
  # ....

- name: staging
  hosts: staging_host
  roles:
    - nginx
  tasks:
    - name: update apt cache
      apt: update_cache=yes cache_valid_time=3600
  # ....

Ответ 10

Как говорили другие, это связано с отсутствием python2. Другие ответы здесь предоставляют обходной путь с pre_tasks и gather_facts: no, однако, если вы находитесь на EC2 и user_data экземпляр с ansible, вы можете использовать опцию user_data:

- ec2:
    key_name: mykey
    instance_type: t2.micro
    image: ami-123456
    wait: yes
    group: webserver
    count: 3
    vpc_subnet_id: subnet-29e63245
    assign_public_ip: yes
    user_data: |
      #!/bin/bash
      apt-get update
      apt-get install -y python-simplejson
    register: ec2

Тогда люди обычно ждут, когда ssh станет доступным, вот так:

  - name: "Wait for the instances to boot and start ssh"
    wait_for:
      host: "{{item.public_ip}}"
      port: 22
      delay: 5
      timeout: 300
    with_items: "{{ ec2.tagged_instances }}"
    when: ec2|changed

Однако я обнаружил, что это не всегда достаточно долго, так как CloudInit выполняется довольно поздно в процессе загрузки, поэтому python2 может быть не установлен сразу после того, как ssh станет доступен. Поэтому я добавил паузу на случай, если экземпляр был только что создан:

  - name: "Wait for cloud init on first boot"
    pause: minutes=2
    when: ec2|changed

Это отлично сработает, и в качестве преимущества вы не проверяете python2 при каждом запуске, и вам не нужно обходиться, чтобы собрать факты позже.

Я уверен, что другие облачные провайдеры предоставляют аналогичную функциональность CloudInit, поэтому адаптируйтесь к своему варианту использования.

Ответ 11

По умолчанию Ansible требует Python 2, однако Ansible 2. 2+ может работать и с Python 3.

Так что либо установите Python 2, используя модуль raw, например

ansible localhost --sudo -m raw -a "yum install -y python2 python-simplejson"

или установите переменную ansible_python_interpreter в файле инвентаризации, например:

[local]
localhost ansible_python_interpreter="env python3"

Для Docker вы можете добавить следующую строку:

RUN printf '[local]\r\nlocalhost ansible_python_interpreter="env python3"\r\n' > /etc/ansible/hosts

или запустите его как:

ansible-playbook /ansible/provision.yml -e 'ansible_python_interpreter=/usr/bin/python3' -c local

Ответ 12

В соответствии с этот Gist вы можете установить Python2 на Ubuntu 16.04 следующим образом:

enter code here
gather_facts: False
pre_tasks:
  - raw: test -e /usr/bin/python || (apt -y update && apt install -y python-minimal)
  - setup: # aka gather_facts

tasks:
  # etc. etc.

Ответ 13

Я смог решить ту же проблему, установив Python на целевой машине, то есть на машине, к которой мы хотим использовать SSH. Я использовал следующую команду:

sudo apt-get install python-minimal

Ответ 14

Множество ответов.. Спасибо за публикацию, так как я начал с этой страницы тоже!

Я немного поработал, и он был прочным с Ubuntu 14.04LTS, Ubuntu 15.04LTS, похоже, сбросил последний python, а Ubuntu 16.04LTS, похоже, упал aptitude.

Я сделал следующее действие в своем загрузочном блоке перед выполнением любых вызовов apt:

- name: "FIX: Ubuntu 16.04 LTS doesn't come with certain modules, required by ansible"
  raw: apt-get install python-minimal aptitude -y
  become: true
  become_user: root
  become_method: sudo

Если вы управляете become в другом месте, не стесняйтесь снимать его.

Источники:

Ответ 15

@Мирослав, спасибо, что указал мне правильное направление. Я использовал user_data в модуле ec2_instance и он работает как удовольствие.

Т.е.

- name: Creating single EC2 instance 
  ec2_instance:
    region: "{{ aws_region }}"
    key_name: "{{ aws_ec2_key_pair }}"
    name: "some-cool-name"
    instance_type: t1.micro
    image_id: ami-d38a4ab1
    security_group: sg-123456
    vpc_subnet_id: sn-678901234
    network:
        assign_public_ip: no
    volumes:
      - device_name: /dev/sda1
        ebs:
          volume_type: gp2
          volume_size: 15
    user_data: |
      #!/bin/bash
      #
      apt update
      apt install -y python-simplejson              
    termination_protection: yes
    wait: yes     

Ответ 16

Вы можете указать Ubuntu 18.04, что вы хотите использовать python3 в качестве первого приоритета для /usr/bin/python.

- hosts: all
  become: true
  pre_tasks:
    - raw: update-alternatives --install /usr/bin/python python /usr/bin/python3 1

Ответ 17

С помощью Packer может оказаться полезным следующее решение

давайте предположим, что вы используете ANSIBLE провайдера упаковщика, ваш конфиг может выглядеть следующим образом

вы можете сначала установить python, используя утилиту инициализации оболочки, а затем настроить параметр ansible_python_intepreter, как показано ниже

"provisioners": [
    {
      "type": "shell",
      "inline": [
        "apk update && apk add --no-cache python python-dev ansible bash"
      ]
    },
    {
      "type": "ansible-local",
      "playbook_file": "playbooks/your-play-book.yml",
      "playbook_dir": "playbooks",
      "extra_arguments": [
        "-e",
        "'ansible_python_interpreter=/usr/bin/python3'",
        "-vvv"
      ]
    },

Ответ 18

У меня была такая же проблема, пока я не понял, что вам также нужно установить python на удаленном хосте, а также на вашем собственном локальном компьютере. теперь это работает!

Ответ 19

Мы просто сталкиваемся с этим.

Мы разворачиваем ubuntu 16.04 на бродягу, поэтому, если вы не используете бродягу, мой комментарий бессмыслен.

Мы установили следующие брандмауэр-плагины (триггер, shell-commander), и мы установили на этом компьютере python 2.7.6 (которые не были без плагинов thioose), и после того, как можно было бы развернуть

Это был наш последний тест, иначе мы собирались включить эту установку в команду оболочки в файле Vagrant

Надеюсь, что это может помочь кому-то