Skip to content

Commit

Permalink
ipasudorule: Allow setting groups for runasuser.
Browse files Browse the repository at this point in the history
On IPA CLI sudorule-add/del-runasuser accept 'group' as a parameter,
and this option was missing in ansible-freeipa ipasudorule module.

This patch adds a new parameter 'runasuser_group' to allow setting
Groups of RunAs Users, as allowed by CLI and WebUI.

New example playboks can be found at:

    playbooks/sudorule/ensure-sudorule-runasusesr-group-is-absent.yml
    playbooks/sudorule/ensure-sudorule-runasusesr-group-is-present.yml
  • Loading branch information
rjeffman committed Sep 18, 2023
1 parent e5b2c12 commit a433ab1
Show file tree
Hide file tree
Showing 5 changed files with 140 additions and 8 deletions.
21 changes: 21 additions & 0 deletions README-sudorule.md
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,27 @@ Example playbook to make sure sudocmds are not present in Sudo Rule:
state: absent
```
Example playbook to ensure a Group of RunAs User is present in sudo rule:
```yaml
---
- name: Playbook no manage sudurule member
hosts: ipaserver
become: no
gather_facts: no

tasks:
- name: Ensure sudorule 'runasuser' do not have 'ipasuers' group as runas users.
ipasudorule:
ipaadmin_password: SomeADMINpassword
name: testrule1
runasuser_group: ipausers
action: member
state: absent
```
Example playbook to make sure Sudo Rule is absent:
```yaml
Expand Down
14 changes: 14 additions & 0 deletions playbooks/sudorule/ensure-sudorule-runasusesr-group-is-absent.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
---
- name: Playbook no manage sudurule member
hosts: ipaserver
become: no
gather_facts: no

tasks:
- name: Ensure sudorule 'runasuser' do not have 'ipasuers' group as runas users.
ipasudorule:
ipaadmin_password: SomeADMINpassword
name: testrule1
runasuser_group: ipausers
action: member
state: absent
13 changes: 13 additions & 0 deletions playbooks/sudorule/ensure-sudorule-runasusesr-group-is-present.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
---
- name: Playbook no manage sudurule member
hosts: ipaserver
become: no
gather_facts: no

tasks:
- name: Ensure sudorule 'runasuser' has 'ipasuers' group as runas users.
ipasudorule:
ipaadmin_password: SomeADMINpassword
name: testrule1
runasuser_group: ipausers
action: member
54 changes: 46 additions & 8 deletions plugins/modules/ipasudorule.py
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,11 @@
required: false
type: list
elements: str
runasuser_group:
description: List of groups for Sudo to execute as.
required: false
type: list
elements: str
runasgroup:
description: List of groups for Sudo to execute as.
required: false
Expand Down Expand Up @@ -214,6 +219,12 @@
hostmask:
- 192.168.122.1/24
- 192.168.120.1/24
# Ensure sudorule 'runasuser' has 'ipasuers' group as runas users.
- ipasudorule:
ipaadmin_password: SomeADMINpassword
name: testrule1
runasuser_group: ipausers
action: member
# Ensure Sudo Rule tesrule1 is absent
Expand Down Expand Up @@ -315,6 +326,8 @@ def main():
default=None),
runasgroup=dict(required=False, type="list", elements="str",
default=None),
runasuser_group=dict(required=False, type="list", elements="str",
default=None),
order=dict(type="int", required=False, aliases=['sudoorder']),
sudooption=dict(required=False, type='list', elements="str",
default=None, aliases=["options"]),
Expand Down Expand Up @@ -362,6 +375,7 @@ def main():
sudooption = ansible_module.params_get("sudooption")
order = ansible_module.params_get("order")
runasuser = ansible_module.params_get_lowercase("runasuser")
runasuser_group = ansible_module.params_get_lowercase("runasuser_group")
runasgroup = ansible_module.params_get_lowercase("runasgroup")
action = ansible_module.params_get("action")

Expand Down Expand Up @@ -406,7 +420,8 @@ def main():
invalid.extend(["host", "hostgroup", "hostmask", "user", "group",
"runasuser", "runasgroup", "allow_sudocmd",
"allow_sudocmdgroup", "deny_sudocmd",
"deny_sudocmdgroup", "sudooption"])
"deny_sudocmdgroup", "sudooption",
"runasuser_group"])

