diff options
Diffstat (limited to 'roles')
28 files changed, 424 insertions, 172 deletions
diff --git a/roles/etcd/tasks/main.yml b/roles/etcd/tasks/main.yml index 064544b03..afec6b30b 100644 --- a/roles/etcd/tasks/main.yml +++ b/roles/etcd/tasks/main.yml @@ -39,7 +39,8 @@ - name: Check for etcd service presence command: systemctl show etcd.service register: etcd_show - + changed_when: false + - name: Mask system etcd when containerized when: openshift.common.is_containerized | bool and 'LoadState=not-found' not in etcd_show.stdout command: systemctl mask etcd diff --git a/roles/openshift_cli/meta/main.yml b/roles/openshift_cli/meta/main.yml index 62de120c6..2c982e278 100644 --- a/roles/openshift_cli/meta/main.yml +++ b/roles/openshift_cli/meta/main.yml @@ -12,6 +12,7 @@ galaxy_info: categories: - cloud dependencies: -- role: openshift_common - role: openshift_docker when: openshift.common.is_containerized | bool +- role: openshift_common +- role: openshift_cli_facts diff --git a/roles/openshift_cli/tasks/main.yml b/roles/openshift_cli/tasks/main.yml index e82903b81..bfa60e5b0 100644 --- a/roles/openshift_cli/tasks/main.yml +++ b/roles/openshift_cli/tasks/main.yml @@ -1,10 +1,4 @@ --- -# TODO: move this to a new 'cli' role -- openshift_facts: - role: common - local_facts: - cli_image: "{{ osm_image | default(None) }}" - - name: Install clients action: "{{ ansible_pkg_mgr }} name={{ openshift.common.service_type }}-clients state=present" when: not openshift.common.is_containerized | bool diff --git a/roles/openshift_cli_facts/meta/main.yml b/roles/openshift_cli_facts/meta/main.yml new file mode 100644 index 000000000..59acde215 --- /dev/null +++ b/roles/openshift_cli_facts/meta/main.yml @@ -0,0 +1,15 @@ +--- +galaxy_info: + author: Jason DeTiberus + description: OpenShift CLI Facts + company: Red Hat, Inc. + license: Apache License, Version 2.0 + min_ansible_version: 1.9 + platforms: + - name: EL + versions: + - 7 + categories: + - cloud +dependencies: +- role: openshift_facts diff --git a/roles/openshift_cli_facts/tasks/main.yml b/roles/openshift_cli_facts/tasks/main.yml new file mode 100644 index 000000000..dd1ed8965 --- /dev/null +++ b/roles/openshift_cli_facts/tasks/main.yml @@ -0,0 +1,6 @@ +--- +# TODO: move this to a new 'cli' role +- openshift_facts: + role: common + local_facts: + cli_image: "{{ osm_image | default(None) }}" diff --git a/roles/openshift_cloud_provider/defaults/main.yml b/roles/openshift_cloud_provider/defaults/main.yml deleted file mode 100644 index 6c7403232..000000000 --- a/roles/openshift_cloud_provider/defaults/main.yml +++ /dev/null @@ -1,7 +0,0 @@ ---- -ocp_os_auth_url: "{{ lookup('env', 'OS_AUTH_URL') }}" -ocp_os_username: "{{ lookup('env', 'OS_USERNAME') }}" -ocp_os_password: "{{ lookup('env', 'OS_PASSWORD') }}" -ocp_os_tenant_id: "{{ lookup('env', 'OS_TENANT_ID') }}" -ocp_os_tenant_name: "{{ lookup('env', 'OS_TENANT_NAME') }}" -ocp_os_region: "{{ lookup('env', 'OS_REGION_NAME') }}" diff --git a/roles/openshift_cloud_provider/meta/main.yml b/roles/openshift_cloud_provider/meta/main.yml new file mode 100644 index 000000000..8ab95bf5a --- /dev/null +++ b/roles/openshift_cloud_provider/meta/main.yml @@ -0,0 +1,15 @@ +--- +galaxy_info: + author: Sylvain Baubeau, Andrew Butcher + description: OpenShift Cloud Provider + company: Red Hat, Inc. + license: Apache License, Version 2.0 + min_ansible_version: 1.9 + platforms: + - name: EL + versions: + - 7 + categories: + - cloud +dependencies: +- role: openshift_facts diff --git a/roles/openshift_cloud_provider/tasks/aws.yml b/roles/openshift_cloud_provider/tasks/aws.yml new file mode 100644 index 000000000..bf2abcbf5 --- /dev/null +++ b/roles/openshift_cloud_provider/tasks/aws.yml @@ -0,0 +1,6 @@ +- name: Create cloud config + ini_file: + dest: "{{ openshift.common.config_base }}/cloudprovider/aws.conf" + section: Global + option: Zone + value: "{{ openshift.provider.zone }}" diff --git a/roles/openshift_cloud_provider/tasks/main.yml b/roles/openshift_cloud_provider/tasks/main.yml index e14f944e8..471fd686b 100644 --- a/roles/openshift_cloud_provider/tasks/main.yml +++ b/roles/openshift_cloud_provider/tasks/main.yml @@ -1,3 +1,24 @@ --- +- name: Set cloud provider facts + openshift_facts: + role: cloudprovider + openshift_env: "{{ item | oo_openshift_env }}" + openshift_env_structures: + - 'openshift.cloudprovider.aws.*' + - 'openshift.cloudprovider.openstack.*' + no_log: true + with_items: + - "{{ hostvars[inventory_hostname] }}" + - "{{ hostvars }}" + +- name: Create cloudprovider config dir + file: + path: "{{ openshift.common.config_base }}/cloudprovider" + state: directory + when: has_cloudprovider | bool + - include: openstack.yml - when: "openshift_cloud_provider is defined and openshift_cloud_provider == 'openstack' and 'provider' in openshift and openshift.provider.name == 'openstack'" + when: cloudprovider_is_openstack | bool + +- include: aws.yml + when: cloudprovider_is_aws | bool diff --git a/roles/openshift_cloud_provider/tasks/openstack.yml b/roles/openshift_cloud_provider/tasks/openstack.yml index a56f1891a..c501121e5 100644 --- a/roles/openshift_cloud_provider/tasks/openstack.yml +++ b/roles/openshift_cloud_provider/tasks/openstack.yml @@ -1,9 +1,10 @@ +--- - fail: msg: "The Openstack integration requires OpenShift Enterprise 3.2 or Origin 1.2." when: not openshift.common.version_gte_3_2_or_1_2 | bool -- name: Create /etc/cloud.conf +- name: Create cloud config template: - dest: /etc/cloud.conf - src: openstack/cloud.conf.j2 - when: ocp_os_auth_url and ocp_os_username and ocp_os_password and (ocp_os_tenant_id or ocp_os_tenant_name)
\ No newline at end of file + dest: "{{ openshift.common.config_base }}/cloudprovider/openstack.conf" + src: openstack.conf.j2 + when: "'auth_url' in openshift.cloudprovider.openstack and 'username' in openshift.cloudprovider.openstack and 'password' in openshift.cloudprovider.openstack and ('tenant_id' in openshift.cloudprovider.openstack or 'tenant_name' in openshift.cloudprovider.openstack)" diff --git a/roles/openshift_cloud_provider/templates/openstack.conf.j2 b/roles/openshift_cloud_provider/templates/openstack.conf.j2 new file mode 100644 index 000000000..1b70edc16 --- /dev/null +++ b/roles/openshift_cloud_provider/templates/openstack.conf.j2 @@ -0,0 +1,17 @@ +[Global] +auth-url = {{ openshift.cloudprovider.openstack.auth_url }} +username = {{ openshift.cloudprovider.openstack.username }} +password = {{ openshift.cloudprovider.openstack.password }} +{% if 'tenant_id' in openshift.cloudprovider.openstack %} +tenant-id = {{ openshift.cloudprovider.openstack.tenant_id }} +{% else %} +tenant-name = {{ openshift.cloudprovider.openstack.tenant_name }} +{% endif %} +{% if 'region' in openshift.cloudprovider.openstack %} +region = {{ openshift.cloudprovider.openstack.region }} +{% endif %} +{% if 'lb_subnet_id' in openshift.cloudprovider.openstack %} ++ ++[LoadBalancer] ++subnet-id = {{ openshift.cloudprovider.openstack.lb_subnet_id }} ++{% endif %} diff --git a/roles/openshift_cloud_provider/templates/openstack/cloud.conf.j2 b/roles/openshift_cloud_provider/templates/openstack/cloud.conf.j2 deleted file mode 100644 index 388f3a735..000000000 --- a/roles/openshift_cloud_provider/templates/openstack/cloud.conf.j2 +++ /dev/null @@ -1,17 +0,0 @@ -[Global] -auth-url = {{ ocp_os_auth_url }} -username = {{ ocp_os_username }} -password = {{ ocp_os_password }} -{% if ocp_os_tenant_id %} -tenant-id = {{ ocp_os_tenant_id }} -{% else %} -tenant-name = {{ ocp_os_tenant_name }} -{% endif %} -{% if ocp_os_region %} -region = {{ ocp_os_region }} -{% endif %} -{% if ocp_os_lb_subnet_id is defined %} -+ -+[LoadBalancer] -+subnet-id = {{ ocp_os_lb_subnet_id }} -+{% endif %}
\ No newline at end of file diff --git a/roles/openshift_cloud_provider/vars/main.yml b/roles/openshift_cloud_provider/vars/main.yml new file mode 100644 index 000000000..c608e9b54 --- /dev/null +++ b/roles/openshift_cloud_provider/vars/main.yml @@ -0,0 +1,4 @@ +--- +has_cloudprovider: "{{ 'cloudprovider' in openshift and 'kind' in openshift.cloudprovider and openshift.cloudprovider.kind != None }}" +cloudprovider_is_aws: "{{ has_cloudprovider | bool and openshift.cloudprovider.kind == 'aws' }}" +cloudprovider_is_openstack: "{{ has_cloudprovider | bool and openshift.cloudprovider.kind == 'openstack' }}" diff --git a/roles/openshift_common/meta/main.yml b/roles/openshift_common/meta/main.yml index d879db0aa..02150406d 100644 --- a/roles/openshift_common/meta/main.yml +++ b/roles/openshift_common/meta/main.yml @@ -12,7 +12,6 @@ galaxy_info: categories: - cloud dependencies: -- { role: os_firewall } -- { role: openshift_facts } -- { role: openshift_repos } -- { role: openshift_cloud_provider } +- role: os_firewall +- role: openshift_facts +- role: openshift_repos diff --git a/roles/openshift_common/tasks/main.yml b/roles/openshift_common/tasks/main.yml index 541efe27a..b6074ff64 100644 --- a/roles/openshift_common/tasks/main.yml +++ b/roles/openshift_common/tasks/main.yml @@ -28,8 +28,12 @@ use_manageiq: "{{ openshift_use_manageiq | default(None) }}" data_dir: "{{ openshift_data_dir | default(None) }}" +# Using oo_image_tag_to_rpm_version here is a workaround for how +# openshift_version is set. That value is computed based on either RPM +# versions or image tags. openshift_common's usage requires that it be a RPM +# version and openshift_cli expects it to be an image tag. - name: Install the base package for versioning - action: "{{ ansible_pkg_mgr }} name={{ openshift.common.service_type }}{{ openshift_version | default('') }} state=present" + action: "{{ ansible_pkg_mgr }} name={{ openshift.common.service_type }}{{ openshift_version | default('') | oo_image_tag_to_rpm_version }} state=present" when: not openshift.common.is_containerized | bool # This invocation also updates the version facts which are necessary diff --git a/roles/openshift_facts/library/openshift_facts.py b/roles/openshift_facts/library/openshift_facts.py index ea7406e5b..0d31d4ddf 100755 --- a/roles/openshift_facts/library/openshift_facts.py +++ b/roles/openshift_facts/library/openshift_facts.py @@ -26,6 +26,8 @@ from distutils.util import strtobool from distutils.version import LooseVersion import struct import socket +from dbus import SystemBus, Interface +from dbus.exceptions import DBusException def migrate_docker_facts(facts): @@ -332,14 +334,10 @@ def normalize_provider_facts(provider, metadata): facts = dict(name=provider, metadata=metadata, network=dict(interfaces=[], ipv6_enabled=False)) - if os.path.exists('/etc/cloud.conf'): - for arg in ('api_server_args', 'controller_args', 'kubelet_args'): - facts[arg] = {'cloud-provider': [provider], - 'cloud-config': ['/etc/cloud.conf']} if provider == 'gce': facts = normalize_gce_facts(metadata, facts) - elif provider == 'ec2': + elif provider == 'aws': facts = normalize_aws_facts(metadata, facts) elif provider == 'openstack': facts = normalize_openstack_facts(metadata, facts) @@ -749,8 +747,9 @@ def set_version_facts_if_unset(facts): """ if 'common' in facts: deployment_type = facts['common']['deployment_type'] - facts['common']['version'] = version = get_openshift_version(facts) + version = get_openshift_version(facts) if version is not None: + facts['common']['version'] = version if deployment_type == 'origin': version_gte_3_1_or_1_1 = LooseVersion(version) >= LooseVersion('1.1.0') version_gte_3_1_1_or_1_1_1 = LooseVersion(version) >= LooseVersion('1.1.1') @@ -918,6 +917,101 @@ def get_current_config(facts): return current_config +def build_kubelet_args(facts): + """ Build node kubelet_args """ + cloud_cfg_path = os.path.join(facts['common']['config_base'], + 'cloudprovider') + if 'node' in facts: + kubelet_args = {} + if 'cloudprovider' in facts: + if facts['cloudprovider']['kind'] == 'aws': + kubelet_args['cloud-provider'] = ['aws'] + kubelet_args['cloud-config'] = [cloud_cfg_path + '/aws.conf'] + if facts['cloudprovider']['kind'] == 'openstack': + kubelet_args['cloud-provider'] = ['openstack'] + kubelet_args['cloud-config'] = [cloud_cfg_path + '/openstack.conf'] + if kubelet_args != {}: + facts = merge_facts({'node': {'kubelet_args': kubelet_args}}, facts, [], []) + return facts + +def build_controller_args(facts): + """ Build master controller_args """ + cloud_cfg_path = os.path.join(facts['common']['config_base'], + 'cloudprovider') + if 'master' in facts: + controller_args = {} + if 'cloudprovider' in facts: + if facts['cloudprovider']['kind'] == 'aws': + controller_args['cloud-provider'] = ['aws'] + controller_args['cloud-config'] = [cloud_cfg_path + '/aws.conf'] + if facts['cloudprovider']['kind'] == 'openstack': + controller_args['cloud-provider'] = ['openstack'] + controller_args['cloud-config'] = [cloud_cfg_path + '/openstack.conf'] + if controller_args != {}: + facts = merge_facts({'master': {'controller_args': controller_args}}, facts, [], []) + return facts + +def build_api_server_args(facts): + """ Build master api_server_args """ + cloud_cfg_path = os.path.join(facts['common']['config_base'], + 'cloudprovider') + if 'master' in facts: + api_server_args = {} + if 'cloudprovider' in facts: + if facts['cloudprovider']['kind'] == 'aws': + api_server_args['cloud-provider'] = ['aws'] + api_server_args['cloud-config'] = [cloud_cfg_path + '/aws.conf'] + if facts['cloudprovider']['kind'] == 'openstack': + api_server_args['cloud-provider'] = ['openstack'] + api_server_args['cloud-config'] = [cloud_cfg_path + '/openstack.conf'] + if api_server_args != {}: + facts = merge_facts({'master': {'api_server_args': api_server_args}}, facts, [], []) + return facts + +def is_service_running(service): + """ Queries systemd through dbus to see if the service is running """ + service_running = False + bus = SystemBus() + systemd = bus.get_object('org.freedesktop.systemd1', '/org/freedesktop/systemd1') + manager = Interface(systemd, dbus_interface='org.freedesktop.systemd1.Manager') + try: + service_unit = service if service.endswith('.service') else manager.GetUnit('{0}.service'.format(service)) + service_proxy = bus.get_object('org.freedesktop.systemd1', str(service_unit)) + service_properties = Interface(service_proxy, dbus_interface='org.freedesktop.DBus.Properties') + service_load_state = service_properties.Get('org.freedesktop.systemd1.Unit', 'LoadState') + service_active_state = service_properties.Get('org.freedesktop.systemd1.Unit', 'ActiveState') + if service_load_state == 'loaded' and service_active_state == 'active': + service_running = True + except DBusException: + pass + + return service_running + +def get_version_output(binary, version_cmd): + """ runs and returns the version output for a command """ + cmd = [] + for item in (binary, version_cmd): + if isinstance(item, list): + cmd.extend(item) + else: + cmd.append(item) + + if os.path.isfile(cmd[0]): + _, output, _ = module.run_command(cmd) + return output + +def get_docker_version_info(): + """ Parses and returns the docker version info """ + result = None + if is_service_running('docker'): + version_info = yaml.safe_load(get_version_output('/usr/bin/docker', 'version')) + if 'Server' in version_info: + result = { + 'api_version': version_info['Server']['API version'], + 'version': version_info['Server']['Version'] + } + return result + def get_openshift_version(facts, cli_image=None): """ Get current version of openshift on the host @@ -959,9 +1053,10 @@ def get_openshift_version(facts, cli_image=None): if version is None and cli_image is not None: # Assume we haven't installed the environment yet and we need - # to query the latest image - exit_code, output, _ = module.run_command(['docker', 'run', '--rm', cli_image, 'version']) - version = parse_openshift_version(output) + # to query the latest image, but only if docker is installed + if 'docker' in facts and 'version' in facts['docker']: + exit_code, output, _ = module.run_command(['docker', 'run', '--rm', cli_image, 'version']) + version = parse_openshift_version(output) return version @@ -1084,31 +1179,6 @@ def merge_facts(orig, new, additive_facts_to_overwrite, protected_facts_to_overw facts[key] = copy.deepcopy(new[key]) return facts - -def merge_provider_facts(facts): - """ Recursively merge provider facts dicts - - Args: - facts (dict): existing facts - Returns: - dict: the facts dict updated with the provider config - """ - if 'provider' not in facts: - return facts - if 'master' in facts: - for arg in ('api_server_args', 'controller_args'): - facts['master'][arg] = merge_facts( - facts['provider'].get(arg, {}), - facts['master'].get(arg, {}), - [], []) - if 'node' in facts: - facts['node']['kubelet_args'] = merge_facts( - facts['provider'].get('kubelet_args', {}), - facts['node'].get('kubelet_args', {}), - [], []) - return facts - - def save_local_facts(filename, facts): """ Save local facts @@ -1235,8 +1305,10 @@ def set_container_facts_if_unset(facts): if safe_get_bool(facts['common']['is_containerized']): facts['common']['admin_binary'] = '/usr/local/bin/oadm' facts['common']['client_binary'] = '/usr/local/bin/oc' - base_version = get_openshift_version(facts, cli_image).split('-')[0] - facts['common']['image_tag'] = "v" + base_version + openshift_version = get_openshift_version(facts, cli_image) + if openshift_version is not None: + base_version = openshift_version.split('-')[0] + facts['common']['image_tag'] = "v" + base_version return facts @@ -1302,13 +1374,20 @@ class OpenShiftFacts(object): Raises: OpenShiftFactsUnsupportedRoleError: """ - known_roles = ['common', 'master', 'node', 'etcd', 'hosted', 'docker'] + known_roles = ['cloudprovider', + 'common', + 'docker', + 'etcd', + 'hosted', + 'master', + 'node'] # Disabling too-many-arguments, this should be cleaned up as a TODO item. # pylint: disable=too-many-arguments def __init__(self, role, filename, local_facts, additive_facts_to_overwrite=None, openshift_env=None, + openshift_env_structures=None, protected_facts_to_overwrite=None): self.changed = False self.filename = filename @@ -1321,12 +1400,14 @@ class OpenShiftFacts(object): self.facts = self.generate_facts(local_facts, additive_facts_to_overwrite, openshift_env, + openshift_env_structures, protected_facts_to_overwrite) def generate_facts(self, local_facts, additive_facts_to_overwrite, openshift_env, + openshift_env_structures, protected_facts_to_overwrite): """ Generate facts @@ -1343,6 +1424,7 @@ class OpenShiftFacts(object): local_facts = self.init_local_facts(local_facts, additive_facts_to_overwrite, openshift_env, + openshift_env_structures, protected_facts_to_overwrite) roles = local_facts.keys() @@ -1359,7 +1441,6 @@ class OpenShiftFacts(object): local_facts, additive_facts_to_overwrite, protected_facts_to_overwrite) - facts = merge_provider_facts(facts) facts['current_config'] = get_current_config(facts) facts = set_url_facts_if_unset(facts) facts = set_project_cfg_facts_if_unset(facts) @@ -1372,6 +1453,9 @@ class OpenShiftFacts(object): facts = set_sdn_facts_if_unset(facts, self.system_facts) facts = set_deployment_facts_if_unset(facts) facts = set_container_facts_if_unset(facts) + facts = build_kubelet_args(facts) + facts = build_controller_args(facts) + facts = build_api_server_args(facts) facts = set_version_facts_if_unset(facts) facts = set_manageiq_facts_if_unset(facts) facts = set_aggregate_facts(facts) @@ -1408,6 +1492,19 @@ class OpenShiftFacts(object): debug_level=2) if 'master' in roles: + scheduler_predicates = [ + {"name": "MatchNodeSelector"}, + {"name": "PodFitsResources"}, + {"name": "PodFitsPorts"}, + {"name": "NoDiskConflict"}, + {"name": "Region", "argument": {"serviceAffinity" : {"labels" : ["region"]}}} + ] + scheduler_priorities = [ + {"name": "LeastRequestedPriority", "weight": 1}, + {"name": "SelectorSpreadPriority", "weight": 1}, + {"name": "Zone", "weight" : 2, "argument": {"serviceAntiAffinity" : {"label": "zone"}}} + ] + defaults['master'] = dict(api_use_ssl=True, api_port='8443', controllers_port='8444', console_use_ssl=True, @@ -1423,7 +1520,9 @@ class OpenShiftFacts(object): session_secrets_file='', access_token_max_seconds=86400, auth_token_max_seconds=500, - oauth_grant_method='auto') + oauth_grant_method='auto', + scheduler_predicates=scheduler_predicates, + scheduler_priorities=scheduler_priorities) if 'node' in roles: defaults['node'] = dict(labels={}, annotations={}, @@ -1432,7 +1531,15 @@ class OpenShiftFacts(object): set_node_ip=False) if 'docker' in roles: - defaults['docker'] = dict(disable_push_dockerhub=False) + docker = dict(disable_push_dockerhub=False) + version_info = get_docker_version_info() + if version_info is not None: + docker['api_version'] = version_info['api_version'] + docker['version'] = version_info['version'] + defaults['docker'] = docker + + if 'cloudprovider' in roles: + defaults['cloudprovider'] = dict(kind=None) defaults['hosted'] = dict( registry=dict( @@ -1452,7 +1559,6 @@ class OpenShiftFacts(object): ) ) - return defaults def guess_host_provider(self): @@ -1488,7 +1594,7 @@ class OpenShiftFacts(object): metadata['instance'].pop('serviceAccounts', None) elif (virt_type == 'xen' and virt_role == 'guest' and re.match(r'.*\.amazon$', product_version)): - provider = 'ec2' + provider = 'aws' metadata_url = 'http://169.254.169.254/latest/meta-data/' metadata = get_provider_metadata(metadata_url) elif re.search(r'OpenStack', product_name): @@ -1530,11 +1636,53 @@ class OpenShiftFacts(object): ) return provider_facts - # Disabling too-many-branches. This should be cleaned up as a TODO item. - #pylint: disable=too-many-branches + @staticmethod + def split_openshift_env_fact_keys(openshift_env_fact, openshift_env_structures): + """ Split openshift_env facts based on openshift_env structures. + + Args: + openshift_env_fact (string): the openshift_env fact to split + ex: 'openshift_cloudprovider_openstack_auth_url' + openshift_env_structures (list): a list of structures to determine fact keys + ex: ['openshift.cloudprovider.openstack.*'] + Returns: + list: a list of keys that represent the fact + ex: ['openshift', 'cloudprovider', 'openstack', 'auth_url'] + """ + # By default, we'll split an openshift_env fact by underscores. + fact_keys = openshift_env_fact.split('_') + + # Determine if any of the provided variable structures match the fact. + matching_structure = None + if openshift_env_structures != None: + for structure in openshift_env_structures: + if re.match(structure, openshift_env_fact): + matching_structure = structure + # Fact didn't match any variable structures so return the default fact keys. + if matching_structure is None: + return fact_keys + + final_keys = [] + structure_keys = matching_structure.split('.') + for structure_key in structure_keys: + # Matched current key. Add to final keys. + if structure_key == fact_keys[structure_keys.index(structure_key)]: + final_keys.append(structure_key) + # Wildcard means we will be taking everything from here to the end of the fact. + elif structure_key == '*': + final_keys.append('_'.join(fact_keys[structure_keys.index(structure_key):])) + # Shouldn't have gotten here, return the fact keys. + else: + return fact_keys + return final_keys + + # Disabling too-many-branches and too-many-locals. + # This should be cleaned up as a TODO item. + #pylint: disable=too-many-branches, too-many-locals def init_local_facts(self, facts=None, additive_facts_to_overwrite=None, openshift_env=None, + openshift_env_structures=None, protected_facts_to_overwrite=None): """ Initialize the local facts @@ -1562,8 +1710,8 @@ class OpenShiftFacts(object): for fact, value in openshift_env.iteritems(): oo_env_facts = dict() current_level = oo_env_facts - keys = fact.split('_')[1:] - if keys[0] != self.role: + keys = self.split_openshift_env_fact_keys(fact, openshift_env_structures)[1:] + if len(keys) > 0 and keys[0] != self.role: continue for key in keys: if key == keys[-1]: @@ -1691,6 +1839,7 @@ def main(): local_facts=dict(default=None, type='dict', required=False), additive_facts_to_overwrite=dict(default=[], type='list', required=False), openshift_env=dict(default={}, type='dict', required=False), + openshift_env_structures=dict(default=[], type='list', required=False), protected_facts_to_overwrite=dict(default=[], type='list', required=False), ), supports_check_mode=True, @@ -1701,6 +1850,7 @@ def main(): local_facts = module.params['local_facts'] additive_facts_to_overwrite = module.params['additive_facts_to_overwrite'] openshift_env = module.params['openshift_env'] + openshift_env_structures = module.params['openshift_env_structures'] protected_facts_to_overwrite = module.params['protected_facts_to_overwrite'] fact_file = '/etc/ansible/facts.d/openshift.fact' @@ -1710,6 +1860,7 @@ def main(): local_facts, additive_facts_to_overwrite, openshift_env, + openshift_env_structures, protected_facts_to_overwrite) file_params = module.params.copy() diff --git a/roles/openshift_facts/tasks/main.yml b/roles/openshift_facts/tasks/main.yml index 50e7e5747..a2eb27fbb 100644 --- a/roles/openshift_facts/tasks/main.yml +++ b/roles/openshift_facts/tasks/main.yml @@ -30,6 +30,6 @@ cluster_id: "{{ openshift_cluster_id | default('default') }}" hostname: "{{ openshift_hostname | default(None) }}" ip: "{{ openshift_ip | default(None) }}" - is_containerized: "{{ containerized | default(None) }}" + is_containerized: "{{ l_is_containerized | default(None) }}" public_hostname: "{{ openshift_public_hostname | default(None) }}" public_ip: "{{ openshift_public_ip | default(None) }}" diff --git a/roles/openshift_master/meta/main.yml b/roles/openshift_master/meta/main.yml index 4eda4a8e2..8ae6bc371 100644 --- a/roles/openshift_master/meta/main.yml +++ b/roles/openshift_master/meta/main.yml @@ -13,3 +13,5 @@ galaxy_info: - cloud dependencies: - role: openshift_cli +- role: openshift_cloud_provider +- role: openshift_master_facts diff --git a/roles/openshift_master/tasks/main.yml b/roles/openshift_master/tasks/main.yml index e64339ea6..23994cdcf 100644 --- a/roles/openshift_master/tasks/main.yml +++ b/roles/openshift_master/tasks/main.yml @@ -23,71 +23,6 @@ msg: "Pacemaker based HA is not supported at this time when used with containerized installs" when: openshift_master_ha | bool and openshift_master_cluster_method == "pacemaker" and openshift.common.is_containerized | bool -- name: Set master facts - openshift_facts: - role: master - local_facts: - cluster_method: "{{ openshift_master_cluster_method | default(None) }}" - cluster_hostname: "{{ openshift_master_cluster_hostname | default(None) }}" - cluster_public_hostname: "{{ openshift_master_cluster_public_hostname | default(None) }}" - debug_level: "{{ openshift_master_debug_level | default(openshift.common.debug_level) }}" - api_port: "{{ openshift_master_api_port | default(None) }}" - api_url: "{{ openshift_master_api_url | default(None) }}" - api_use_ssl: "{{ openshift_master_api_use_ssl | default(None) }}" - public_api_url: "{{ openshift_master_public_api_url | default(None) }}" - console_path: "{{ openshift_master_console_path | default(None) }}" - console_port: "{{ openshift_master_console_port | default(None) }}" - console_url: "{{ openshift_master_console_url | default(None) }}" - console_use_ssl: "{{ openshift_master_console_use_ssl | default(None) }}" - public_console_url: "{{ openshift_master_public_console_url | default(None) }}" - logging_public_url: "{{ openshift_master_logging_public_url | default(None) }}" - metrics_public_url: "{{ openshift_master_metrics_public_url | default(None) }}" - logout_url: "{{ openshift_master_logout_url | default(None) }}" - extension_scripts: "{{ openshift_master_extension_scripts | default(None) }}" - extension_stylesheets: "{{ openshift_master_extension_stylesheets | default(None) }}" - extensions: "{{ openshift_master_extensions | default(None) }}" - oauth_template: "{{ openshift_master_oauth_template | default(None) }}" - etcd_hosts: "{{ openshift_master_etcd_hosts | default(None) }}" - etcd_port: "{{ openshift_master_etcd_port | default(None) }}" - etcd_use_ssl: "{{ openshift_master_etcd_use_ssl | default(None) }}" - etcd_urls: "{{ openshift_master_etcd_urls | default(None) }}" - embedded_etcd: "{{ openshift_master_embedded_etcd | default(None) }}" - embedded_kube: "{{ openshift_master_embedded_kube | default(None) }}" - embedded_dns: "{{ openshift_master_embedded_dns | default(None) }}" - dns_port: "{{ openshift_master_dns_port | default(None) }}" - bind_addr: "{{ openshift_master_bind_addr | default(None) }}" - pod_eviction_timeout: "{{ openshift_master_pod_eviction_timeout | default(None) }}" - portal_net: "{{ openshift_master_portal_net | default(None) }}" - session_max_seconds: "{{ openshift_master_session_max_seconds | default(None) }}" - session_name: "{{ openshift_master_session_name | default(None) }}" - session_secrets_file: "{{ openshift_master_session_secrets_file | default(None) }}" - session_auth_secrets: "{{ openshift_master_session_auth_secrets | default(None) }}" - session_encryption_secrets: "{{ openshift_master_session_encryption_secrets | default(None) }}" - access_token_max_seconds: "{{ openshift_master_access_token_max_seconds | default(None) }}" - auth_token_max_seconds: "{{ openshift_master_auth_token_max_seconds | default(None) }}" - identity_providers: "{{ openshift_master_identity_providers | default(None) }}" - registry_url: "{{ oreg_url | default(None) }}" - oauth_grant_method: "{{ openshift_master_oauth_grant_method | default(None) }}" - sdn_cluster_network_cidr: "{{ osm_cluster_network_cidr | default(None) }}" - sdn_host_subnet_length: "{{ osm_host_subnet_length | default(None) }}" - default_subdomain: "{{ openshift_master_default_subdomain | default(osm_default_subdomain) | default(None) }}" - custom_cors_origins: "{{ osm_custom_cors_origins | default(None) }}" - default_node_selector: "{{ osm_default_node_selector | default(None) }}" - project_request_message: "{{ osm_project_request_message | default(None) }}" - project_request_template: "{{ osm_project_request_template | default(None) }}" - mcs_allocator_range: "{{ osm_mcs_allocator_range | default(None) }}" - mcs_labels_per_project: "{{ osm_mcs_labels_per_project | default(None) }}" - uid_allocator_range: "{{ osm_uid_allocator_range | default(None) }}" - router_selector: "{{ openshift_router_selector | default(None) }}" - registry_selector: "{{ openshift_registry_selector | default(None) }}" - api_server_args: "{{ osm_api_server_args | default(None) }}" - controller_args: "{{ osm_controller_args | default(None) }}" - infra_nodes: "{{ openshift_infra_nodes | default(None) }}" - disabled_features: "{{ osm_disabled_features | default(None) }}" - master_count: "{{ openshift_master_count | default(None) }}" - controller_lease_ttl: "{{ osm_controller_lease_ttl | default(None) }}" - master_image: "{{ osm_image | default(None) }}" - - name: Install Master package action: "{{ ansible_pkg_mgr }} name={{ openshift.common.service_type }}-master{{ openshift_version }} state=present" when: not openshift.common.is_containerized | bool @@ -130,9 +65,9 @@ - restart master controllers - name: Create the scheduler config - template: + copy: + content: "{{ scheduler_config | to_nice_json }}" dest: "{{ openshift_master_scheduler_conf }}" - src: scheduler.json.j2 backup: true notify: - restart master diff --git a/roles/openshift_master/templates/atomic-openshift-master.j2 b/roles/openshift_master/templates/atomic-openshift-master.j2 index c848e0ac2..7f1576682 100644 --- a/roles/openshift_master/templates/atomic-openshift-master.j2 +++ b/roles/openshift_master/templates/atomic-openshift-master.j2 @@ -4,6 +4,11 @@ CONFIG_FILE={{ openshift_master_config_file }} IMAGE_VERSION={{ openshift_version }} {% endif %} +{% if 'cloudprovider' in openshift and 'aws' in openshift.cloudprovider and openshift.cloudprovider.kind == 'aws' and 'access_key' in openshift.cloudprovider.aws and 'secret_key' in openshift.cloudprovider.aws %} +AWS_ACCESS_KEY_ID={{ openshift.cloudprovider.aws.access_key }} +AWS_SECRET_ACCESS_KEY={{ openshift.cloudprovider.aws.secret_key }} +{% endif %} + # Proxy configuration # Origin uses standard HTTP_PROXY environment variables. Be sure to set # NO_PROXY for your master diff --git a/roles/openshift_master/templates/native-cluster/atomic-openshift-master-api.j2 b/roles/openshift_master/templates/native-cluster/atomic-openshift-master-api.j2 index 8e2d927aa..fa2323a2c 100644 --- a/roles/openshift_master/templates/native-cluster/atomic-openshift-master-api.j2 +++ b/roles/openshift_master/templates/native-cluster/atomic-openshift-master-api.j2 @@ -4,6 +4,11 @@ CONFIG_FILE={{ openshift_master_config_file }} IMAGE_VERSION={{ openshift_version }} {% endif %} +{% if 'cloudprovider' in openshift and 'aws' in openshift.cloudprovider and openshift.cloudprovider.kind == 'aws' and 'access_key' in openshift.cloudprovider.aws and 'secret_key' in openshift.cloudprovider.aws %} +AWS_ACCESS_KEY_ID={{ openshift.cloudprovider.aws.access_key }} +AWS_SECRET_ACCESS_KEY={{ openshift.cloudprovider.aws.secret_key }} +{% endif %} + # Proxy configuration # Origin uses standard HTTP_PROXY environment variables. Be sure to set # NO_PROXY for your master diff --git a/roles/openshift_master/templates/native-cluster/atomic-openshift-master-controllers.j2 b/roles/openshift_master/templates/native-cluster/atomic-openshift-master-controllers.j2 index 5c6cb2dcb..632dfbb8a 100644 --- a/roles/openshift_master/templates/native-cluster/atomic-openshift-master-controllers.j2 +++ b/roles/openshift_master/templates/native-cluster/atomic-openshift-master-controllers.j2 @@ -4,6 +4,11 @@ CONFIG_FILE={{ openshift_master_config_file }} IMAGE_VERSION={{ openshift_version }} {% endif %} +{% if 'cloudprovider' in openshift and 'aws' in openshift.cloudprovider and openshift.cloudprovider.kind == 'aws' and 'access_key' in openshift.cloudprovider.aws and 'secret_key' in openshift.cloudprovider.aws %} +AWS_ACCESS_KEY_ID={{ openshift.cloudprovider.aws.access_key }} +AWS_SECRET_ACCESS_KEY={{ openshift.cloudprovider.aws.secret_key }} +{% endif %} + # Proxy configuration # Origin uses standard HTTP_PROXY environment variables. Be sure to set # NO_PROXY for your master diff --git a/roles/openshift_master/templates/scheduler.json.j2 b/roles/openshift_master/templates/scheduler.json.j2 deleted file mode 100644 index cb5f43bb2..000000000 --- a/roles/openshift_master/templates/scheduler.json.j2 +++ /dev/null @@ -1,15 +0,0 @@ -{ - "kind": "Policy", - "apiVersion": "v1", - "predicates": [ - {"name": "MatchNodeSelector"}, - {"name": "PodFitsResources"}, - {"name": "PodFitsPorts"}, - {"name": "NoDiskConflict"}, - {"name": "Region", "argument": {"serviceAffinity" : {"labels" : ["region"]}}} - ],"priorities": [ - {"name": "LeastRequestedPriority", "weight": 1}, - {"name": "ServiceSpreadingPriority", "weight": 1}, - {"name": "Zone", "weight" : 2, "argument": {"serviceAntiAffinity" : {"label": "zone"}}} - ] -} diff --git a/roles/openshift_master/vars/main.yml b/roles/openshift_master/vars/main.yml index 75f08e378..198f9235d 100644 --- a/roles/openshift_master/vars/main.yml +++ b/roles/openshift_master/vars/main.yml @@ -8,6 +8,12 @@ openshift_master_session_secrets_file: "{{ openshift_master_config_dir }}/sessio openshift_master_policy: "{{ openshift_master_config_dir }}/policy.json" openshift_version: "{{ openshift_pkg_version | default(openshift_image_tag) | default(openshift.common.image_tag) | default('') }}" +scheduler_config: + kind: Policy + apiVersion: v1 + predicates: "{{ openshift.master.scheduler_predicates }}" + priorities: "{{ openshift.master.scheduler_priorities }}" + openshift_master_valid_grant_methods: - auto - prompt diff --git a/roles/openshift_master_facts/meta/main.yml b/roles/openshift_master_facts/meta/main.yml new file mode 100644 index 000000000..9dbf719f8 --- /dev/null +++ b/roles/openshift_master_facts/meta/main.yml @@ -0,0 +1,15 @@ +--- +galaxy_info: + author: Jason DeTiberus + description: OpenShift Master Facts + company: Red Hat, Inc. + license: Apache License, Version 2.0 + min_ansible_version: 1.9 + platforms: + - name: EL + versions: + - 7 + categories: + - cloud +dependencies: +- role: openshift_facts diff --git a/roles/openshift_master_facts/tasks/main.yml b/roles/openshift_master_facts/tasks/main.yml new file mode 100644 index 000000000..2a3e38af4 --- /dev/null +++ b/roles/openshift_master_facts/tasks/main.yml @@ -0,0 +1,67 @@ +--- +- name: Set master facts + openshift_facts: + role: master + local_facts: + cluster_method: "{{ openshift_master_cluster_method | default(None) }}" + cluster_hostname: "{{ openshift_master_cluster_hostname | default(None) }}" + cluster_public_hostname: "{{ openshift_master_cluster_public_hostname | default(None) }}" + debug_level: "{{ openshift_master_debug_level | default(openshift.common.debug_level) }}" + api_port: "{{ openshift_master_api_port | default(None) }}" + api_url: "{{ openshift_master_api_url | default(None) }}" + api_use_ssl: "{{ openshift_master_api_use_ssl | default(None) }}" + public_api_url: "{{ openshift_master_public_api_url | default(None) }}" + console_path: "{{ openshift_master_console_path | default(None) }}" + console_port: "{{ openshift_master_console_port | default(None) }}" + console_url: "{{ openshift_master_console_url | default(None) }}" + console_use_ssl: "{{ openshift_master_console_use_ssl | default(None) }}" + public_console_url: "{{ openshift_master_public_console_url | default(None) }}" + logging_public_url: "{{ openshift_master_logging_public_url | default(None) }}" + metrics_public_url: "{{ openshift_master_metrics_public_url | default(None) }}" + logout_url: "{{ openshift_master_logout_url | default(None) }}" + extension_scripts: "{{ openshift_master_extension_scripts | default(None) }}" + extension_stylesheets: "{{ openshift_master_extension_stylesheets | default(None) }}" + extensions: "{{ openshift_master_extensions | default(None) }}" + oauth_template: "{{ openshift_master_oauth_template | default(None) }}" + etcd_hosts: "{{ openshift_master_etcd_hosts | default(None) }}" + etcd_port: "{{ openshift_master_etcd_port | default(None) }}" + etcd_use_ssl: "{{ openshift_master_etcd_use_ssl | default(None) }}" + etcd_urls: "{{ openshift_master_etcd_urls | default(None) }}" + embedded_etcd: "{{ openshift_master_embedded_etcd | default(None) }}" + embedded_kube: "{{ openshift_master_embedded_kube | default(None) }}" + embedded_dns: "{{ openshift_master_embedded_dns | default(None) }}" + dns_port: "{{ openshift_master_dns_port | default(None) }}" + bind_addr: "{{ openshift_master_bind_addr | default(None) }}" + pod_eviction_timeout: "{{ openshift_master_pod_eviction_timeout | default(None) }}" + portal_net: "{{ openshift_master_portal_net | default(None) }}" + session_max_seconds: "{{ openshift_master_session_max_seconds | default(None) }}" + session_name: "{{ openshift_master_session_name | default(None) }}" + session_secrets_file: "{{ openshift_master_session_secrets_file | default(None) }}" + session_auth_secrets: "{{ openshift_master_session_auth_secrets | default(None) }}" + session_encryption_secrets: "{{ openshift_master_session_encryption_secrets | default(None) }}" + access_token_max_seconds: "{{ openshift_master_access_token_max_seconds | default(None) }}" + auth_token_max_seconds: "{{ openshift_master_auth_token_max_seconds | default(None) }}" + identity_providers: "{{ openshift_master_identity_providers | default(None) }}" + registry_url: "{{ oreg_url | default(None) }}" + oauth_grant_method: "{{ openshift_master_oauth_grant_method | default(None) }}" + sdn_cluster_network_cidr: "{{ osm_cluster_network_cidr | default(None) }}" + sdn_host_subnet_length: "{{ osm_host_subnet_length | default(None) }}" + default_subdomain: "{{ openshift_master_default_subdomain | default(osm_default_subdomain) | default(None) }}" + custom_cors_origins: "{{ osm_custom_cors_origins | default(None) }}" + default_node_selector: "{{ osm_default_node_selector | default(None) }}" + project_request_message: "{{ osm_project_request_message | default(None) }}" + project_request_template: "{{ osm_project_request_template | default(None) }}" + mcs_allocator_range: "{{ osm_mcs_allocator_range | default(None) }}" + mcs_labels_per_project: "{{ osm_mcs_labels_per_project | default(None) }}" + uid_allocator_range: "{{ osm_uid_allocator_range | default(None) }}" + router_selector: "{{ openshift_router_selector | default(None) }}" + registry_selector: "{{ openshift_registry_selector | default(None) }}" + api_server_args: "{{ osm_api_server_args | default(None) }}" + controller_args: "{{ osm_controller_args | default(None) }}" + infra_nodes: "{{ openshift_infra_nodes | default(None) }}" + disabled_features: "{{ osm_disabled_features | default(None) }}" + master_count: "{{ openshift_master_count | default(None) }}" + controller_lease_ttl: "{{ osm_controller_lease_ttl | default(None) }}" + master_image: "{{ osm_image | default(None) }}" + scheduler_predicates: "{{ openshift_master_scheduler_predicates | default(None) }}" + scheduler_priorities: "{{ openshift_master_scheduler_priorities | default(None) }}" diff --git a/roles/openshift_node/meta/main.yml b/roles/openshift_node/meta/main.yml index 702012489..84ba9ac2e 100644 --- a/roles/openshift_node/meta/main.yml +++ b/roles/openshift_node/meta/main.yml @@ -12,5 +12,6 @@ galaxy_info: categories: - cloud dependencies: -- role: openshift_common - role: openshift_docker +- role: openshift_cloud_provider +- role: openshift_common diff --git a/roles/openshift_node/tasks/main.yml b/roles/openshift_node/tasks/main.yml index 993c8c0cd..80b3e710d 100644 --- a/roles/openshift_node/tasks/main.yml +++ b/roles/openshift_node/tasks/main.yml @@ -81,6 +81,21 @@ notify: - restart node +- name: Configure AWS Cloud Provider Settings + lineinfile: + dest: /etc/sysconfig/{{ openshift.common.service_type }}-node + regexp: "{{ item.regex }}" + line: "{{ item.line }}" + create: true + with_items: + - regex: '^AWS_ACCESS_KEY_ID=' + line: "AWS_ACCESS_KEY_ID={{ openshift.cloudprovider.aws.access_key }}" + - regex: '^AWS_SECRET_ACCESS_KEY=' + line: "AWS_SECRET_ACCESS_KEY={{ openshift.cloudprovider.aws.secret_key }}" + when: "'cloudprovider' in openshift and 'aws' in openshift.cloudprovider and openshift.cloudprovider.kind == 'aws' and 'access_key' in openshift.cloudprovider.aws and 'secret_key' in openshift.cloudprovider.aws" + notify: + - restart node + - name: Additional storage plugin configuration include: storage_plugins/main.yml |