From 6df89ad7db6a76a34dae70e25ea2f19cd55560f4 Mon Sep 17 00:00:00 2001 From: Rafael Guterres Jeffman Date: Tue, 3 Jun 2025 21:29:43 -0300 Subject: [PATCH] ipaidrange: Require usage of range id parameters When adding a new idrange of type 'ipa-local', the 'base_id', 'range_size', 'rid_base' and 'secondary_rid_base' are required so that range entries are correctly set when SID are enabled. Fixes: https://issues.redhat.com/browse/RHEL-79820 Signed-off-by: Rafael Guterres Jeffman --- README-idrange.md | 21 ++------------- plugins/modules/ipaidrange.py | 20 ++++++++++++++ tests/idrange/test_idrange.yml | 49 ++++++++++++++++++++++++++++++++++ 3 files changed, 71 insertions(+), 19 deletions(-) diff --git a/README-idrange.md b/README-idrange.md index f5a5b32a..2f6552bc 100644 --- a/README-idrange.md +++ b/README-idrange.md @@ -68,23 +68,6 @@ Example playbook to ensure a local domain idrange is present: name: local_domain_id_range base_id: 150000 range_size: 200000 -``` - -Example playbook to ensure a local domain idrange is present, with RID and secondary RID base values: - -```yaml ---- -- name: Playbook to manage IPA idrange. - hosts: ipaserver - become: no - - tasks: - - name: Ensure local idrange is present - ipaidrange: - ipaadmin_password: SomeADMINpassword - name: local_domain_id_range - base_id: 150000000 - range_size: 200000 rid_base: 1000000 secondary_rid_base: 200000000 ``` @@ -172,8 +155,8 @@ Variable | Description | Required `name` \| `cn` | The list of idrange name strings. | yes `base_id` \| `ipabaseid` | First Posix ID of the range. (int) | yes, if `state: present` `range_size` \| `ipaidrangesize` | Number of IDs in the range. (int) | yes, if `state: present` -`rid_base` \| `ipabaserid` | First RID of the corresponding RID range. (int) | no -`secondary_rid_base` \| `ipasecondarybaserid` | First RID of the secondary RID range. (int) | no +`rid_base` \| `ipabaserid` | First RID of the corresponding RID range. (int) | yes, if `idrange_type: ipa-local` and `state: present` | +`secondary_rid_base` \| `ipasecondarybaserid` | First RID of the secondary RID range. (int) | yes, if `idrange_type: ipa-local` and `state: present` | `dom_sid` \| `ipanttrusteddomainsid` | Domain SID of the trusted domain. | no `idrange_type` \| `iparangetype` | ID range type, one of `ipa-ad-trust`, `ipa-ad-trust-posix`, `ipa-local`. Only valid if idrange does not exist. | no `dom_name` \| `ipanttrusteddomainname` | Name of the trusted domain. Can only be used when `ipaapi_context: server`. | no diff --git a/plugins/modules/ipaidrange.py b/plugins/modules/ipaidrange.py index 60a2fdc7..74f948fa 100644 --- a/plugins/modules/ipaidrange.py +++ b/plugins/modules/ipaidrange.py @@ -281,6 +281,14 @@ def main(): # Connect to IPA API with ansible_module.ipa_connect(): + # set required fields + required = ["base_id", "range_size"] + requires_baserid = ( + ansible_module.ipa_command_param_exists("config_mod", "enable_sid") + and idrange_type in [None, "ipa-local"] + ) + if requires_baserid: + required.extend(["rid_base", "secondary_rid_base"]) commands = [] for name in names: @@ -321,6 +329,18 @@ def main(): del args["iparangetype"] commands.append([name, "idrange_mod", args]) else: + # Check if required parameters were given + missing_params = [ + pname for pname in required + if ansible_module.params_get(pname) is None + ] + if missing_params: + ansible_module.fail_json( + msg=( + "Missing required parameters: %s" + % (", ".join(missing_params)) + ) + ) commands.append([name, "idrange_add", args]) elif state == "absent": diff --git a/tests/idrange/test_idrange.yml b/tests/idrange/test_idrange.yml index 2becb9c1..e75a7931 100644 --- a/tests/idrange/test_idrange.yml +++ b/tests/idrange/test_idrange.yml @@ -36,6 +36,50 @@ # Test local idrange, only if ipa-adtrust-install was not executed. - name: Test local idrange block: + - name: Can't add idrange without base_id + ipaidrange: + ipaadmin_password: SomeADMINpassword + ipaapi_context: "{{ ipa_context | default(omit) }}" + name: local_id_range + range_size: 200000 + rid_base: 1000000 + secondary_rid_base: 200000000 + register: result + failed_when: "not (result.failed and 'Missing required parameters: base_id' in result.msg)" + + - name: Can't add idrange without range_size + ipaidrange: + ipaadmin_password: SomeADMINpassword + ipaapi_context: "{{ ipa_context | default(omit) }}" + name: local_id_range + base_id: 150000000 + rid_base: 1000000 + secondary_rid_base: 200000000 + register: result + failed_when: "not (result.failed and 'Missing required parameters: range_size' in result.msg)" + + - name: Can't add idrange without rid_base + ipaidrange: + ipaadmin_password: SomeADMINpassword + ipaapi_context: "{{ ipa_context | default(omit) }}" + name: local_id_range + base_id: 150000000 + range_size: 200000 + secondary_rid_base: 200000000 + register: result + failed_when: "not (result.failed and 'Missing required parameters: rid_base' in result.msg)" + + - name: Can't add idrange without secondary_rid_base + ipaidrange: + ipaadmin_password: SomeADMINpassword + ipaapi_context: "{{ ipa_context | default(omit) }}" + name: local_id_range + base_id: 150000000 + range_size: 200000 + rid_base: 1000000 + register: result + failed_when: "not (result.failed and 'Missing required parameters: secondary_rid_base' in result.msg)" + - name: Ensure idrange with minimal attributes is present ipaidrange: ipaadmin_password: SomeADMINpassword @@ -43,6 +87,8 @@ name: local_id_range base_id: 150000000 range_size: 200000 + rid_base: 1000000 + secondary_rid_base: 200000000 register: result failed_when: not (result.failed or result.changed) or (result.failed and 'ipa-adtrust-install has already been run' not in result.msg) @@ -54,6 +100,8 @@ name: local_id_range base_id: 150000000 range_size: 200000 + rid_base: 1000000 + secondary_rid_base: 200000000 register: result failed_when: result.changed or (result.failed and 'ipa-adtrust-install has already been run' not in result.msg) @@ -118,6 +166,7 @@ ipaadmin_password: SomeADMINpassword ipaapi_context: "{{ ipa_context | default(omit) }}" name: local_id_range + state: absent - name: Execute idrange tests if trust test environment is supported when: trust_test_is_supported | default(false)