diff --git a/.travis.yml b/.travis.yml index bcb44082..e90285fd 100644 --- a/.travis.yml +++ b/.travis.yml @@ -15,6 +15,7 @@ env: - BASE_DISTRO: ubuntu:precise - BASE_DISTRO: ubuntu:trusty - BASE_DISTRO: ubuntu:xenial + - BASE_DISTRO: ubuntu:beaver - BASE_DISTRO: ubuntu:artful - BASE_DISTRO: alpine:3.5 - BASE_DISTRO: alpine:3.4 diff --git a/README.md b/README.md index c27dc936..2ef1351c 100644 --- a/README.md +++ b/README.md @@ -5,8 +5,6 @@ Ansible Container is a tool for building Docker images and orchestrating containers using Ansible playbooks. -**NOTE: Ansible Container is no longer under active development as of February 2018.** - ## How it works Use Ansible Container to manage the container lifecycle from development, through testing, to production: @@ -36,14 +34,14 @@ Use Ansible Container to manage the container lifecycle from development, throug Install using *pip*, the Python package manager: - $ sudo pip install ansible-container[docker,openshift] + $ sudo pip install "ansible-container[docker,openshift]" Or, to install without root privileges, use [virtualenv](https://virtualenv.pypa.io/en/stable/) to first create a Python sandbox: $ virtualenv ansible-container $ source ansible-container/bin/activate - $ pip install ansible-container[docker,openshift] + $ pip install "ansible-container[docker,openshift]" For more details, prerequisite, and instructions on installing the latest development release, please view our [Installation Guide](https://docs.ansible.com/ansible-container/installation.html). diff --git a/container/core.py b/container/core.py index db6c36c2..793ce8b6 100644 --- a/container/core.py +++ b/container/core.py @@ -696,7 +696,8 @@ def _find_base_image_id(engine, service_name, service): return image_id def _intermediate_build_container_name(engine, service_name, image_fingerprint, role_name): - return u'%s-%s-%s' % (engine.container_name_for_service(service_name), image_fingerprint[:8], role_name) + safe_role_name = re.sub(r"[^a-zA-Z0-9_.-]", "_", role_name) + return u'%s-%s-%s' % (engine.container_name_for_service(service_name), image_fingerprint[:8], safe_role_name) def _run_intermediate_build_container(engine, container_name, cur_image_id, service_name, service, **kwargs): diff --git a/container/docker/engine.py b/container/docker/engine.py index 0e632faa..a4d2fc50 100644 --- a/container/docker/engine.py +++ b/container/docker/engine.py @@ -1123,37 +1123,29 @@ def build_conductor_image(self, base_path, base_image, prebaking=False, cache=Tr tarball_file = open(tarball_path, 'rb') logger.info('Starting Docker build of Ansible Container Conductor image (please be patient)...') # FIXME: Error out properly if build of conductor fails. - if self.debug: - for line in self.client.api.build(fileobj=tarball_file, - custom_context=True, - tag=tag, - rm=True, - decode=True, - nocache=not cache): - try: - if line.get('status') == 'Downloading': - # skip over lines that give spammy byte-by-byte - # progress of downloads - continue - elif 'errorDetail' in line: - raise exceptions.AnsibleContainerException( - "Error building conductor image: {0}".format(line['errorDetail']['message'])) - except ValueError: - pass - except exceptions.AnsibleContainerException: - raise - - # this bypasses the fancy colorized logger for things that - # are just STDOUT of a process - plainLogger.debug(text.to_text(line.get('stream', json.dumps(line))).rstrip()) - return self.get_image_id_by_tag(tag) - else: - image = self.client.images.build(fileobj=tarball_file, - custom_context=True, - tag=tag, - rm=True, - nocache=not cache) - return image.id + for line in self.client.api.build(fileobj=tarball_file, + custom_context=True, + tag=tag, + rm=True, + decode=True, + nocache=not cache): + try: + if line.get('status') == 'Downloading': + # skip over lines that give spammy byte-by-byte + # progress of downloads + continue + elif 'errorDetail' in line: + raise exceptions.AnsibleContainerException( + "Error building conductor image: {0}".format(line['errorDetail']['message'])) + except ValueError: + pass + except exceptions.AnsibleContainerException: + raise + + # this bypasses the fancy colorized logger for things that + # are just STDOUT of a process + plainLogger.debug(text.to_text(line.get('stream', json.dumps(line))).rstrip()) + return self.get_image_id_by_tag(tag) def get_runtime_volume_id(self, mount_point): try: diff --git a/container/docker/templates/conductor-src-dockerfile.j2 b/container/docker/templates/conductor-src-dockerfile.j2 index baf5cb3d..c8a751b2 100644 --- a/container/docker/templates/conductor-src-dockerfile.j2 +++ b/container/docker/templates/conductor-src-dockerfile.j2 @@ -16,7 +16,7 @@ RUN yum update -y && \ yum clean all {% elif distro in ["amazonlinux"] %} RUN yum -y update && \ - yum -y install make git gcc python27-devel rsync libffi-devel openssl-devel && \ + yum -y install make git gcc python27-devel rsync libffi-devel openssl-devel tar && \ yum clean all {% elif "rhel" in distro %} RUN yum -y update-minimal --disablerepo "*" \ diff --git a/container/utils/__init__.py b/container/utils/__init__.py index 10168261..cc603d49 100644 --- a/container/utils/__init__.py +++ b/container/utils/__init__.py @@ -272,7 +272,7 @@ def hash_dir(hash_obj, dir_path): for root, dirs, files in os.walk(dir_path, topdown=True): for file_path in files: abs_file_path = os.path.join(root, file_path) - hash_obj.update(abs_file_path) + hash_obj.update(abs_file_path.encode('utf-8')) hash_obj.update('::') hash_file(hash_obj, abs_file_path) diff --git a/requirements.txt b/requirements.txt index c43c5a64..5f902778 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,7 @@ Jinja2>=2.9 pip>=6.0 PyYAML>=3.12 +docker==2.7.0 requests>=2 ruamel.yaml>=0.15.34 six>=1.10 diff --git a/setup.py b/setup.py index fdb3593a..08a98497 100644 --- a/setup.py +++ b/setup.py @@ -7,7 +7,10 @@ from setuptools import setup, find_packages from setuptools.command.test import test as TestCommand from setuptools.command.sdist import sdist as SDistCommand -from pip.req import parse_requirements +try: + from pip._internal.req import parse_requirements +except ImportError: + from pip.req import parse_requirements import container class PlaybookAsTests(TestCommand): diff --git a/test/roles/validate-start-stop-restart/tasks/main.yml b/test/roles/validate-start-stop-restart/tasks/main.yml index 21437316..32fe8f0f 100644 --- a/test/roles/validate-start-stop-restart/tasks/main.yml +++ b/test/roles/validate-start-stop-restart/tasks/main.yml @@ -24,7 +24,7 @@ - include: includes/show-output.yml output_file=./task.output registered_output="{{ output }}" - name: Wait until built containers are running - command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test{{ distro.name|replace('-','') }}_{{ distro.name }}_1" + command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test-{{ distro.name }}_{{ distro.name }}_1" register: container_run_status until: container_run_status.stdout == 'running' retries: 6 @@ -34,7 +34,7 @@ - run - name: Note start time - command: "docker inspect --format='{{'{{'}} .State.StartedAt {{'}}'}}' test{{ distro.name|replace('-','') }}_{{ distro.name }}_1" + command: "docker inspect --format='{{'{{'}} .State.StartedAt {{'}}'}}' test-{{ distro.name }}_{{ distro.name }}_1" register: container_run_start tags: - restart @@ -53,7 +53,7 @@ - include: includes/show-output.yml output_file=./task.output registered_output="{{ output }}" - name: Wait until built containers are running - command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test{{ distro.name|replace('-','') }}_{{ distro.name }}_1" + command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test-{{ distro.name }}_{{ distro.name }}_1" register: container_restart_status until: container_restart_status.stdout == 'running' retries: 6 @@ -63,7 +63,7 @@ - run - name: Note start time - command: "docker inspect --format='{{'{{'}} .State.StartedAt {{'}}'}}' test{{ distro.name|replace('-','') }}_{{ distro.name }}_1" + command: "docker inspect --format='{{'{{'}} .State.StartedAt {{'}}'}}' test-{{ distro.name }}_{{ distro.name }}_1" register: container_restart_start tags: - restart @@ -93,7 +93,7 @@ - include: includes/show-output.yml output_file=./task.output registered_output="{{ output }}" - name: Wait until built containers are stop - command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test{{ distro.name|replace('-','') }}_{{ distro.name }}_1" + command: "docker inspect --format='{{'{{'}} .State.Status {{'}}'}}' test-{{ distro.name }}_{{ distro.name }}_1" register: container_stop_status until: container_stop_status.stdout != 'running' retries: 6