-1

I am currently working on rewriting an old tool that uses ansible to create a virtual environment in which it hosts a python based app. The failing playbook is as follows:

- name: Ensure bash, OpenSSL, and libssl are the latest versions
  become: true
  apt: name={{ item }} update_cache=yes state=latest
  with_items:
    - bash
    - openssl
    - libssl-dev
    - libssl-doc
  tags: packages

- name: install minimum packages
  apt: name={{ item }} update_cache=yes state=installed
  with_items:
    - libav-tools
    - build-essential
    - python-pip
    - python-numpy
    - python-scipy
    - python-software-properties
    - python-dev
    - python-setuptools
    - python-libxml2
    - python-libxslt1
    - python3.4-dev
    - libatlas-base-dev
    - gcc
    - gfortran
    - g++
    - binutils
    - libproj-dev
    - gdal-bin
    - python-gdal
    - python-lxml
    - python3-lxml
    - libblas-dev
    - pkg-config
    - gfortran
    - python-dev
    - libxml2-dev
    - libjpeg8-dev
    - libjpeg-dev
    - libpq-dev
    - libpng12-0
    - libpng-dev    
    - libpng12-dev
    - libfreetype6
    - libfreetype6-dev
    - supervisor
    - nginx
    - git
    - ntp
    - htop
    - libcurl4-openssl-dev
    - libgdal-dev
    - libtool
    - libxml2
    - libxslt1.1
    - libxslt1-dev
    - redis-server
    - freetype*
    - php5-gd
    - python-memcache



- name: upgrade packages
  apt: upgrade=safe

- name: Install virtualenv
  pip: name=virtualenv
  tags: packages

- name: Create the virtualenv
  command: virtualenv /home/mrv/www/v_env --no-site-packages
           creates=/home/mrv/www/v_env/bin/activate

It fails when it tries to "Create the virtualenv" as it is unable to install the zipp module. The error line is as follows (truncated):

File \"/usr/local/lib/python2.7/dist-packages/importlib_metadata/_init_.py\", line 9, in <module>", "    import zipp", "ImportError: No module named zipp"], "stdout": "", "stdout_lines": []}

I learnt that zipp now requires python 3.6 and upwards while this virtualenv seems to be using python 2.7 Is there any way around this? Or can I mention what version of python I want to use in the playbook itself? I barely know Ansible thus asking for help.

EDIT: I came across this post that mentions specifying the python version - Ansible creating a virtualenv

Following this, I tried:

- name: Create the virtualenv
  command: 
    cmd: virtualenv /home/mrv/www/v_env --no-site-packages -p python3.6
    creates: "/home/mrv/www/v_env/bin/activate"

But this did not work either.

Nikit Parakh
  • 65
  • 1
  • 7

2 Answers2

0

There is a variable in ansible to set the python interpreter(indirectly version) in the host:

Example:

ansible_python_interpreter: "/usr/bin/python3.6"

You can set it through group_vars or inventory or extra-vars. Set the value to the desired python version. So For example, In my virtual environments, I have python defaulted at /home/ps/.pyenv/shims/python, so if I do not set ansible_python_interpreter ansible will use this path,but if you set it to something else, ansible would honor it.

P....
  • 17,421
  • 2
  • 32
  • 52
  • Which exact file would this go in, I am really a beginner here – Nikit Parakh Nov 12 '20 at 15:21
  • for example, with `extra-vars` you can run your playbook as below: `ansible-playbook playbook.yml -i inventory -e "ansible_python_interpreter= "/usr/bin/python3.6"` – gary lopez Nov 12 '20 at 15:25
  • The tool uses vagrant to run the ansible playbooks. So I just use "vagrant provision" to run it. – Nikit Parakh Nov 12 '20 at 15:28
  • You can add it to inventory or see this https://docs.ansible.com/ansible/latest/reference_appendices/python_3_support.html#using-python-3-on-the-managed-machines-with-commands-and-playbooks – P.... Nov 12 '20 at 15:30
  • You can add extra-vars in your Vagrafile. https://www.vagrantup.com/docs/provisioning/ansible_common#extra_vars – gary lopez Nov 12 '20 at 15:33
  • I added it to extra_vars in the vagrantfile, but now, running it throws: ```fatal: [default]: FAILED! => {"ansible_facts": {}, "changed": false, "failed_modules": {"setup": {"failed": true, "module_stderr": "Shared connection to 127.0.0.1 closed.\r\n", "module_stdout": "/bin/sh: 1: /usr/bin/python3.6: not found\r\n", "msg": "The module failed to execute correctly, you probably need to set the interpreter.\nSee stdout/stderr for the exact error", "rc": 127}}, "msg": "The following modules failed to execute: setup\n"}``` – Nikit Parakh Nov 12 '20 at 15:41
  • I found that I don't have python3.6, but 3.8. So I put that instead and it threw the same error – Nikit Parakh Nov 12 '20 at 15:53
  • @NikitParakh you can set that variable for controller node via inventory file. Please see the above link I shared and how to use it. Based on your Question I understand that you need to set it for controller node not controller node – P.... Nov 12 '20 at 22:04
0

I have a recommendation for your tasks with apt module, when this module is used with a loop (with_items) ansible runs individually it's much efficient use a list directly in the name option.

Try as below

- name: Ensure bash, OpenSSL, and libssl are the latest versions
  become: true
  apt: 
    update_cache: yes 
    state: latest  
    name:
      - bash
      - openssl
      - libssl-dev
      - libssl-doc
  tags: packages

- name: install minimum packages
  apt: 
    update_cache: yes 
    state: present
    name:
      - libav-tools
      - build-essential
      - python-pip
      - python-numpy
      - python-scipy
      - python-software-properties
      - python-dev
      - python-setuptools
      - python-libxml2
      - python-libxslt1
      - python3.4-dev
      - libatlas-base-dev
      - gcc
      - gfortran
      - g++
      - binutils
      - libproj-dev
      - gdal-bin
      - python-gdal
      - python-lxml
      - python3-lxml
      - libblas-dev
      - pkg-config
      - gfortran
      - python-dev
      - libxml2-dev
      - libjpeg8-dev
      - libjpeg-dev
      - libpq-dev
      - libpng12-0
      - libpng-dev    
      - libpng12-dev
      - libfreetype6
      - libfreetype6-dev
      - supervisor
      - nginx
      - git
      - ntp
      - htop
      - libcurl4-openssl-dev
      - libgdal-dev
      - libtool
      - libxml2
      - libxslt1.1
      - libxslt1-dev
      - redis-server
      - freetype*
      - php5-gd
      - python-memcache
gary lopez
  • 1,823
  • 7
  • 15
  • You can do even better: construct the list dynamically with set_fact depending on tag and call apt only once with the full dynamic list – Zeitounator Nov 12 '20 at 16:00