diff --git a/roles/ipaserver/library/ipaserver_enable_ipa.py b/roles/ipaserver/library/ipaserver_enable_ipa.py index 332c72ffe867d749780d7bdbfef8980d1f86d239..0292a6583b11906c95236fb20763b098ed53e9e9 100644 --- a/roles/ipaserver/library/ipaserver_enable_ipa.py +++ b/roles/ipaserver/library/ipaserver_enable_ipa.py @@ -5,7 +5,7 @@ # # Based on ipa-server-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,15 +39,18 @@ description: Enable IPA options: hostname: description: Fully qualified name of this host - required: yes + type: str + required: no setup_dns: description: Configure bind with our zone - required: no + type: bool + required: yes setup_ca: description: Configure a dogtag CA - required: no + type: bool + required: yes author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -58,6 +61,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( + check_imports, AnsibleModuleLog, setup_logging, options, paths, api, sysrestore, tasks, service, bindinstance, redirect_stdout, services ) @@ -66,13 +70,14 @@ from ansible.module_utils.ansible_ipa_server import ( def main(): ansible_module = AnsibleModule( argument_spec=dict( - hostname=dict(required=False), + hostname=dict(required=False, type='str'), setup_dns=dict(required=True, type='bool'), setup_ca=dict(required=True, type='bool'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_load_cache.py b/roles/ipaserver/library/ipaserver_load_cache.py index e3f6fd32ae5c8175d105b90e1296ee5d24fed04d..0806c1d11a1249ca1b927d360b12e09952448ea1 100644 --- a/roles/ipaserver/library/ipaserver_load_cache.py +++ b/roles/ipaserver/library/ipaserver_load_cache.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,9 +39,10 @@ description: Load cache file options: dm_password: description: Directory Manager password - required: no + type: str + required: yes author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -54,7 +55,7 @@ import os from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - setup_logging, options, paths, read_cache + check_imports, setup_logging, options, paths, read_cache ) @@ -62,11 +63,12 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), + dm_password=dict(required=True, type='str', no_log=True), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() # set values ############################################################ diff --git a/roles/ipaserver/library/ipaserver_master_password.py b/roles/ipaserver/library/ipaserver_master_password.py index 3021498ba77ef60dc7ffc69f6830e3dd221da56d..d048a839882d2586d2572e5702ed09e83c368d0a 100644 --- a/roles/ipaserver/library/ipaserver_master_password.py +++ b/roles/ipaserver/library/ipaserver_master_password.py @@ -5,7 +5,7 @@ # # Based on ipa-server-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -40,12 +40,14 @@ description: options: dm_password: description: Directory Manager password - required: no + type: str + required: yes master_password: description: kerberos master password (normally autogenerated) - required: yes + type: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -54,6 +56,7 @@ EXAMPLES = ''' RETURN = ''' password: description: The master password + type: str returned: always ''' @@ -61,6 +64,7 @@ import os from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( + check_imports, setup_logging, options, paths, read_cache, ipa_generate_password ) @@ -69,13 +73,14 @@ def main(): module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - master_password=dict(required=False, no_log=True), + dm_password=dict(required=True, type='str', no_log=True), + master_password=dict(required=False, type='str', no_log=True), ), - supports_check_mode=True, + supports_check_mode=False, ) module._ansible_debug = True + check_imports(module) setup_logging() options.dm_password = module.params.get('dm_password') diff --git a/roles/ipaserver/library/ipaserver_prepare.py b/roles/ipaserver/library/ipaserver_prepare.py index 7a65a9f57ae96c897349631046a8563050c2b822..f8277c11f1e403549d023958e0d5d88a6bbb21f1 100644 --- a/roles/ipaserver/library/ipaserver_prepare.py +++ b/roles/ipaserver/library/ipaserver_prepare.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,116 +39,176 @@ description: Prepare IPA server deployment options: force: description: Installer force parameter - required: yes + type: bool + default: no + required: no dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes ip_addresses: description: List of Master Server IP Addresses - required: yes + type: list + elements: str + required: no domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no ca_cert_files: description: List of files containing CA certificates for the service certificate files - required: yes + type: list + elements: str + required: no no_host_dns: description: Do not use DNS for hostname lookup during installation - required: yes + type: bool + default: no + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no setup_kra: description: Configure a dogtag KRA - required: yes + type: bool + default: no + required: no setup_dns: description: Configure bind with our zone - required: yes + type: bool + default: no + required: no external_ca: description: External ca setting - required: yes + type: bool + required: no external_ca_type: description: Type of the external CA - required: yes + type: str + required: no external_ca_profile: description: Specify the certificate profile/template to use at the external CA - required: yes + type: str + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no allow_zone_overlap: description: Create DNS zone even if it already exists - required: yes + type: bool + default: no + required: no reverse_zones: description: The reverse DNS zones to use - required: yes + type: list + elements: str + required: no no_reverse: description: Do not create new reverse DNS zone - required: yes + type: bool + default: no + required: no auto_reverse: description: Create necessary reverse zones - required: yes + type: bool + default: no + required: no forwarders: description: Add DNS forwarders - required: yes + type: list + elements: str + required: no no_forwarders: description: Do not add any DNS forwarders, use root servers instead - required: yes + type: bool + default: no + required: no auto_forwarders: description: Use DNS forwarders configured in /etc/resolv.conf - required: yes + type: bool + default: no + required: no forward_policy: description: DNS forwarding policy for global forwarders - required: yes + type: str + choices: ['first', 'only'] + required: no no_dnssec_validation: description: Disable DNSSEC validation - required: yes + type: bool + default: no + required: no enable_compat: description: Enable support for trusted domains for old clients - required: yes + type: bool + default: no + required: no netbios_name: description: NetBIOS name of the IPA domain - required: yes + type: str + required: no rid_base: description: Start value for mapping UIDs and GIDs to RIDs - required: yes + type: int + required: no secondary_rid_base: description: Start value of the secondary range for mapping UIDs and GIDs to RIDs - required: yes + type: int + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no + random_serial_numbers: + description: Enable random serial numbers + type: bool + default: no + required: no sid_generation_always: description: Enable SID generation always - required: yes + type: bool + default: no + required: no _hostname_overridden: description: The installer _hostname_overridden setting - required: yes + type: bool + default: no + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -161,8 +221,8 @@ import os from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, - ansible_module_get_parsed_ip_addresses, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, + paths, ansible_module_get_parsed_ip_addresses, redirect_stdout, adtrust, api, default_subject_base, default_ca_subject_dn, ipautil, installutils, ca, kra, dns, get_server_ip_address, no_matching_interface_for_ip_address_warning, @@ -175,13 +235,15 @@ def main(): argument_spec=dict( # basic force=dict(required=False, type='bool', default=False), - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - ip_addresses=dict(required=False, type='list', default=[]), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=False), - ca_cert_files=dict(required=False, type='list', default=[]), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + ip_addresses=dict(required=False, type='list', elements='str', + default=[]), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), + ca_cert_files=dict(required=False, type='list', elements='str', + default=[]), no_host_dns=dict(required=False, type='bool', default=False), # server setup_adtrust=dict(required=False, type='bool', default=False), @@ -191,26 +253,30 @@ def main(): # client # certificate system external_ca=dict(required=False, type='bool'), - external_ca_type=dict(required=False), - external_ca_profile=dict(required=False), - external_cert_files=dict(required=False, type='list', default=[]), - subject_base=dict(required=False), - ca_subject=dict(required=False), + external_ca_type=dict(required=False, type='str'), + external_ca_profile=dict(required=False, type='str'), + external_cert_files=dict(required=False, type='list', + elements='str', default=[]), + subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), # dns allow_zone_overlap=dict(required=False, type='bool', default=False), - reverse_zones=dict(required=False, type='list', default=[]), + reverse_zones=dict(required=False, type='list', elements='str', + default=[]), no_reverse=dict(required=False, type='bool', default=False), auto_reverse=dict(required=False, type='bool', default=False), - forwarders=dict(required=False, type='list', default=[]), + forwarders=dict(required=False, type='list', elements='str', + default=[]), no_forwarders=dict(required=False, type='bool', default=False), auto_forwarders=dict(required=False, type='bool', default=False), - forward_policy=dict(default=None, choices=['first', 'only']), + forward_policy=dict(required=False, type='str', + choices=['first', 'only'], default=None), no_dnssec_validation=dict(required=False, type='bool', default=False), # ad trust enable_compat=dict(required=False, type='bool', default=False), - netbios_name=dict(required=False), + netbios_name=dict(required=False, type='str'), rid_base=dict(required=False, type='int'), secondary_rid_base=dict(required=False, type='int'), @@ -223,10 +289,11 @@ def main(): _hostname_overridden=dict(required=False, type='bool', default=False), ), - supports_check_mode=True, + supports_check_mode=False, ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_set_ds_password.py b/roles/ipaserver/library/ipaserver_set_ds_password.py index f4d767be2d0a185c909d3e80d851d12704df69af..f339fbc48ffe1c918b6d56908d2af715b8b40bb7 100644 --- a/roles/ipaserver/library/ipaserver_set_ds_password.py +++ b/roles/ipaserver/library/ipaserver_set_ds_password.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,64 +39,86 @@ description: Set DS password options: dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: no + type: str + required: yes setup_ca: description: Configure a dogtag CA - required: no + type: bool + required: yes idstart: description: The starting value for the IDs range (default random) - required: no + type: int + required: yes idmax: description: The max value for the IDs range (default idstart+199999) - required: no + type: int + required: yes no_hbac_allow: description: Don't install allow_all HBAC rule - required: yes + type: bool + default: no + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no dirsrv_config_file: description: The path to LDIF file that will be used to modify configuration of dse.ldif during installation of the directory server instance - required: yes + type: str + required: no _dirsrv_pkcs12_info: description: The installer _dirsrv_pkcs12_info setting - required: yes + type: list + elements: str + required: no dirsrv_cert_files: description: Files containing the Directory Server SSL certificate and private key - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no domainlevel: description: The domain level - required: yes + type: int + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -107,6 +129,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( + check_imports, MAX_DOMAIN_LEVEL, AnsibleModuleLog, options, sysrestore, paths, api_Backend_ldap2, ds_init_info, redirect_stdout, setup_logging ) @@ -116,25 +139,28 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=True), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=True, type='str'), # server setup_ca=dict(required=True, type='bool'), idstart=dict(required=True, type='int'), idmax=dict(required=True, type='int'), no_hbac_allow=dict(required=False, type='bool', default=False), no_pkinit=dict(required=False, type='bool', default=False), - dirsrv_config_file=dict(required=False), - _dirsrv_pkcs12_info=dict(required=False, type='list'), + dirsrv_config_file=dict(required=False, type='str'), + _dirsrv_pkcs12_info=dict(required=False, type='list', + elements='str'), # ssl certificate - dirsrv_cert_files=dict(required=False, type='list', default=[]), - subject_base=dict(required=False), - ca_subject=dict(required=False), + dirsrv_cert_files=dict(required=False, type='list', elements='str', + default=[]), + subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), # certificate system - external_cert_files=dict(required=False, type='list', default=[]), + external_cert_files=dict(required=False, type='list', + elements='str', default=[]), # additional domainlevel=dict(required=False, type='int', default=MAX_DOMAIN_LEVEL), @@ -142,6 +168,7 @@ def main(): ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_adtrust.py b/roles/ipaserver/library/ipaserver_setup_adtrust.py index 428d25286e6b2f450b04ccfa7347a0a93ba87916..820748be96f6e68d78f39bb1d0e43283369a856e 100644 --- a/roles/ipaserver/library/ipaserver_setup_adtrust.py +++ b/roles/ipaserver/library/ipaserver_setup_adtrust.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,31 +39,42 @@ description: Setup trust ad options: hostname: description: Fully qualified name of this host - required: yes + type: str + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no enable_compat: description: Enable support for trusted domains for old clients - required: yes + type: bool + default: no + required: no rid_base: description: Start value for mapping UIDs and GIDs to RIDs - required: yes + type: int + required: no secondary_rid_base: description: Start value of the secondary range for mapping UIDs and GIDs to RIDs - required: yes + type: int + required: no adtrust_netbios_name: description: The adtrust netbios_name setting - required: no + type: str + required: yes adtrust_reset_netbios_name: description: The adtrust reset_netbios_name setting - required: no + type: bool + required: yes author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -74,7 +85,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, api_Backend_ldap2, redirect_stdout, adtrust, api ) @@ -83,7 +94,7 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - hostname=dict(required=False), + hostname=dict(required=False, type='str'), setup_ca=dict(required=False, type='bool', default=False), setup_adtrust=dict(required=False, type='bool', default=False), # ad trust @@ -91,12 +102,13 @@ def main(): rid_base=dict(required=False, type='int'), secondary_rid_base=dict(required=False, type='int'), # additional - adtrust_netbios_name=dict(required=True), + adtrust_netbios_name=dict(required=True, type='str'), adtrust_reset_netbios_name=dict(required=True, type='bool'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_ca.py b/roles/ipaserver/library/ipaserver_setup_ca.py index 8c01e3c9cffb2237fc920d7a1f198af2946792c5..815edca7d99a6fc76fc703e1f299bbe74a89ceaf 100644 --- a/roles/ipaserver/library/ipaserver_setup_ca.py +++ b/roles/ipaserver/library/ipaserver_setup_ca.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,119 +39,169 @@ description: Setup CA options: dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes master_password: description: kerberos master password (normally autogenerated) - required: no + type: str + required: yes ip_addresses: description: List of Master Server IP Addresses - required: yes + type: list + elements: str + required: no domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no no_host_dns: description: Do not use DNS for hostname lookup during installation - required: yes + type: bool + default: no + required: no pki_config_override: description: Path to ini file with config overrides - required: yes + type: str + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no setup_kra: description: Configure a dogtag KRA - required: yes + type: bool + default: no + required: no setup_dns: description: Configure bind with our zone - required: yes + type: bool + default: no + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no idstart: description: The starting value for the IDs range (default random) - required: no + type: int + required: yes idmax: description: The max value for the IDs range (default idstart+199999) - required: no + type: int + required: yes no_hbac_allow: description: Don't install allow_all HBAC rule - required: yes + type: bool + default: no + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no dirsrv_config_file: description: The path to LDIF file that will be used to modify configuration of dse.ldif during installation of the directory server instance - required: yes + type: str + required: no dirsrv_cert_files: description: Files containing the Directory Server SSL certificate and private key - required: yes + type: list + elements: str + required: no _dirsrv_pkcs12_info: description: The installer _dirsrv_pkcs12_info setting - required: yes + type: list + elements: str + required: no external_ca: description: External ca setting - required: yes + type: bool + default: no + required: no external_ca_type: description: Type of the external CA - required: yes + type: str + required: no external_ca_profile: description: Specify the certificate profile/template to use at the external CA - required: yes + type: str + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no _subject_base: description: The installer _subject_base setting - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no _ca_subject: description: The installer _ca_subject setting - required: yes + type: str + required: no ca_signing_algorithm: description: Signing algorithm of the IPA CA certificate - required: yes + type: str + required: no _random_serial_numbers: description: The installer _random_serial_numbers setting + type: bool required: yes reverse_zones: description: The reverse DNS zones to use - required: yes + type: list + elements: str + required: no no_reverse: description: Do not create new reverse DNS zone - required: yes + type: bool + default: no + required: no auto_forwarders: description: Use DNS forwarders configured in /etc/resolv.conf - required: yes + type: bool + default: no + required: no domainlevel: description: The domain level - required: yes + type: int + required: no _http_ca_cert: description: The installer _http_ca_cert setting - required: yes + type: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -164,7 +214,7 @@ import os from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, ansible_module_get_parsed_ip_addresses, api_Backend_ldap2, redirect_stdout, ca, installutils, ds_init_info, custodiainstance, write_cache, x509, decode_certificate @@ -175,15 +225,16 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - master_password=dict(required=True, no_log=True), - ip_addresses=dict(required=False, type='list', default=[]), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=False), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + master_password=dict(required=True, type='str', no_log=True), + ip_addresses=dict(required=False, type='list', elements='str', + default=[]), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), no_host_dns=dict(required=False, type='bool', default=False), - pki_config_override=dict(required=False), + pki_config_override=dict(required=False, type='str'), # server setup_adtrust=dict(required=False, type='bool', default=False), setup_kra=dict(required=False, type='bool', default=False), @@ -193,32 +244,36 @@ def main(): idmax=dict(required=True, type='int'), no_hbac_allow=dict(required=False, type='bool', default=False), no_pkinit=dict(required=False, type='bool', default=False), - dirsrv_config_file=dict(required=False), - dirsrv_cert_files=dict(required=False, type='list'), - _dirsrv_pkcs12_info=dict(required=False, type='list'), + dirsrv_config_file=dict(required=False, type='str'), + dirsrv_cert_files=dict(required=False, type='list', + elements='str'), + _dirsrv_pkcs12_info=dict(required=False, type='list', + elements='str'), # certificate system external_ca=dict(required=False, type='bool', default=False), - external_ca_type=dict(required=False), - external_ca_profile=dict(required=False), + external_ca_type=dict(required=False, type='str'), + external_ca_profile=dict(required=False, type='str'), external_cert_files=dict(required=False, type='list', - default=None), - subject_base=dict(required=False), - _subject_base=dict(required=False), - ca_subject=dict(required=False), - _ca_subject=dict(required=False), - ca_signing_algorithm=dict(required=False), + elements='str', default=None), + subject_base=dict(required=False, type='str'), + _subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), + _ca_subject=dict(required=False, type='str'), + ca_signing_algorithm=dict(required=False, type='str'), _random_serial_numbers=dict(required=True, type='bool'), # dns - reverse_zones=dict(required=False, type='list', default=[]), + reverse_zones=dict(required=False, type='list', elements='str', + default=[]), no_reverse=dict(required=False, type='bool', default=False), auto_forwarders=dict(required=False, type='bool', default=False), # additional domainlevel=dict(required=False, type='int'), - _http_ca_cert=dict(required=False), + _http_ca_cert=dict(required=False, type='str'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_custodia.py b/roles/ipaserver/library/ipaserver_setup_custodia.py index a788ad1268bbf58eb99f96cfe1bfe1527a30b0fe..be337c1d502e0c97074fdf9266a69dd061eb5b19 100644 --- a/roles/ipaserver/library/ipaserver_setup_custodia.py +++ b/roles/ipaserver/library/ipaserver_setup_custodia.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,15 +39,19 @@ description: Setup custodia options: realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -58,7 +62,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - setup_logging, AnsibleModuleLog, options, + check_imports, setup_logging, AnsibleModuleLog, options, api_Backend_ldap2, custodiainstance, redirect_stdout ) @@ -68,13 +72,14 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - realm=dict(required=True), - hostname=dict(required=False), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), setup_ca=dict(required=False, type='bool', default=False), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_dns.py b/roles/ipaserver/library/ipaserver_setup_dns.py index 1ed1fe4fe6655773f97ba3b0426e28d103b9d025..cf31eda93ae163544912ed84ae560017ba32c62e 100644 --- a/roles/ipaserver/library/ipaserver_setup_dns.py +++ b/roles/ipaserver/library/ipaserver_setup_dns.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,42 +39,61 @@ description: Setup DNS options: ip_addresses: description: List of Master Server IP Addresses - required: yes + type: list + elements: str + required: no domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: no + type: str + required: yes setup_dns: description: Configure bind with our zone - required: no + type: bool + required: yes setup_ca: description: Configure a dogtag CA - required: no + type: bool + required: yes zonemgr: description: DNS zone manager e-mail address. Defaults to hostmaster@DOMAIN - required: yes + type: str + required: no forwarders: description: Add DNS forwarders - required: no + type: list + elements: str + required: yes forward_policy: description: DNS forwarding policy for global forwarders - required: yes + type: str + choices: ['first', 'only'] + default: 'first' + required: no no_dnssec_validation: description: Disable DNSSEC validation - required: yes + type: bool + default: no + required: no dns_ip_addresses: description: The dns ip_addresses setting - required: no + type: list + elements: str + required: yes dns_reverse_zones: description: The dns reverse_zones setting - required: no + type: list + elements: str + required: yes author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -85,7 +104,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, paths, dns, + check_imports, AnsibleModuleLog, setup_logging, options, paths, dns, ansible_module_get_parsed_ip_addresses, sysrestore, api_Backend_ldap2, redirect_stdout, bindinstance ) @@ -95,26 +114,29 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - ip_addresses=dict(required=False, type='list', default=[]), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=True), + ip_addresses=dict(required=False, type='list', elements='str', + default=[]), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=True, type='str'), # server setup_dns=dict(required=True, type='bool'), setup_ca=dict(required=True, type='bool'), # dns - zonemgr=dict(required=False), - forwarders=dict(required=True, type='list'), - forward_policy=dict(default='first', choices=['first', 'only']), + zonemgr=dict(required=False, type='str'), + forwarders=dict(required=True, type='list', elements='str'), + forward_policy=dict(required=False, choices=['first', 'only'], + default='first'), no_dnssec_validation=dict(required=False, type='bool', default=False), # additional - dns_ip_addresses=dict(required=True, type='list'), - dns_reverse_zones=dict(required=True, type='list'), + dns_ip_addresses=dict(required=True, type='list', elements='str'), + dns_reverse_zones=dict(required=True, type='list', elements='str'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_ds.py b/roles/ipaserver/library/ipaserver_setup_ds.py index 76fb4b73c93c95ffedcb0272b9ff0622caec1ec3..4479daaaf8248e21112e2e8065a4dd71adb44ba1 100644 --- a/roles/ipaserver/library/ipaserver_setup_ds.py +++ b/roles/ipaserver/library/ipaserver_setup_ds.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,61 +39,83 @@ description: Configure directory server options: dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no idstart: description: The starting value for the IDs range (default random) - required: no + type: int + required: yes idmax: description: The max value for the IDs range (default idstart+199999) - required: no + type: int + required: yes no_hbac_allow: description: Don't install allow_all HBAC rule - required: yes + type: bool + default: no + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no dirsrv_config_file: description: The path to LDIF file that will be used to modify configuration of dse.ldif during installation of the directory server instance - required: yes + type: str + required: no dirsrv_cert_files: description: Files containing the Directory Server SSL certificate and private key - required: yes + type: list + elements: str + required: no _dirsrv_pkcs12_info: description: The installer _dirsrv_pkcs12_info setting - required: yes + type: list + elements: str + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -104,7 +126,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, api_Backend_ldap2, redirect_stdout, api, NUM_VERSION, tasks, dsinstance, ntpinstance, IPAAPI_USER ) @@ -114,24 +136,27 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=False), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), # server idstart=dict(required=True, type='int'), idmax=dict(required=True, type='int'), no_hbac_allow=dict(required=False, type='bool', default=False), no_pkinit=dict(required=False, type='bool', default=False), - dirsrv_config_file=dict(required=False), + dirsrv_config_file=dict(required=False, type='str'), # ssl certificate - dirsrv_cert_files=dict(required=False, type='list', default=[]), - _dirsrv_pkcs12_info=dict(required=False, type='list'), + dirsrv_cert_files=dict(required=False, type='list', elements='str', + default=[]), + _dirsrv_pkcs12_info=dict(required=False, type='list', + elements='str'), # certificate system - external_cert_files=dict(required=False, type='list', default=[]), - subject_base=dict(required=False), - ca_subject=dict(required=False), + external_cert_files=dict(required=False, type='list', + elements='str', default=[]), + subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), # additional setup_ca=dict(required=False, type='bool', default=False), @@ -139,6 +164,7 @@ def main(): ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_http.py b/roles/ipaserver/library/ipaserver_setup_http.py index 5f72b1cbe49a2d05e0a67f5621ae76c4e0464b58..cd6478eeb8d951f8aa2568cf563ca3659e022118 100644 --- a/roles/ipaserver/library/ipaserver_setup_http.py +++ b/roles/ipaserver/library/ipaserver_setup_http.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,107 +39,155 @@ description: Setup HTTP options: dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes master_password: description: kerberos master password (normally autogenerated) - required: no + type: str + required: yes domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no ip_addresses: description: List of Master Server IP Addresses - required: yes + type: list + elements: str + required: no reverse_zones: description: The reverse DNS zones to use - required: yes + type: list + elements: str + required: no http_cert_files: description: File containing the Apache Server SSL certificate and private key - required: yes + type: list + elements: str + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no setup_kra: description: Configure a dogtag KRA - required: yes + type: bool + default: no + required: no setup_dns: description: Configure bind with our zone - required: yes + type: bool + default: no + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no no_host_dns: description: Do not use DNS for hostname lookup during installation - required: yes + type: bool + default: no + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no no_hbac_allow: description: Don't install allow_all HBAC rule - required: yes + type: bool + default: no + required: no no_ui_redirect: description: Do not automatically redirect to the Web UI - required: yes + type: bool + default: no + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no _subject_base: description: The installer _subject_base setting - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no _ca_subject: description: The installer _ca_subject setting - required: yes + type: str + required: no idstart: description: The starting value for the IDs range (default random) - required: no + type: int + required: yes idmax: description: The max value for the IDs range (default idstart+199999) - required: no + type: int + required: yes domainlevel: description: The domain level - required: yes + type: int + required: no dirsrv_config_file: description: The path to LDIF file that will be used to modify configuration of dse.ldif during installation of the directory server instance - required: yes + type: str + required: no dirsrv_cert_files: description: Files containing the Directory Server SSL certificate and private key - required: yes + type: list + elements: str + required: no no_reverse: description: Do not create new reverse DNS zone - required: yes + type: bool + default: no + required: no auto_forwarders: description: Use DNS forwarders configured in /etc/resolv.conf - required: yes + type: bool + default: no + required: no _dirsrv_pkcs12_info: description: The installer _dirsrv_pkcs12_info setting - required: yes + type: list + elements: str + required: no _http_pkcs12_info: description: The installer _http_pkcs12_info setting - required: yes + type: list + elements: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -150,7 +198,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, ansible_module_get_parsed_ip_addresses, api_Backend_ldap2, redirect_stdout, ds_init_info, krbinstance, httpinstance, ca, service, tasks @@ -161,16 +209,19 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - master_password=dict(required=True, no_log=True), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=False), - - ip_addresses=dict(required=False, type='list', default=[]), - reverse_zones=dict(required=False, type='list', default=[]), - http_cert_files=dict(required=False, type='list', default=[]), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + master_password=dict(required=True, type='str', no_log=True), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), + + ip_addresses=dict(required=False, type='list', elements='str', + default=[]), + reverse_zones=dict(required=False, type='list', elements='str', + default=[]), + http_cert_files=dict(required=False, type='list', elements='str', + default=[]), setup_adtrust=dict(required=False, type='bool', default=False), setup_kra=dict(required=False, type='bool', default=False), @@ -183,29 +234,34 @@ def main(): no_ui_redirect=dict(required=False, type='bool', default=False), - external_cert_files=dict(required=False, type='list', default=[]), - subject_base=dict(required=False), - _subject_base=dict(required=False), - ca_subject=dict(required=False), - _ca_subject=dict(required=False), + external_cert_files=dict(required=False, type='list', + elements='str', default=[]), + subject_base=dict(required=False, type='str'), + _subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), + _ca_subject=dict(required=False, type='str'), idstart=dict(required=True, type='int'), idmax=dict(required=True, type='int'), domainlevel=dict(required=False, type='int'), dirsrv_config_file=dict(required=False), - dirsrv_cert_files=dict(required=False, type='list', default=[]), + dirsrv_cert_files=dict(required=False, type='list', elements='str', + default=[]), no_reverse=dict(required=False, type='bool', default=False), auto_forwarders=dict(required=False, type='bool', default=False), # _update_hosts_file=dict(required=False, type='bool', # default=False), - _dirsrv_pkcs12_info=dict(required=False, type='list'), - _http_pkcs12_info=dict(required=False, type='list'), + _dirsrv_pkcs12_info=dict(required=False, type='list', + elements='str'), + _http_pkcs12_info=dict(required=False, type='list', + elements='str'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_kra.py b/roles/ipaserver/library/ipaserver_setup_kra.py index 78f1fe26de6cfbc8dc577980edfe44442bb99b95..9f05ef5a1da40f3a99c154cc60c8e36e09bdcf3a 100644 --- a/roles/ipaserver/library/ipaserver_setup_kra.py +++ b/roles/ipaserver/library/ipaserver_setup_kra.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,24 +39,30 @@ description: Setup KRA options: dm_password: description: Directory Manager password - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: no + type: str + required: yes setup_ca: description: Configure a dogtag CA - required: no + type: bool + required: yes setup_kra: description: Configure a dogtag KRA - required: no + type: bool + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes pki_config_override: description: Path to ini file with config overrides - required: yes + type: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -67,7 +73,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, + check_imports, AnsibleModuleLog, setup_logging, options, api_Backend_ldap2, redirect_stdout, api, custodiainstance, kra ) @@ -76,16 +82,17 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - hostname=dict(required=True), + dm_password=dict(required=True, type='str', no_log=True), + hostname=dict(required=True, type='str'), setup_ca=dict(required=True, type='bool'), setup_kra=dict(required=True, type='bool'), - realm=dict(required=True), - pki_config_override=dict(required=False), + realm=dict(required=True, type='str'), + pki_config_override=dict(required=False, type='str'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_krb.py b/roles/ipaserver/library/ipaserver_setup_krb.py index 70daab2528728a0aba279ad1dfac2e9b44ba5636..df37ed31a50f9845482a9d68dff808148b8761ff 100644 --- a/roles/ipaserver/library/ipaserver_setup_krb.py +++ b/roles/ipaserver/library/ipaserver_setup_krb.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,79 +39,115 @@ description: Setup KRB options: dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes master_password: description: kerberos master password (normally autogenerated) - required: no + type: str + required: yes domain: description: Primary DNS domain of the IPA deployment - required: no + type: str + required: yes realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no ip_addresses: description: List of Master Server IP Addresses - required: yes + type: list + elements: str + required: no reverse_zones: description: The reverse DNS zones to use - required: yes + type: list + elements: str + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no setup_kra: description: Configure a dogtag KRA - required: yes + type: bool + default: no + required: no setup_dns: description: Configure bind with our zone - required: yes + type: bool + default: no + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no no_host_dns: description: Do not use DNS for hostname lookup during installation - required: yes + type: bool + default: no + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no no_hbac_allow: description: Don't install allow_all HBAC rule - required: yes + type: bool + default: no + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no idstart: description: The starting value for the IDs range (default random) - required: no + type: int + required: yes idmax: description: The max value for the IDs range (default idstart+199999) - required: no + type: int + required: yes no_reverse: description: Do not create new reverse DNS zone - required: yes + type: bool + default: no + required: no auto_forwarders: description: Use DNS forwarders configured in /etc/resolv.conf - required: yes + type: bool + default: no + required: no _pkinit_pkcs12_info: description: The installer _pkinit_pkcs12_info setting - required: yes + type: list + elements: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -122,7 +158,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, ansible_module_get_parsed_ip_addresses, api_Backend_ldap2, redirect_stdout, krbinstance ) @@ -132,15 +168,17 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - master_password=dict(required=True, no_log=True), - domain=dict(required=True), - realm=dict(required=True), - hostname=dict(required=False), - - ip_addresses=dict(required=False, type='list', default=[]), - reverse_zones=dict(required=False, type='list', default=[]), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + master_password=dict(required=True, type='str', no_log=True), + domain=dict(required=True, type='str'), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), + + ip_addresses=dict(required=False, type='list', elements='str', + default=[]), + reverse_zones=dict(required=False, type='list', elements='str', + default=[]), setup_adtrust=dict(required=False, type='bool', default=False), setup_kra=dict(required=False, type='bool', default=False), @@ -151,9 +189,10 @@ def main(): no_pkinit=dict(required=False, type='bool', default=False), no_hbac_allow=dict(required=False, type='bool', default=False), - external_cert_files=dict(required=False, type='list', default=[]), - subject_base=dict(required=False), - ca_subject=dict(required=False), + external_cert_files=dict(required=False, type='list', + elements='str', default=[]), + subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), idstart=dict(required=True, type='int'), idmax=dict(required=True, type='int'), @@ -161,11 +200,13 @@ def main(): no_reverse=dict(required=False, type='bool', default=False), auto_forwarders=dict(required=False, type='bool', default=False), - _pkinit_pkcs12_info=dict(required=False, type='list'), + _pkinit_pkcs12_info=dict(required=False, type='list', + elements='str'), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_ntp.py b/roles/ipaserver/library/ipaserver_setup_ntp.py index 9efad2137ebf509102f83a7b98f9ee773b9695c9..eac722b5da03d923c6412e1e1589bcb63f3bb9a6 100644 --- a/roles/ipaserver/library/ipaserver_setup_ntp.py +++ b/roles/ipaserver/library/ipaserver_setup_ntp.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,12 +39,15 @@ description: Setup NTP options: ntp_servers: description: ntp servers to use - required: yes + type: list + elements: str + required: no ntp_pool: description: ntp server pool to use - required: yes + type: str + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -55,7 +58,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, sysrestore, paths, + check_imports, AnsibleModuleLog, setup_logging, options, sysrestore, paths, redirect_stdout, time_service, sync_time, ntpinstance, timeconf, getargspec ) @@ -64,12 +67,14 @@ from ansible.module_utils.ansible_ipa_server import ( def main(): ansible_module = AnsibleModule( argument_spec=dict( - ntp_servers=dict(required=False, type='list', default=None), - ntp_pool=dict(required=False, default=None), + ntp_servers=dict(required=False, type='list', elements='str', + default=None), + ntp_pool=dict(required=False, type='str', default=None), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_setup_otpd.py b/roles/ipaserver/library/ipaserver_setup_otpd.py index ca1e06c4671362d57f9a7aa40247387a09a2b9b0..f89681184a8817b3db234040be62406ad91d95dc 100644 --- a/roles/ipaserver/library/ipaserver_setup_otpd.py +++ b/roles/ipaserver/library/ipaserver_setup_otpd.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,15 +39,19 @@ description: Setup OTPD options: realm: description: Kerberos realm name of the IPA deployment - required: no + type: str + required: yes hostname: description: Fully qualified name of this host - required: yes + type: str + required: no setup_ca: description: Configure a dogtag CA - required: yes + type: bool + default: no + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -58,7 +62,7 @@ RETURN = ''' from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.ansible_ipa_server import ( - AnsibleModuleLog, setup_logging, options, + check_imports, AnsibleModuleLog, setup_logging, options, api_Backend_ldap2, redirect_stdout, otpdinstance, ipautil ) @@ -67,13 +71,14 @@ def main(): ansible_module = AnsibleModule( argument_spec=dict( # basic - realm=dict(required=True), - hostname=dict(required=False), + realm=dict(required=True, type='str'), + hostname=dict(required=False, type='str'), setup_ca=dict(required=False, type='bool', default=False), ), ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/library/ipaserver_test.py b/roles/ipaserver/library/ipaserver_test.py index f830f37d8a3660815c1a3bc805c7bab23cffaab4..cf5b7c8f0f7f3eb3ee56bda383ae162ef41cefd2 100644 --- a/roles/ipaserver/library/ipaserver_test.py +++ b/roles/ipaserver/library/ipaserver_test.py @@ -5,7 +5,7 @@ # # Based on ipa-client-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -39,169 +39,246 @@ description: IPA server test options: force: description: Installer force parameter - required: yes + type: bool + default: no + required: no dm_password: description: Directory Manager password - required: no + type: str + required: yes password: description: Admin user kerberos password - required: no + type: str + required: yes master_password: description: kerberos master password (normally autogenerated) - required: yes + type: str + required: no domain: description: Primary DNS domain of the IPA deployment - required: yes + type: str + required: no realm: description: Kerberos realm name of the IPA deployment - required: yes + type: str + required: no hostname: description: Fully qualified name of this host - required: yes + type: str + required: no ca_cert_files: description: List of files containing CA certificates for the service certificate files - required: yes + type: list + elements: str + required: no no_host_dns: description: Do not use DNS for hostname lookup during installation - required: yes + type: bool + default: no + required: no pki_config_override: description: Path to ini file with config overrides - required: yes + type: str + required: no skip_mem_check: description: Skip checking for minimum required memory - required: yes + type: bool + default: no + required: no setup_adtrust: description: Configure AD trust capability - required: yes + type: bool + default: no + required: no setup_kra: description: Configure a dogtag KRA - required: yes + type: bool + default: no + required: no setup_dns: description: Configure bind with our zone - required: yes + type: bool + default: no + required: no idstart: description: The starting value for the IDs range (default random) - required: yes + type: int + required: no idmax: description: The max value for the IDs range (default idstart+199999) - required: yes + type: int + required: no no_pkinit: description: Disable pkinit setup steps - required: yes + type: bool + default: no + required: no dirsrv_config_file: description: The path to LDIF file that will be used to modify configuration of dse.ldif during installation of the directory server instance - required: yes + type: str + required: no dirsrv_cert_files: description: Files containing the Directory Server SSL certificate and private key - required: yes + type: list + elements: str + required: no http_cert_files: description: File containing the Apache Server SSL certificate and private key - required: yes + type: list + elements: str + required: no pkinit_cert_files: description: File containing the Kerberos KDC SSL certificate and private key - required: yes + type: list + elements: str + required: no dirsrv_pin: description: The password to unlock the Directory Server private key - required: yes + type: str + required: no http_pin: description: The password to unlock the Apache Server private key - required: yes + type: str + required: no pkinit_pin: description: The password to unlock the Kerberos KDC private key - required: yes + type: str + required: no dirsrv_cert_name: description: Name of the Directory Server SSL certificate to install - required: yes + type: str + required: no http_cert_name: description: Name of the Apache Server SSL certificate to install - required: yes + type: str + required: no pkinit_cert_name: description: Name of the Kerberos KDC SSL certificate to install - required: yes + type: str + required: no ntp_servers: description: ntp servers to use - required: yes + type: list + elements: str + required: no ntp_pool: description: ntp server pool to use - required: yes + type: str + required: no no_ntp: description: Do not configure ntp - required: yes + type: bool + default: no + required: no external_ca: description: External ca setting - required: yes + type: bool + default: no + required: no external_ca_type: description: Type of the external CA - required: yes + type: str + required: no external_ca_profile: description: Specify the certificate profile/template to use at the external CA - required: yes + type: str + required: no external_cert_files: description: File containing the IPA CA certificate and the external CA certificate chain - required: yes + type: list + elements: str + required: no subject_base: description: The certificate subject base (default O=<realm-name>). RDNs are in LDAP order (most specific RDN first). - required: yes + type: str + required: no ca_subject: description: The installer ca_subject setting - required: yes + type: str + required: no allow_zone_overlap: description: Create DNS zone even if it already exists - required: yes + type: bool + default: no + required: no reverse_zones: description: The reverse DNS zones to use - required: yes + type: list + elements: str + required: no no_reverse: description: Do not create new reverse DNS zone - required: yes + type: bool + default: no + required: no auto_reverse: description: Create necessary reverse zones - required: yes + type: bool + default: no + required: no zonemgr: description: DNS zone manager e-mail address. Defaults to hostmaster@DOMAIN - required: yes + type: str + required: no forwarders: description: Add DNS forwarders - required: yes + type: list + elements: str + required: no no_forwarders: description: Do not add any DNS forwarders, use root servers instead - required: yes + type: bool + default: no + required: no auto_forwarders: description: Use DNS forwarders configured in /etc/resolv.conf - required: yes + type: bool + default: no + required: no forward_policy: description: DNS forwarding policy for global forwarders - required: yes + type: str + choices: ['first', 'only'] + required: no no_dnssec_validation: description: Disable DNSSEC validation - required: yes + type: bool + default: no + required: no enable_compat: description: Enable support for trusted domains for old clients - required: yes + type: bool + default: no + required: no netbios_name: description: NetBIOS name of the IPA domain - required: yes + type: str + required: no rid_base: description: Start value for mapping UIDs and GIDs to RIDs - required: yes + type: int + default: 1000 + required: no secondary_rid_base: description: Start value of the secondary range for mapping UIDs and GIDs to RIDs - required: yes + type: int + default: 100000000 + required: no author: - - Thomas Woerner + - Thomas Woerner (@t-woerner) ''' EXAMPLES = ''' @@ -218,6 +295,7 @@ from shutil import copyfile from ansible.module_utils.basic import AnsibleModule from ansible.module_utils._text import to_native from ansible.module_utils.ansible_ipa_server import ( + check_imports, AnsibleModuleLog, setup_logging, options, adtrust_imported, kra_imported, PKIIniLoader, MIN_DOMAIN_LEVEL, MAX_DOMAIN_LEVEL, check_zone_overlap, redirect_stdout, validate_dm_password, validate_admin_password, @@ -239,15 +317,16 @@ def main(): argument_spec=dict( # basic force=dict(required=False, type='bool', default=False), - dm_password=dict(required=True, no_log=True), - password=dict(required=True, no_log=True), - master_password=dict(required=False, no_log=True), - domain=dict(required=False), - realm=dict(required=False), - hostname=dict(required=False), - ca_cert_files=dict(required=False, type='list', default=[]), + dm_password=dict(required=True, type='str', no_log=True), + password=dict(required=True, type='str', no_log=True), + master_password=dict(required=False, type='str', no_log=True), + domain=dict(required=False, type='str'), + realm=dict(required=False, type='str'), + hostname=dict(required=False, type='str'), + ca_cert_files=dict(required=False, type='list', elements='str', + default=[]), no_host_dns=dict(required=False, type='bool', default=False), - pki_config_override=dict(required=False), + pki_config_override=dict(required=False, type='str'), skip_mem_check=dict(required=False, type='bool', default=False), # server setup_adtrust=dict(required=False, type='bool', default=False), @@ -258,21 +337,25 @@ def main(): # no_hbac_allow no_pkinit=dict(required=False, type='bool', default=False), # no_ui_redirect - dirsrv_config_file=dict(required=False), + dirsrv_config_file=dict(required=False, type='str'), # ssl certificate - dirsrv_cert_files=dict(required=False, type='list', default=None), - http_cert_files=dict(required=False, type='list', default=None), - pkinit_cert_files=dict(required=False, type='list', default=None), - dirsrv_pin=dict(required=False), - http_pin=dict(required=False), - pkinit_pin=dict(required=False), - dirsrv_cert_name=dict(required=False), - http_cert_name=dict(required=False), - pkinit_cert_name=dict(required=False), + dirsrv_cert_files=dict(required=False, type='list', elements='str', + default=None), + http_cert_files=dict(required=False, type='list', elements='str', + default=None), + pkinit_cert_files=dict(required=False, type='list', elements='str', + default=None), + dirsrv_pin=dict(required=False, type='str'), + http_pin=dict(required=False, type='str'), + pkinit_pin=dict(required=False, type='str'), + dirsrv_cert_name=dict(required=False, type='str'), + http_cert_name=dict(required=False, type='str'), + pkinit_cert_name=dict(required=False, type='str'), # client # mkhomedir - ntp_servers=dict(required=False, type='list', default=None), - ntp_pool=dict(required=False, default=None), + ntp_servers=dict(required=False, type='list', elements='str', + default=None), + ntp_pool=dict(required=False, type='str', default=None), no_ntp=dict(required=False, type='bool', default=False), # ssh_trust_dns # no_ssh @@ -280,38 +363,42 @@ def main(): # no_dns_sshfp # certificate system external_ca=dict(required=False, type='bool', default=False), - external_ca_type=dict(required=False), - external_ca_profile=dict(required=False), + external_ca_type=dict(required=False, type='str'), + external_ca_profile=dict(required=False, type='str'), external_cert_files=dict(required=False, type='list', - default=None), - subject_base=dict(required=False), - ca_subject=dict(required=False), + elements='str', default=None), + subject_base=dict(required=False, type='str'), + ca_subject=dict(required=False, type='str'), # ca_signing_algorithm # dns allow_zone_overlap=dict(required=False, type='bool', default=False), - reverse_zones=dict(required=False, type='list', default=[]), + reverse_zones=dict(required=False, type='list', elements='str', + default=[]), no_reverse=dict(required=False, type='bool', default=False), auto_reverse=dict(required=False, type='bool', default=False), - zonemgr=dict(required=False), - forwarders=dict(required=False, type='list', default=[]), + zonemgr=dict(required=False, type='str'), + forwarders=dict(required=False, type='list', elements='str', + default=[]), no_forwarders=dict(required=False, type='bool', default=False), auto_forwarders=dict(required=False, type='bool', default=False), - forward_policy=dict(default=None, choices=['first', 'only']), + forward_policy=dict(required=False, type='str', + choices=['first', 'only'], default=None), no_dnssec_validation=dict(required=False, type='bool', default=False), # ad trust enable_compat=dict(required=False, type='bool', default=False), - netbios_name=dict(required=False), + netbios_name=dict(required=False, type='str'), rid_base=dict(required=False, type='int', default=1000), secondary_rid_base=dict(required=False, type='int', default=100000000), # additional ), - supports_check_mode=True, + supports_check_mode=False, ) ansible_module._ansible_debug = True + check_imports(ansible_module) setup_logging() ansible_log = AnsibleModuleLog(ansible_module) diff --git a/roles/ipaserver/module_utils/ansible_ipa_server.py b/roles/ipaserver/module_utils/ansible_ipa_server.py index f1f4972b690b3fb44fd2f07a622a031088762916..6dec4bc210b1a2497f3c5accefae6cf3210d477e 100644 --- a/roles/ipaserver/module_utils/ansible_ipa_server.py +++ b/roles/ipaserver/module_utils/ansible_ipa_server.py @@ -3,9 +3,9 @@ # Authors: # Thomas Woerner <twoerner@redhat.com> # -# Based on ipa-client-install code +# Based on ipa-server-install code # -# Copyright (C) 2017 Red Hat +# Copyright (C) 2017-2022 Red Hat # see file 'COPYING' for use and warranty information # # This program is free software; you can redistribute it and/or modify @@ -23,12 +23,12 @@ from __future__ import (absolute_import, division, print_function) -__metaclass__ = type +__metaclass__ = type # pylint: disable=invalid-name __all__ = ["IPAChangeConf", "certmonger", "sysrestore", "root_logger", "ipa_generate_password", "run", "ScriptError", "services", "tasks", "errors", "x509", "DOMAIN_LEVEL_0", "MIN_DOMAIN_LEVEL", - "validate_domain_name", + "MAX_DOMAIN_LEVEL", "validate_domain_name", "no_matching_interface_for_ip_address_warning", "check_zone_overlap", "timeconf", "ntpinstance", "adtrust", "bindinstance", "ca", "dns", "httpinstance", "installutils", @@ -41,45 +41,42 @@ __all__ = ["IPAChangeConf", "certmonger", "sysrestore", "root_logger", "adtrustinstance", "IPAAPI_USER", "sync_time", "PKIIniLoader", "default_subject_base", "default_ca_subject_dn", "check_ldap_conf", "encode_certificate", "decode_certificate", - "check_available_memory", "getargspec", "get_min_idstart"] + "check_available_memory", "getargspec", "get_min_idstart", + "paths", "api", "ipautil", "adtrust_imported", "NUM_VERSION", + "time_service", "kra_imported", "dsinstance", "IPA_PYTHON_VERSION", + "NUM_VERSION"] import sys - -# HACK: workaround for Ansible 2.9 -# https://github.com/ansible/ansible/issues/68361 -if 'ansible.executor' in sys.modules: - for attr in __all__: - setattr(sys.modules[__name__], attr, None) - -else: - - import logging +import logging + +# Import getargspec from inspect or provide own getargspec for +# Python 2 compatibility with Python 3.11+. +try: + from inspect import getargspec +except ImportError: + from collections import namedtuple + from inspect import getfullargspec + + # The code is copied from Python 3.10 inspect.py + # Authors: Ka-Ping Yee <ping@lfw.org> + # Yury Selivanov <yselivanov@sprymix.com> + ArgSpec = namedtuple('ArgSpec', 'args varargs keywords defaults') + + def getargspec(func): + args, varargs, varkw, defaults, kwonlyargs, _kwonlydefaults, \ + ann = getfullargspec(func) + if kwonlyargs or ann: + raise ValueError( + "Function has keyword-only parameters or annotations" + ", use inspect.signature() API which can support them") + return ArgSpec(args, varargs, varkw, defaults) + + +try: from contextlib import contextmanager as contextlib_contextmanager from ansible.module_utils import six import base64 - # Import getargspec from inspect or provide own getargspec for - # Python 2 compatibility with Python 3.11+. - try: - from inspect import getargspec - except ImportError: - from collections import namedtuple - from inspect import getfullargspec - - # The code is copied from Python 3.10 inspect.py - # Authors: Ka-Ping Yee <ping@lfw.org> - # Yury Selivanov <yselivanov@sprymix.com> - ArgSpec = namedtuple('ArgSpec', 'args varargs keywords defaults') - - def getargspec(func): - args, varargs, varkw, defaults, kwonlyargs, _kwonlydefaults, \ - ann = getfullargspec(func) - if kwonlyargs or ann: - raise ValueError( - "Function has keyword-only parameters or annotations" - ", use inspect.signature() API which can support them") - return ArgSpec(args, varargs, varkw, defaults) - from ipapython.version import NUM_VERSION, VERSION if NUM_VERSION < 30201: @@ -211,223 +208,249 @@ else: raise Exception("freeipa version '%s' is too old" % VERSION) - logger = logging.getLogger("ipa-server-install") +except ImportError as _err: + ANSIBLE_IPA_SERVER_MODULE_IMPORT_ERROR = str(_err) - def setup_logging(): - # logger.setLevel(logging.DEBUG) - standard_logging_setup( - paths.IPASERVER_INSTALL_LOG, verbose=False, debug=False, - filemode='a', console_format='%(message)s') + for attr in __all__: + setattr(sys.modules[__name__], attr, None) +else: + ANSIBLE_IPA_SERVER_MODULE_IMPORT_ERROR = None - @contextlib_contextmanager - def redirect_stdout(stream): - sys.stdout = stream - try: - yield stream - finally: - sys.stdout = sys.__stdout__ - - class AnsibleModuleLog(): - def __init__(self, module): - self.module = module - _ansible_module_log = self - - class AnsibleLoggingHandler(logging.Handler): - def emit(self, record): - _ansible_module_log.write(self.format(record)) - - self.logging_handler = AnsibleLoggingHandler() - logger.setLevel(logging.DEBUG) - logger.root.addHandler(self.logging_handler) - - def close(self): - self.flush() - - def flush(self): - pass - - def log(self, msg): - # self.write(msg+"\n") - self.write(msg) - - def debug(self, msg): - self.module.debug(msg) - - def info(self, msg): - self.module.debug(msg) - - @staticmethod - def isatty(): - return False - - def write(self, msg): - self.module.debug(msg) - # self.module.warn(msg) - - # pylint: disable=too-few-public-methods, useless-object-inheritance - # pylint: disable=too-many-instance-attributes - class options_obj(object): # pylint: disable=invalid-name - def __init__(self): - self._replica_install = False - self.dnssec_master = False # future unknown - self.disable_dnssec_master = False # future unknown - self.domainlevel = MAX_DOMAIN_LEVEL # deprecated - self.domain_level = self.domainlevel # deprecated - self.interactive = False - self.unattended = not self.interactive - - # def __getattribute__(self, attr): - # logger.info(" <-- Accessing options.%s" % attr) - # return super(options_obj, self).__getattribute__(attr) - - # def __getattr__(self, attr): - # logger.info(" --> Adding missing options.%s" % attr) - # setattr(self, attr, None) - # return getattr(self, attr) - - def knobs(self): - for name in self.__dict__: - yield self, name - - # pylint: enable=too-few-public-methods, useless-object-inheritance - - # pylint: enable=too-many-instance-attributes - options = options_obj() - installer = options - - # pylint: disable=attribute-defined-outside-init - - # ServerMasterInstall - options.add_sids = True - options.add_agents = False - - # Installable - options.uninstalling = False - - # ServerInstallInterface - options.description = "Server" - - options.kinit_attempts = 1 - options.fixed_primary = True - options.permit = False - options.enable_dns_updates = False - options.no_krb5_offline_passwords = False - options.preserve_sssd = False - options.no_sssd = False - - # ServerMasterInstall - options.force_join = False - options.servers = None - options.no_wait_for_dns = True - options.host_password = None - options.keytab = None - options.setup_ca = True - # always run sidgen task and do not allow adding agents on first master - options.add_sids = True - options.add_agents = False - - # ADTrustInstallInterface - # no_msdcs is deprecated - options.no_msdcs = False - - # For pylint - options.external_cert_files = None - options.dirsrv_cert_files = None - - # Uninstall - options.ignore_topology_disconnect = False - options.ignore_last_of_role = False - - # pylint: enable=attribute-defined-outside-init - - # pylint: disable=invalid-name - def api_Backend_ldap2(host_name, setup_ca, connect=False): - # we are sure we have the configuration file ready. - cfg = dict(context='installer', confdir=paths.ETC_IPA, in_server=True, - host=host_name) - if setup_ca: - # we have an IPA-integrated CA - cfg['ca_host'] = host_name - - api.bootstrap(**cfg) - api.finalize() - if connect: - api.Backend.ldap2.connect() - - # pylint: enable=invalid-name - - def ds_init_info(ansible_log, fstore, domainlevel, dirsrv_config_file, - realm_name, host_name, domain_name, dm_password, - idstart, idmax, subject_base, ca_subject, - _no_hbac_allow, dirsrv_pkcs12_info, no_pkinit): - - if not options.external_cert_files: - _ds = dsinstance.DsInstance(fstore=fstore, domainlevel=domainlevel, - config_ldif=dirsrv_config_file) - _ds.set_output(ansible_log) - - if options.dirsrv_cert_files: - _dirsrv_pkcs12_info = dirsrv_pkcs12_info - else: - _dirsrv_pkcs12_info = None - - with redirect_stdout(ansible_log): - _ds.init_info(realm_name, host_name, domain_name, dm_password, - subject_base, ca_subject, idstart, idmax, - # hbac_allow=not no_hbac_allow, - _dirsrv_pkcs12_info, setup_pkinit=not no_pkinit) - else: - _ds = dsinstance.DsInstance(fstore=fstore, domainlevel=domainlevel) - _ds.set_output(ansible_log) - with redirect_stdout(ansible_log): - _ds.init_info(realm_name, host_name, domain_name, dm_password, - subject_base, ca_subject, 1101, 1100, None, - setup_pkinit=not no_pkinit) +logger = logging.getLogger("ipa-server-install") - return _ds - def ansible_module_get_parsed_ip_addresses(ansible_module, - param='ip_addresses'): - ip_addrs = [] - for _ip in ansible_module.params.get(param): - try: - ip_parsed = ipautil.CheckedIPAddress(_ip) - except Exception as err: - ansible_module.fail_json( - msg="Invalid IP Address %s: %s" % (_ip, err)) - ip_addrs.append(ip_parsed) - return ip_addrs - - def encode_certificate(cert): - """ - Encode a certificate using base64. - - It also takes FreeIPA and Python versions into account. - """ - if isinstance(cert, (str, bytes)): - encoded = base64.b64encode(cert) - else: - encoded = base64.b64encode(cert.public_bytes(Encoding.DER)) - if not six.PY2: - encoded = encoded.decode('ascii') - return encoded - - def decode_certificate(cert): - """ - Decode a certificate using base64. - - It also takes FreeIPA versions into account and returns a - IPACertificate for newer IPA versions. - """ - if hasattr(x509, "IPACertificate"): - cert = cert.strip() - if not cert.startswith("-----BEGIN CERTIFICATE-----"): - cert = "-----BEGIN CERTIFICATE-----\n" + cert - if not cert.endswith("-----END CERTIFICATE-----"): - cert += "\n-----END CERTIFICATE-----" - - cert = certificate_loader(cert.encode('utf-8')) +def setup_logging(): + # logger.setLevel(logging.DEBUG) + standard_logging_setup( + paths.IPASERVER_INSTALL_LOG, verbose=False, debug=False, + filemode='a', console_format='%(message)s') + + +@contextlib_contextmanager +def redirect_stdout(stream): + sys.stdout = stream + try: + yield stream + finally: + sys.stdout = sys.__stdout__ + + +class AnsibleModuleLog(): + def __init__(self, module): + self.module = module + _ansible_module_log = self + + class AnsibleLoggingHandler(logging.Handler): + def emit(self, record): + _ansible_module_log.write(self.format(record)) + + self.logging_handler = AnsibleLoggingHandler() + logger.setLevel(logging.DEBUG) + logger.root.addHandler(self.logging_handler) + + def close(self): + self.flush() + + def flush(self): + pass + + def log(self, msg): + # self.write(msg+"\n") + self.write(msg) + + def debug(self, msg): + self.module.debug(msg) + + def info(self, msg): + self.module.debug(msg) + + @staticmethod + def isatty(): + return False + + def write(self, msg): + self.module.debug(msg) + # self.module.warn(msg) + + +# pylint: disable=too-few-public-methods, useless-object-inheritance +# pylint: disable=too-many-instance-attributes +class options_obj(object): # pylint: disable=invalid-name + def __init__(self): + self._replica_install = False + self.dnssec_master = False # future unknown + self.disable_dnssec_master = False # future unknown + self.domainlevel = MAX_DOMAIN_LEVEL # deprecated + self.domain_level = self.domainlevel # deprecated + self.interactive = False + self.unattended = not self.interactive + + # def __getattribute__(self, attr): + # logger.info(" <-- Accessing options.%s" % attr) + # return super(options_obj, self).__getattribute__(attr) + + # def __getattr__(self, attr): + # logger.info(" --> Adding missing options.%s" % attr) + # setattr(self, attr, None) + # return getattr(self, attr) + + def knobs(self): + for name in self.__dict__: + yield self, name + + +# pylint: enable=too-few-public-methods, useless-object-inheritance + + +# pylint: enable=too-many-instance-attributes +options = options_obj() +installer = options + +# pylint: disable=attribute-defined-outside-init + +# ServerMasterInstall +options.add_sids = True +options.add_agents = False + +# Installable +options.uninstalling = False + +# ServerInstallInterface +options.description = "Server" + +options.kinit_attempts = 1 +options.fixed_primary = True +options.permit = False +options.enable_dns_updates = False +options.no_krb5_offline_passwords = False +options.preserve_sssd = False +options.no_sssd = False + +# ServerMasterInstall +options.force_join = False +options.servers = None +options.no_wait_for_dns = True +options.host_password = None +options.keytab = None +options.setup_ca = True +# always run sidgen task and do not allow adding agents on first master +options.add_sids = True +options.add_agents = False + +# ADTrustInstallInterface +# no_msdcs is deprecated +options.no_msdcs = False + +# For pylint +options.external_cert_files = None +options.dirsrv_cert_files = None + +# Uninstall +options.ignore_topology_disconnect = False +options.ignore_last_of_role = False + +# pylint: enable=attribute-defined-outside-init + + +# pylint: disable=invalid-name +def api_Backend_ldap2(host_name, setup_ca, connect=False): + # we are sure we have the configuration file ready. + cfg = dict(context='installer', confdir=paths.ETC_IPA, in_server=True, + host=host_name) + if setup_ca: + # we have an IPA-integrated CA + cfg['ca_host'] = host_name + + api.bootstrap(**cfg) + api.finalize() + if connect: + api.Backend.ldap2.connect() + + +# pylint: enable=invalid-name + + +def ds_init_info(ansible_log, fstore, domainlevel, dirsrv_config_file, + realm_name, host_name, domain_name, dm_password, + idstart, idmax, subject_base, ca_subject, + _no_hbac_allow, dirsrv_pkcs12_info, no_pkinit): + + if not options.external_cert_files: + _ds = dsinstance.DsInstance(fstore=fstore, domainlevel=domainlevel, + config_ldif=dirsrv_config_file) + _ds.set_output(ansible_log) + + if options.dirsrv_cert_files: + _dirsrv_pkcs12_info = dirsrv_pkcs12_info else: - cert = base64.b64decode(cert) - return cert + _dirsrv_pkcs12_info = None + + with redirect_stdout(ansible_log): + _ds.init_info(realm_name, host_name, domain_name, dm_password, + subject_base, ca_subject, idstart, idmax, + # hbac_allow=not no_hbac_allow, + _dirsrv_pkcs12_info, setup_pkinit=not no_pkinit) + else: + _ds = dsinstance.DsInstance(fstore=fstore, domainlevel=domainlevel) + _ds.set_output(ansible_log) + + with redirect_stdout(ansible_log): + _ds.init_info(realm_name, host_name, domain_name, dm_password, + subject_base, ca_subject, 1101, 1100, None, + setup_pkinit=not no_pkinit) + + return _ds + + +def ansible_module_get_parsed_ip_addresses(ansible_module, + param='ip_addresses'): + ip_addrs = [] + for _ip in ansible_module.params.get(param): + try: + ip_parsed = ipautil.CheckedIPAddress(_ip) + except Exception as err: + ansible_module.fail_json( + msg="Invalid IP Address %s: %s" % (_ip, err)) + ip_addrs.append(ip_parsed) + return ip_addrs + + +def encode_certificate(cert): + """ + Encode a certificate using base64. + + It also takes FreeIPA and Python versions into account. + """ + if isinstance(cert, (str, bytes)): + encoded = base64.b64encode(cert) + else: + encoded = base64.b64encode(cert.public_bytes(Encoding.DER)) + if not six.PY2: + encoded = encoded.decode('ascii') + return encoded + + +def decode_certificate(cert): + """ + Decode a certificate using base64. + + It also takes FreeIPA versions into account and returns a + IPACertificate for newer IPA versions. + """ + if hasattr(x509, "IPACertificate"): + cert = cert.strip() + if not cert.startswith("-----BEGIN CERTIFICATE-----"): + cert = "-----BEGIN CERTIFICATE-----\n" + cert + if not cert.endswith("-----END CERTIFICATE-----"): + cert += "\n-----END CERTIFICATE-----" + + cert = certificate_loader(cert.encode('utf-8')) + else: + cert = base64.b64decode(cert) + return cert + + +def check_imports(module): + if ANSIBLE_IPA_SERVER_MODULE_IMPORT_ERROR is not None: + module.fail_json(msg=ANSIBLE_IPA_SERVER_MODULE_IMPORT_ERROR)