diff options
| -rw-r--r-- | playbooks/init/main.yml | 6 | ||||
| -rw-r--r-- | playbooks/init/version.yml | 29 | ||||
| -rw-r--r-- | roles/lib_utils/action_plugins/sanity_checks.py | 57 | ||||
| -rw-r--r-- | roles/openshift_version/defaults/main.yml | 2 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/check_available_rpms.yml | 10 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/first_master.yml | 30 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/first_master_containerized_version.yml (renamed from roles/openshift_version/tasks/set_version_containerized.yml) | 8 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/first_master_rpm_version.yml | 16 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/main.yml | 206 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/masters_and_nodes.yml | 39 | ||||
| -rw-r--r-- | roles/openshift_version/tasks/set_version_rpm.yml | 24 | 
11 files changed, 181 insertions, 246 deletions
| diff --git a/playbooks/init/main.yml b/playbooks/init/main.yml index 20457e508..8a3f4682d 100644 --- a/playbooks/init/main.yml +++ b/playbooks/init/main.yml @@ -17,12 +17,12 @@  - import_playbook: facts.yml -- import_playbook: sanity_checks.yml -  when: not (skip_sanity_checks | default(False)) -  - import_playbook: version.yml    when: not (skip_verison | default(False)) +- import_playbook: sanity_checks.yml +  when: not (skip_sanity_checks | default(False)) +  - name: Initialization Checkpoint End    hosts: all    gather_facts: false diff --git a/playbooks/init/version.yml b/playbooks/init/version.yml index 37a5284d5..ae5470db1 100644 --- a/playbooks/init/version.yml +++ b/playbooks/init/version.yml @@ -2,8 +2,11 @@  # NOTE: requires openshift_facts be run  - name: Determine openshift_version to configure on first master    hosts: oo_first_master -  roles: -  - openshift_version +  tasks: +  - include_role: +      name: openshift_version +      tasks_from: first_master.yml +  - debug: msg="openshift_pkg_version set to {{ openshift_pkg_version }}"  # NOTE: We set this even on etcd hosts as they may also later run as masters,  # and we don't want to install wrong version of docker and have to downgrade @@ -11,11 +14,19 @@  - name: Set openshift_version for etcd, node, and master hosts    hosts: oo_etcd_to_config:oo_nodes_to_config:oo_masters_to_config:!oo_first_master    vars: -    openshift_version: "{{ hostvars[groups.oo_first_master.0].openshift_version }}" -  pre_tasks: +    l_first_master_openshift_version: "{{ hostvars[groups.oo_first_master.0].openshift_version }}" +    l_first_master_openshift_pkg_version: "{{ hostvars[groups.oo_first_master.0].openshift_pkg_version }}" +    l_first_master_openshift_image_tag: "{{ hostvars[groups.oo_first_master.0].openshift_image_tag}}" +  tasks:    - set_fact: -      openshift_pkg_version: -{{ openshift_version }} -    when: openshift_pkg_version is not defined -  - debug: msg="openshift_pkg_version set to {{ openshift_pkg_version }}" -  roles: -  - openshift_version +      openshift_version: "{{ l_first_master_openshift_version }}" +      openshift_pkg_version: "{{ l_first_master_openshift_pkg_version }}" +      openshift_image_tag: "{{ l_first_master_openshift_image_tag }}" + +# NOTE: These steps should only be run against masters and nodes. +- name: Ensure the requested version packages are available. +  hosts: "{{ l_openshift_version_check_hosts | default('oo_nodes_to_config:oo_masters_to_config:!oo_first_master') }}" +  tasks: +  - include_role: +      name: openshift_version +      tasks_from: masters_and_nodes.yml diff --git a/roles/lib_utils/action_plugins/sanity_checks.py b/roles/lib_utils/action_plugins/sanity_checks.py index 1bf332678..09ce55e8f 100644 --- a/roles/lib_utils/action_plugins/sanity_checks.py +++ b/roles/lib_utils/action_plugins/sanity_checks.py @@ -2,6 +2,8 @@  Ansible action plugin to ensure inventory variables are set  appropriately and no conflicting options have been provided.  """ +import re +  from ansible.plugins.action import ActionBase  from ansible import errors @@ -15,6 +17,27 @@ NET_PLUGIN_LIST = (('openshift_use_openshift_sdn', True),                     ('openshift_use_contiv', False),                     ('openshift_use_calico', False)) +ENTERPRISE_TAG_REGEX_ERROR = """openshift_image_tag must be in the format +v#.#[.#[.#]]. Examples: v1.2, v3.4.1, v3.5.1.3, +v3.5.1.3.4, v1.2-1, v1.2.3-4, v1.2.3-4.5, v1.2.3-4.5.6 +You specified openshift_image_tag={}""" + +ORIGIN_TAG_REGEX_ERROR = """openshift_image_tag must be in the format +v#.#.#[-optional.#]. Examples: v1.2.3, v3.5.1-alpha.1 +You specified openshift_image_tag={}""" + +ORIGIN_TAG_REGEX = {'re': '(^v?\\d+\\.\\d+\\.\\d+(-[\\w\\-\\.]*)?$)', +                    'error_msg': ORIGIN_TAG_REGEX_ERROR} +ENTERPRISE_TAG_REGEX = {'re': '(^v\\d+\\.\\d+(\\.\\d+)*(-\\d+(\\.\\d+)*)?$)', +                        'error_msg': ENTERPRISE_TAG_REGEX_ERROR} +IMAGE_TAG_REGEX = {'origin': ORIGIN_TAG_REGEX, +                   'openshift-enterprise': ENTERPRISE_TAG_REGEX} + +CONTAINERIZED_NO_TAG_ERROR_MSG = """To install a containerized Origin release, +you must set openshift_release or openshift_image_tag in your inventory to +specify which version of the OpenShift component images to use. +(Suggestion: add openshift_release="x.y" to inventory.)""" +  def to_bool(var_to_check):      """Determine a boolean value given the multiple @@ -44,6 +67,7 @@ class ActionModule(ActionBase):              type_strings = ", ".join(VALID_DEPLOYMENT_TYPES)              msg = "openshift_deployment_type must be defined and one of {}".format(type_strings)              raise errors.AnsibleModuleError(msg) +        return openshift_deployment_type      def check_python_version(self, hostvars, host, distro):          """Ensure python version is 3 for Fedora and python 2 for others""" @@ -58,6 +82,35 @@ class ActionModule(ActionBase):              if ansible_python['version']['major'] != 2:                  msg = "openshift-ansible requires Python 2 for {};".format(distro) +    def check_image_tag_format(self, hostvars, host, openshift_deployment_type): +        """Ensure openshift_image_tag is formatted correctly""" +        openshift_image_tag = self.template_var(hostvars, host, 'openshift_image_tag') +        if not openshift_image_tag or openshift_image_tag == 'latest': +            return None +        regex_to_match = IMAGE_TAG_REGEX[openshift_deployment_type]['re'] +        res = re.match(regex_to_match, str(openshift_image_tag)) +        if res is None: +            msg = IMAGE_TAG_REGEX[openshift_deployment_type]['error_msg'] +            msg = msg.format(str(openshift_image_tag)) +            raise errors.AnsibleModuleError(msg) + +    def no_origin_image_version(self, hostvars, host, openshift_deployment_type): +        """Ensure we can determine what image version to use with origin +          fail when: +          - openshift_is_containerized +          - openshift_deployment_type == 'origin' +          - openshift_release is not defined +          - openshift_image_tag is not defined""" +        if not openshift_deployment_type == 'origin': +            return None +        oic = self.template_var(hostvars, host, 'openshift_is_containerized') +        if not to_bool(oic): +            return None +        orelease = self.template_var(hostvars, host, 'openshift_release') +        oitag = self.template_var(hostvars, host, 'openshift_image_tag') +        if not orelease and not oitag: +            raise errors.AnsibleModuleError(CONTAINERIZED_NO_TAG_ERROR_MSG) +      def network_plugin_check(self, hostvars, host):          """Ensure only one type of network plugin is enabled"""          res = [] @@ -88,8 +141,10 @@ class ActionModule(ActionBase):      def run_checks(self, hostvars, host):          """Execute the hostvars validations against host"""          distro = self.template_var(hostvars, host, 'ansible_distribution') -        self.check_openshift_deployment_type(hostvars, host) +        odt = self.check_openshift_deployment_type(hostvars, host)          self.check_python_version(hostvars, host, distro) +        self.check_image_tag_format(hostvars, host, odt) +        self.no_origin_image_version(hostvars, host, odt)          self.network_plugin_check(hostvars, host)          self.check_hostname_vars(hostvars, host) diff --git a/roles/openshift_version/defaults/main.yml b/roles/openshift_version/defaults/main.yml index 354699637..e2e6538c9 100644 --- a/roles/openshift_version/defaults/main.yml +++ b/roles/openshift_version/defaults/main.yml @@ -8,3 +8,5 @@ openshift_service_type_dict:  openshift_service_type: "{{ openshift_service_type_dict[openshift_deployment_type] }}"  openshift_use_crio_only: False + +l_first_master_version_task_file: "{{ openshift_is_containerized | ternary('first_master_containerized_version.yml', 'first_master_rpm_version.yml') }}" diff --git a/roles/openshift_version/tasks/check_available_rpms.yml b/roles/openshift_version/tasks/check_available_rpms.yml new file mode 100644 index 000000000..bdbc63d27 --- /dev/null +++ b/roles/openshift_version/tasks/check_available_rpms.yml @@ -0,0 +1,10 @@ +--- +- name: Get available {{ openshift_service_type}} version +  repoquery: +    name: "{{ openshift_service_type}}" +    ignore_excluders: true +  register: rpm_results + +- fail: +    msg: "Package {{ openshift_service_type}} not found" +  when: not rpm_results.results.package_found diff --git a/roles/openshift_version/tasks/first_master.yml b/roles/openshift_version/tasks/first_master.yml new file mode 100644 index 000000000..374725086 --- /dev/null +++ b/roles/openshift_version/tasks/first_master.yml @@ -0,0 +1,30 @@ +--- +# Determine the openshift_version to configure if none has been specified or set previously. + +# Protect the installed version by default unless explicitly told not to, or given an +# openshift_version already. +- name: Use openshift.common.version fact as version to configure if already installed +  set_fact: +    openshift_version: "{{ openshift.common.version }}" +  when: +  - openshift.common.version is defined +  - openshift_version is not defined or openshift_version == "" +  - openshift_protect_installed_version | bool + +- include_tasks: "{{ l_first_master_version_task_file }}" + +- block: +  - debug: +      msg: "openshift_pkg_version was not defined. Falling back to -{{ openshift_version }}" +  - set_fact: +      openshift_pkg_version: -{{ openshift_version }} +  when: +  - openshift_pkg_version is not defined +  - openshift_upgrade_target is not defined + +- block: +  - debug: +      msg: "openshift_image_tag was not defined. Falling back to v{{ openshift_version }}" +  - set_fact: +      openshift_image_tag: v{{ openshift_version }} +  when: openshift_image_tag is not defined diff --git a/roles/openshift_version/tasks/set_version_containerized.yml b/roles/openshift_version/tasks/first_master_containerized_version.yml index a808f050e..e02a75eab 100644 --- a/roles/openshift_version/tasks/set_version_containerized.yml +++ b/roles/openshift_version/tasks/first_master_containerized_version.yml @@ -21,7 +21,7 @@    register: cli_image_version    when:    - openshift_version is not defined -  - not openshift_use_crio_only | bool +  - not openshift_use_crio_only  # Origin latest = pre-release version (i.e. v1.3.0-alpha.1-321-gb095e3a)  - set_fact: @@ -30,7 +30,7 @@    - openshift_version is not defined    - openshift.common.deployment_type == 'origin'    - cli_image_version.stdout_lines[0].split('-') | length > 1 -  - not openshift_use_crio_only | bool +  - not openshift_use_crio_only  - set_fact:      openshift_version: "{{ cli_image_version.stdout_lines[0].split(' ')[1].split('-')[0][1:] }}" @@ -45,14 +45,14 @@    when:    - openshift_version is defined    - openshift_version.split('.') | length == 2 -  - not openshift_use_crio_only | bool +  - not openshift_use_crio_only  - set_fact:      openshift_version: "{{ cli_image_version.stdout_lines[0].split(' ')[1].split('-')[0:2][1:] | join('-') if openshift.common.deployment_type == 'origin' else cli_image_version.stdout_lines[0].split(' ')[1].split('-')[0][1:] }}"    when:    - openshift_version is defined    - openshift_version.split('.') | length == 2 -  - not openshift_use_crio_only | bool +  - not openshift_use_crio_only  # TODO: figure out a way to check for the openshift_version when using CRI-O.  # We should do that using the images in the ostree storage so we don't have diff --git a/roles/openshift_version/tasks/first_master_rpm_version.yml b/roles/openshift_version/tasks/first_master_rpm_version.yml new file mode 100644 index 000000000..264baca65 --- /dev/null +++ b/roles/openshift_version/tasks/first_master_rpm_version.yml @@ -0,0 +1,16 @@ +--- +- name: Set rpm version to configure if openshift_pkg_version specified +  set_fact: +    # Expects a leading "-" in inventory, strip it off here, and remove trailing release, +    openshift_version: "{{ openshift_pkg_version[1:].split('-')[0] }}" +  when: +  - openshift_pkg_version is defined +  - openshift_version is not defined + +# These tasks should only be run against masters and nodes +- name: Set openshift_version for rpm installation +  include_tasks: check_available_rpms.yml + +- set_fact: +    openshift_version: "{{ rpm_results.results.versions.available_versions.0 }}" +  when: openshift_version is not defined diff --git a/roles/openshift_version/tasks/main.yml b/roles/openshift_version/tasks/main.yml index 97e58ffac..b42794858 100644 --- a/roles/openshift_version/tasks/main.yml +++ b/roles/openshift_version/tasks/main.yml @@ -1,206 +1,2 @@  --- -# Determine the openshift_version to configure if none has been specified or set previously. - -# Block attempts to install origin without specifying some kind of version information. -# This is because the latest tags for origin are usually alpha builds, which should not -# be used by default. Users must indicate what they want. -- name: Abort when we cannot safely guess what Origin image version the user wanted -  fail: -    msg: |- -      To install a containerized Origin release, you must set openshift_release or -      openshift_image_tag in your inventory to specify which version of the OpenShift -      component images to use. You may want the latest (usually alpha) releases or -      a more stable release. (Suggestion: add openshift_release="x.y" to inventory.) -  when: -  - openshift_is_containerized | bool -  - openshift.common.deployment_type == 'origin' -  - openshift_release is not defined -  - openshift_image_tag is not defined - -# Normalize some values that we need in a certain format that might be confusing: -- set_fact: -    openshift_release: "{{ openshift_release[1:] }}" -  when: -  - openshift_release is defined -  - openshift_release[0] == 'v' - -- set_fact: -    openshift_release: "{{ openshift_release | string }}" -  when: -  - openshift_release is defined - -# Verify that the image tag is in a valid format -- when: -  - openshift_image_tag is defined -  - openshift_image_tag != "latest" -  block: - -  # Verifies that when the deployment type is origin the version: -  # - starts with a v -  # - Has 3 integers seperated by dots -  # It also allows for optional trailing data which: -  # - must start with a dash -  # - may contain numbers, letters, dashes and dots. -  - name: (Origin) Verify openshift_image_tag is valid -    when: openshift.common.deployment_type == 'origin' -    assert: -      that: -      - "{{ openshift_image_tag is match('(^v?\\d+\\.\\d+\\.\\d+(-[\\w\\-\\.]*)?$)') }}" -      msg: |- -        openshift_image_tag must be in the format v#.#.#[-optional.#]. Examples: v1.2.3, v3.5.1-alpha.1 -        You specified openshift_image_tag={{ openshift_image_tag }} - -  # Verifies that when the deployment type is openshift-enterprise the version: -  # - starts with a v -  # - Has at least 2 integers seperated by dots -  # It also allows for optional trailing data which: -  # - must start with a dash -  # - may contain numbers -  # - may containe dots (https://github.com/openshift/openshift-ansible/issues/5192) -  # -  - name: (Enterprise) Verify openshift_image_tag is valid -    when: openshift.common.deployment_type == 'openshift-enterprise' -    assert: -      that: -      - "{{ openshift_image_tag is match('(^v\\d+\\.\\d+(\\.\\d+)*(-\\d+(\\.\\d+)*)?$)') }}" -      msg: |- -        openshift_image_tag must be in the format v#.#[.#[.#]]. Examples: v1.2, v3.4.1, v3.5.1.3, -        v3.5.1.3.4, v1.2-1, v1.2.3-4, v1.2.3-4.5, v1.2.3-4.5.6 -        You specified openshift_image_tag={{ openshift_image_tag }} - -# Make sure we copy this to a fact if given a var: -- set_fact: -    openshift_version: "{{ openshift_version | string }}" -  when: openshift_version is defined - -# Protect the installed version by default unless explicitly told not to, or given an -# openshift_version already. -- name: Use openshift.common.version fact as version to configure if already installed -  set_fact: -    openshift_version: "{{ openshift.common.version }}" -  when: -  - openshift.common.version is defined -  - openshift_version is not defined or openshift_version == "" -  - openshift_protect_installed_version | bool - -# The rest of these tasks should only execute on -# masters and nodes as we can verify they have subscriptions -- when: -  - inventory_hostname in groups['oo_masters_to_config'] or inventory_hostname in groups['oo_nodes_to_config'] -  block: -  - name: Set openshift_version for rpm installation -    include_tasks: set_version_rpm.yml -    when: not openshift_is_containerized | bool - -  - name: Set openshift_version for containerized installation -    include_tasks: set_version_containerized.yml -    when: openshift_is_containerized | bool - -  - block: -    - name: Get available {{ openshift_service_type}} version -      repoquery: -        name: "{{ openshift_service_type}}" -        ignore_excluders: true -      register: rpm_results -    - fail: -        msg: "Package {{ openshift_service_type}} not found" -      when: not rpm_results.results.package_found -    - set_fact: -        openshift_rpm_version: "{{ rpm_results.results.versions.available_versions.0 | default('0.0', True) }}" -    - name: Fail if rpm version and docker image version are different -      fail: -        msg: "OCP rpm version {{ openshift_rpm_version }} is different from OCP image version {{ openshift_version }}" -      # Both versions have the same string representation -      when: -      - openshift_rpm_version != openshift_version -      # if openshift_pkg_version or openshift_image_tag is defined, user gives a permission the rpm and docker image versions can differ -      - openshift_pkg_version is not defined -      - openshift_image_tag is not defined -    when: -    - openshift_is_containerized | bool -    - not openshift_is_atomic | bool - -  # Warn if the user has provided an openshift_image_tag but is not doing a containerized install -  # NOTE: This will need to be modified/removed for future container + rpm installations work. -  - name: Warn if openshift_image_tag is defined when not doing a containerized install -    debug: -      msg: > -        openshift_image_tag is used for containerized installs. If you are trying to -        specify an image for a non-container install see oreg_url or oreg_url_master or oreg_url_node. -    when: -    - not openshift_is_containerized | bool -    - openshift_image_tag is defined - -  # At this point we know openshift_version is set appropriately. Now we set -  # openshift_image_tag and openshift_pkg_version, so all roles can always assume -  # each of this variables *will* be set correctly and can use them per their -  # intended purpose. - -  - block: -    - debug: -        msg: "openshift_image_tag was not defined. Falling back to v{{ openshift_version }}" - -    - set_fact: -        openshift_image_tag: v{{ openshift_version }} - -    when: openshift_image_tag is not defined - -  - block: -    - debug: -        msg: "openshift_pkg_version was not defined. Falling back to -{{ openshift_version }}" - -    - set_fact: -        openshift_pkg_version: -{{ openshift_version }} - -    when: -    - openshift_pkg_version is not defined -    - openshift_upgrade_target is not defined - -  - fail: -      msg: openshift_version role was unable to set openshift_version -    name: Abort if openshift_version was not set -    when: openshift_version is not defined - -  - fail: -      msg: openshift_version role was unable to set openshift_image_tag -    name: Abort if openshift_image_tag was not set -    when: openshift_image_tag is not defined - -  - fail: -      msg: openshift_version role was unable to set openshift_pkg_version -    name: Abort if openshift_pkg_version was not set -    when: -    - openshift_pkg_version is not defined -    - openshift_upgrade_target is not defined - - -  - fail: -      msg: "No OpenShift version available; please ensure your systems are fully registered and have access to appropriate yum repositories." -    name: Abort if openshift_pkg_version was not set -    when: -    - not openshift_is_containerized | bool -    - openshift_version == '0.0' - -  # We can't map an openshift_release to full rpm version like we can with containers; make sure -  # the rpm version we looked up matches the release requested and error out if not. -  - name: For an RPM install, abort when the release requested does not match the available version. -    when: -    - not openshift_is_containerized | bool -    - openshift_release is defined -    assert: -      that: -      - openshift_version.startswith(openshift_release) | bool -      msg: |- -        You requested openshift_release {{ openshift_release }}, which is not matched by -        the latest OpenShift RPM we detected as {{ openshift_service_type }}-{{ openshift_version }} -        on host {{ inventory_hostname }}. -        We will only install the latest RPMs, so please ensure you are getting the release -        you expect. You may need to adjust your Ansible inventory, modify the repositories -        available on the host, or run the appropriate OpenShift upgrade playbook. - -  # The end result of these three variables is quite important so make sure they are displayed and logged: -  - debug: var=openshift_release - -  - debug: var=openshift_image_tag - -  - debug: var=openshift_pkg_version +# This role is meant to be used with include_role. diff --git a/roles/openshift_version/tasks/masters_and_nodes.yml b/roles/openshift_version/tasks/masters_and_nodes.yml new file mode 100644 index 000000000..fbeb22d8b --- /dev/null +++ b/roles/openshift_version/tasks/masters_and_nodes.yml @@ -0,0 +1,39 @@ +--- +# These tasks should only be run against masters and nodes + +- block: +  - name: Check openshift_version for rpm installation +    include_tasks: check_available_rpms.yml +  - name: Fail if rpm version and docker image version are different +    fail: +      msg: "OCP rpm version {{ openshift_rpm_version }} is different from OCP image version {{ openshift_version }}" +    # Both versions have the same string representation +    when: rpm_results.results.versions.available_versions.0 != openshift_version +  # block when +  when: not openshift_is_atomic | bool + +# We can't map an openshift_release to full rpm version like we can with containers; make sure +# the rpm version we looked up matches the release requested and error out if not. +- name: For an RPM install, abort when the release requested does not match the available version. +  when: +  - not openshift_is_containerized | bool +  - openshift_release is defined +  assert: +    that: +    - l_rpm_version.startswith(openshift_release) | bool +    msg: |- +      You requested openshift_release {{ openshift_release }}, which is not matched by +      the latest OpenShift RPM we detected as {{ openshift_service_type }}-{{ l_rpm_version }} +      on host {{ inventory_hostname }}. +      We will only install the latest RPMs, so please ensure you are getting the release +      you expect. You may need to adjust your Ansible inventory, modify the repositories +      available on the host, or run the appropriate OpenShift upgrade playbook. +  vars: +    l_rpm_version: "{{ rpm_results.results.versions.available_versions.0 }}" + +# The end result of these three variables is quite important so make sure they are displayed and logged: +- debug: var=openshift_release + +- debug: var=openshift_image_tag + +- debug: var=openshift_pkg_version diff --git a/roles/openshift_version/tasks/set_version_rpm.yml b/roles/openshift_version/tasks/set_version_rpm.yml deleted file mode 100644 index c7ca5ceae..000000000 --- a/roles/openshift_version/tasks/set_version_rpm.yml +++ /dev/null @@ -1,24 +0,0 @@ ---- -- name: Set rpm version to configure if openshift_pkg_version specified -  set_fact: -    # Expects a leading "-" in inventory, strip it off here, and remove trailing release, -    openshift_version: "{{ openshift_pkg_version[1:].split('-')[0] }}" -  when: -  - openshift_pkg_version is defined -  - openshift_version is not defined - -- block: -  - name: Get available {{ openshift_service_type}} version -    repoquery: -      name: "{{ openshift_service_type}}" -      ignore_excluders: true -    register: rpm_results - -  - fail: -      msg: "Package {{ openshift_service_type}} not found" -    when: not rpm_results.results.package_found - -  - set_fact: -      openshift_version: "{{ rpm_results.results.versions.available_versions.0 | default('0.0', True) }}" -  when: -  - openshift_version is not defined | 
