diff --git a/roles/pulp_django_user/README.md b/roles/pulp_django_user/README.md index 0bc8e0f..52be468 100644 --- a/roles/pulp_django_user/README.md +++ b/roles/pulp_django_user/README.md @@ -12,6 +12,8 @@ Role variables * `pulp_validate_certs`: Whether to validate Pulp server certificate. Default is `true` * `pulp_django_users`: List of Django users to create. Default is an empty list. +Note: User groups are evauluated against the user's current list of groups returned from the Pulp server API. Removing a group from the list of groups defined in `pulp_django_users[*].groups` will result in the user being removed from that group, and adding a group will result in the user being added to that group. Adding an empty `groups:` for a user will result in that user being removed from all groups. + Example playbook ---------------- @@ -28,4 +30,7 @@ Example playbook pulp_django_users: - username: test-user password: correct horse battery staple + groups: + - existing.container.namespace.consumers.one + - existing.container.namespace.consumers.two ``` diff --git a/roles/pulp_django_user/tasks/main.yml b/roles/pulp_django_user/tasks/main.yml index 0001cdb..03a1803 100644 --- a/roles/pulp_django_user/tasks/main.yml +++ b/roles/pulp_django_user/tasks/main.yml @@ -46,3 +46,10 @@ loop: "{{ pulp_django_users }}" loop_control: label: "{{ item.username }}" + +- name: Add or remove user from group(s) + include_tasks: user_groups/add_or_remove_users.yml + # Noop if pulp_django_users is defined but empty + loop: "{{ pulp_django_users | default([], true) }}" + loop_control: + loop_var: user diff --git a/roles/pulp_django_user/tasks/user_groups/add_or_remove_users.yml b/roles/pulp_django_user/tasks/user_groups/add_or_remove_users.yml new file mode 100644 index 0000000..2d1f5ee --- /dev/null +++ b/roles/pulp_django_user/tasks/user_groups/add_or_remove_users.yml @@ -0,0 +1,27 @@ +--- + +- name: Get all groups that user belongs to + uri: + url: "{{ pulp_get_user_url }}?username={{ user.username }}" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + method: GET + status_code: 200 + force_basic_auth: true + register: user_group_result + +- name: Set current_group_membership fact + set_fact: + current_group_membership: "{{ user_group_result | json_query('json.results[*].groups') | flatten | map(attribute='name') | list }}" + +- name: Remove user from groups not defined in pulp_django_users + include_tasks: remove_user_from_groups.yml + loop: "{{ current_group_membership | difference(user.groups | default([], true)) }}" + loop_control: + loop_var: remove_group + +- name: Add user to groups defined in pulp_django_users + include_tasks: add_user_to_groups.yml + loop: "{{ user.groups | default([], true) | difference(current_group_membership) }}" + loop_control: + loop_var: add_group diff --git a/roles/pulp_django_user/tasks/user_groups/add_user_to_groups.yml b/roles/pulp_django_user/tasks/user_groups/add_user_to_groups.yml new file mode 100644 index 0000000..bf70c1e --- /dev/null +++ b/roles/pulp_django_user/tasks/user_groups/add_user_to_groups.yml @@ -0,0 +1,39 @@ +--- +# These user/group combinations definitely DO NOT exist on pulp server + +- name: Get group href from Pulp API + uri: + url: "{{ pulp_add_group_user_url }}?name={{ add_group }}" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + method: GET + status_code: 200 + force_basic_auth: true + register: group_href_result + +- name: Fail when group cannot be unambiguosly returned from Pulp + fail: + msg: > + "Pulp API query: GET '{{ group_href_result.url }}' did not return + exactly one group. Groupname '{{ add_group }}' was found + '{{ group_href_result.json.count }}' times. + Groupnames should be unique and exist before associating users + with them" + when: group_href_result.json.count != 1 + +# Will fail before we get here if the group doesn't exist or has +# an ambiguous name +- name: Add user to group + uri: + url: "{{ pulp_url }}{{ group_href_result.json.results[0].pulp_href }}users/" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + body: + username: "{{ user.username }}" + body_format: json + method: POST + force_basic_auth: true + # Always returns 201 even if user/group exists + status_code: 201 + # If we get here we're always changing something + changed_when: true diff --git a/roles/pulp_django_user/tasks/user_groups/remove_user_from_groups.yml b/roles/pulp_django_user/tasks/user_groups/remove_user_from_groups.yml new file mode 100644 index 0000000..64bf11a --- /dev/null +++ b/roles/pulp_django_user/tasks/user_groups/remove_user_from_groups.yml @@ -0,0 +1,56 @@ +--- +# These user/group combinations definitely DO exist on pulp server + +- name: Get group href from Pulp API + uri: + url: "{{ pulp_add_group_user_url }}?name={{ remove_group }}" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + method: GET + status_code: 200 + force_basic_auth: true + register: group_href_result + +# We should only return a single group here because we've just queried +# from pulp API +- name: Fail when group cannot be unambiguosly returned from Pulp API + fail: + msg: > + "Pulp API query: GET '{{ group_href_result.url }}' did not return + exactly one group. Groupname '{{ remove_group }}' was found + '{{ group_href_result.json.count }}' times. + Groupnames should be unique and exist before associating users + with them" + when: group_href_result.json.count != 1 + +- name: Get user id from Pulp API + uri: + url: "{{ pulp_get_user_url }}?username={{ user.username }}" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + method: GET + status_code: 200 + force_basic_auth: true + register: user_list_result + +- name: Fail when user id cannot be unambiguosly returned from Pulp API + fail: + msg: > + "Pulp API query: GET '{{ user_list_result.url }}' did not return + exactly one user id. User '{{ user.username }}' was found + '{{ user_list_result.json.count }}' times." + when: user_list_result.json.count != 1 + +# Will fail before we get here if the group/user doesn't exist +- name: Remove user from group + # DELETE {{ pulp_url }}/pulp/api/v3/groups/880/users/11/ + uri: + url: "{{ pulp_url }}{{ group_href_result.json.results[0].pulp_href }}users/{{ user_list_result.json.results[0].id }}/" + user: "{{ pulp_admin_username }}" + password: "{{ pulp_admin_password }}" + method: DELETE + # Always returns 204 even if user/group doesn't exist + status_code: 204 + force_basic_auth: true + # If we get here, we're always changing something + changed_when: true diff --git a/roles/pulp_django_user/vars/main.yml b/roles/pulp_django_user/vars/main.yml index ba25749..640992b 100644 --- a/roles/pulp_django_user/vars/main.yml +++ b/roles/pulp_django_user/vars/main.yml @@ -1,3 +1,5 @@ --- pulp_login_url: "{{ pulp_url }}/admin/login/?next=/admin/" pulp_add_user_url: "{{ pulp_url }}/admin/auth/user/add/" +pulp_get_user_url: "{{ pulp_url }}/pulp/api/v3/users/" +pulp_add_group_user_url: "{{ pulp_url }}/pulp/api/v3/groups/"