elif state in ["enabled", "disabled"]:
if len(names) < 1:
Expand All @@ -420,7 +435,7 @@ def main():
"nomembers", "nomembers", "host", "hostgroup", "hostmask",
"user", "group", "allow_sudocmd", "allow_sudocmdgroup",
"deny_sudocmd", "deny_sudocmdgroup", "runasuser",
"runasgroup", "order", "sudooption"]
"runasgroup", "order", "sudooption", "runasuser_group"]
else:
ansible_module.fail_json(msg="Invalid state '%s'" % state)

Expand Down Expand Up @@ -453,6 +468,7 @@ def main():
deny_cmdgroup_add, deny_cmdgroup_del = [], []
sudooption_add, sudooption_del = [], []
runasuser_add, runasuser_del = [], []
runasuser_group_add, runasuser_group_del = [], []
runasgroup_add, runasgroup_del = [], []

for name in names:
Expand Down Expand Up @@ -552,6 +568,12 @@ def main():
+ res_find.get('ipasudorunasextuser', [])
)
)
runasuser_group_add, runasuser_group_del = (
gen_add_del_lists(
runasuser_group,
res_find.get('ipasudorunas_group', [])
)
)

# runasgroup attribute can be used with both IPA and
# non-IPA (external) groups. IPA will handle the correct
Expand Down Expand Up @@ -623,6 +645,11 @@ def main():
(list(res_find.get('ipasudorunas_user', []))
+ list(res_find.get('ipasudorunasextuser', [])))
)
if runasuser_group is not None:
runasuser_group_add = gen_add_list(
runasuser_group,
list(res_find.get('ipasudorunas_group', []))
)
# runasgroup attribute can be used with both IPA and
# non-IPA (external) groups, so we need to compare
# the provided list against both users and external
Expand Down Expand Up @@ -703,6 +730,11 @@ def main():
+ list(res_find.get('ipasudorunasextuser', []))
)
)
if runasuser_group is not None:
runasuser_group_del = gen_intersection_list(
runasuser_group,
list(res_find.get('ipasudorunas_group', []))
)
# runasgroup attribute can be used with both IPA and
# non-IPA (external) groups, so we need to compare
# the provided list against both groups and external
Expand Down Expand Up @@ -812,13 +844,19 @@ def main():
}
])
# Manage RunAS users
if runasuser_add:
commands.append([
name, "sudorule_add_runasuser", {"user": runasuser_add}
])
if runasuser_del:
if runasuser_add or runasuser_group_add:
# Can't use empty lists with command "sudorule_add_runasuser".
_args = {}
if runasuser_add:
_args["user"] = runasuser_add
if runasuser_group_add:
_args["group"] = runasuser_group_add
commands.append([name, "sudorule_add_runasuser", _args])
if runasuser_del or runasuser_group_del:
commands.append([
name, "sudorule_remove_runasuser", {"user": runasuser_del}
name,
"sudorule_remove_runasuser",
{"user": runasuser_del, "group": runasuser_group_del}
])

# Manage RunAS Groups
Expand Down
46 changes: 46 additions & 0 deletions tests/sudorule/test_sudorule.yml
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,52 @@
register: result
failed_when: result.changed or result.failed

- name: Ensure group01 is on the list of users sudorule execute as.
ipasudorule:
ipaadmin_password: SomeADMINpassword
ipaapi_context: "{{ ipa_context | default(omit) }}"
name: testrule1
runasuser_group:
- group01
action: member
register: result
failed_when: not result.changed or result.failed

- name: Ensure group01 is on the list of users sudorule execute as, again.
ipasudorule:
ipaadmin_password: SomeADMINpassword
ipaapi_context: "{{ ipa_context | default(omit) }}"
name: testrule1
runasuser_group:
- group01
action: member
register: result
failed_when: result.changed or result.failed

- name: Ensure group01 is not on the list of users sudorule execute as.
ipasudorule:
ipaadmin_password: SomeADMINpassword
ipaapi_context: "{{ ipa_context | default(omit) }}"
name: testrule1
runasuser_group:
- group01
action: member
state: absent
register: result
failed_when: not result.changed or result.failed

- name: Ensure group01 is not on the list of users sudorule execute as, again.
ipasudorule:
ipaadmin_password: SomeADMINpassword
ipaapi_context: "{{ ipa_context | default(omit) }}"
name: testrule1
runasuser_group:
- group01
action: member
state: absent
register: result
failed_when: result.changed or result.failed

- name: Ensure group01 is on the list of group sudorule execute as.
ipasudorule:
ipaadmin_password: SomeADMINpassword
Expand Down

0 comments on commit a433ab1

Please sign in to comment.