re-add collections; aap not happy

This commit is contained in:
2024-02-07 17:21:22 -05:00
parent 4ac2aab28d
commit 80f03628d2
3297 changed files with 461576 additions and 6 deletions

View File

@ -0,0 +1 @@
output/

View File

@ -0,0 +1,2 @@
shippable/posix/group1
skip/aix

View File

@ -0,0 +1,215 @@
# (c) 2017, Martin Krizek <mkrizek@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: Create ansible user
user:
name: "{{ test_user }}"
- name: Create ansible group
group:
name: "{{ test_group }}"
- name: Clean up working directory and files
file:
path: "{{ output_dir }}"
state: absent
- name: Create working directory
file:
path: "{{ output_dir }}"
state: directory
- name: Create ansible file
file:
path: "{{ test_file }}"
state: touch
- name: Create ansible dir
file:
path: "{{ test_dir }}"
state: directory
##############################################################################
- name: Grant ansible user read access to a file
acl:
path: "{{ test_file }}"
entity: "{{ test_user }}"
etype: user
permissions: r
state: present
register: output
- name: get getfacl output
shell: "getfacl {{ test_file | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is changed
- output is not failed
- "'user:{{ test_user }}:r--' in output.acl"
- "'user:{{ test_user }}:r--' in getfacl_output.stdout_lines"
##############################################################################
- name: Obtain the acl for a specific file
acl:
path: "{{ test_file }}"
register: output
- name: get getfacl output
shell: "getfacl {{ test_file | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is not changed
- output is not failed
- "'user::rw-' in output.acl"
- "'user:{{ test_user }}:r--' in output.acl"
- "'group::r--' in output.acl"
- "'mask::r--' in output.acl"
- "'other::r--' in output.acl"
- "'user::rw-' in getfacl_output.stdout_lines"
- "'user:{{ test_user }}:r--' in getfacl_output.stdout_lines"
- "'group::r--' in getfacl_output.stdout_lines"
- "'mask::r--' in getfacl_output.stdout_lines"
- "'other::r--' in getfacl_output.stdout_lines"
##############################################################################
- name: Removes the acl for ansible user on a specific file
acl:
path: "{{ test_file }}"
entity: "{{ test_user }}"
etype: user
state: absent
register: output
- name: get getfacl output
shell: "getfacl {{ test_file | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is changed
- output is not failed
- "'user:{{ test_user }}:r--' not in output.acl"
- "'user:{{ test_user }}:r--' not in getfacl_output.stdout_lines"
##############################################################################
- name: Sets default acl for ansible user on ansible dir
acl:
path: "{{ test_dir }}"
entity: "{{ test_user }}"
etype: user
permissions: rw
default: yes
state: present
register: output
- name: get getfacl output
shell: "getfacl {{ test_dir | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is changed
- output is not failed
- "'user:{{ test_user }}:rw-' in output.acl"
- "'default:user:{{ test_user }}:rw-' in getfacl_output.stdout_lines"
##############################################################################
- name: Cleanup
shell: "setfacl -b {{ test_dir | quote }}"
##############################################################################
- name: Same as previous but using entry shorthand
acl:
path: "{{ test_dir }}"
entry: "user:{{ test_user }}:rw-"
default: yes
state: present
register: output
- name: get getfacl output
shell: "getfacl {{ test_dir | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is changed
- output is not failed
- "'user:{{ test_user }}:rw-' in output.acl"
- "'default:user:{{ test_user }}:rw-' in getfacl_output.stdout_lines"
##############################################################################
- name: Same as previous, to test idempotence
acl:
path: "{{ test_dir }}"
entry: "user:{{ test_user }}:rw-"
default: yes
state: present
register: output
- name: get getfacl output
shell: "getfacl {{ test_dir | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is not changed
- output is not failed
- "'user:{{ test_user }}:rw-' in output.acl"
- "'default:user:{{ test_user }}:rw-' in getfacl_output.stdout_lines"
##############################################################################
- name: Cleanup
shell: "setfacl -b {{ test_dir | quote }}"
##############################################################################
- name: Set default acls
acl:
path: "{{ test_dir }}"
entry: "{{ item }}"
default: yes
state: present
with_items:
- "user:{{ test_user }}:rw-"
- "group:{{ test_group }}:rw-"
- name: Remove default group test_user acl
acl:
path: "{{ test_dir }}"
entry: "group:{{ test_group }}:rw-"
default: yes
state: absent
register: output
- name: get getfacl output
shell: "getfacl {{ test_dir | quote }}"
register: getfacl_output
- name: verify output
assert:
that:
- output is changed
- output is not failed
- "'user::rwx' in getfacl_output.stdout_lines"
- "'group::r-x' in getfacl_output.stdout_lines"
- "'other::r-x' in getfacl_output.stdout_lines"
- "'default:user::rwx' in getfacl_output.stdout_lines"
- "'default:user:{{ test_user }}:rw-' in getfacl_output.stdout_lines"
- "'default:group::r-x' in getfacl_output.stdout_lines"
- "'default:mask::rwx' in getfacl_output.stdout_lines"
- "'default:other::r-x' in getfacl_output.stdout_lines"
- "'default:group:{{ test_group }}:rw-' not in getfacl_output.stdout_lines"

View File

@ -0,0 +1,36 @@
# (c) 2017, Martin Krizek <mkrizek@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- block:
- include: acl.yml
when: ansible_system == 'Linux' # TODO enable acls mount option on FreeBSD to test it there too
always:
- name: delete created directory and file
file:
path: '{{ item }}'
state: absent
with_items:
- '{{ test_dir }}'
- '{{ test_file }}'
vars:
test_user: ansible_user
test_group: ansible_group
test_file: '{{ output_dir }}/ansible file'
test_dir: "{{ output_dir }}/ansible_dir/with some space"

View File

@ -0,0 +1,3 @@
shippable/posix/group1
destructive
disabled # fixme package

View File

@ -0,0 +1,2 @@
dependencies:
- prepare_tests

View File

@ -0,0 +1,62 @@
# Test code for the at module.
# (c) 2017, James Tanner <tanner.jc@gmail.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- set_fact: output_dir_test={{output_dir}}/at
- name: make sure our testing sub-directory does not exist
file: path="{{ output_dir_test }}" state=absent
- name: create our testing sub-directory
file: path="{{ output_dir_test }}" state=directory
##
## at
##
- name: define distros to attempt installing at on
set_fact:
package_distros:
- RedHat
- CentOS
- ScientificLinux
- Fedora
- Ubuntu
- Debian
- openSUSE Leap
- name: ensure at is installed
package:
name: at
state: present
when: ansible_distribution in package_distros
- name: run the first example
at:
command: "ls -d / > /dev/null"
count: 20
units: minutes
register: at_test0
- debug: var=at_test0
- name: validate results
assert:
that:
- 'at_test0.changed is defined'
- 'at_test0.count is defined'
- 'at_test0.script_file is defined'
- 'at_test0.state is defined'
- 'at_test0.units is defined'

View File

@ -0,0 +1,2 @@
needs/root
shippable/posix/group1

View File

@ -0,0 +1,36 @@
dss_key_basic: ssh-dss DATA_BASIC root@testing
dss_key_unquoted_option: idle-timeout=5m ssh-dss DATA_UNQUOTED_OPTION root@testing
dss_key_command: command="/bin/true" ssh-dss DATA_COMMAND root@testing
dss_key_complex_command: command="echo foo 'bar baz'" ssh-dss DATA_COMPLEX_COMMAND root@testing
dss_key_command_single_option: no-port-forwarding,command="/bin/true" ssh-dss DATA_COMMAND_SINGLE_OPTIONS root@testing
dss_key_command_multiple_options: no-port-forwarding,idle-timeout=5m,command="/bin/true" ssh-dss DATA_COMMAND_MULTIPLE_OPTIONS root@testing
dss_key_trailing: ssh-dss DATA_TRAILING root@testing foo bar baz
rsa_key_basic: ssh-rsa DATA_BASIC root@testing
multiple_key_base: |
ssh-rsa DATA_BASIC 1@testing
ssh-dss DATA_TRAILING 2@testing foo bar baz
ssh-dss DATA_TRAILING 3@testing foo bar baz
ecdsa-sha2-nistp521 ECDSA_DATA 4@testing
multiple_key_different_order: |
ssh-dss DATA_TRAILING 2@testing foo bar baz
ssh-dss DATA_TRAILING 3@testing foo bar baz
ssh-rsa DATA_BASIC 1@testing
ecdsa-sha2-nistp521 ECDSA_DATA 4@testing
multiple_key_different_order_2: |
ssh-dss DATA_TRAILING 2@testing foo bar baz
ssh-rsa WHATEVER 2.5@testing
ssh-dss DATA_TRAILING 3@testing foo bar baz
ssh-rsa DATA_BASIC 1@testing
ecdsa-sha2-nistp521 ECDSA_DATA 4@testing
multiple_key_exclusive: |
ssh-rsa DATA_BASIC 1@testing
ecdsa-sha2-nistp521 ECDSA_DATA 4@testing
multiple_keys_comments: |
ssh-rsa DATA_BASIC 1@testing
# I like adding comments yo-dude-this-is-not-a-key INVALID_DATA 2@testing
ecdsa-sha2-nistp521 ECDSA_DATA 4@testing

View File

@ -0,0 +1,5 @@
# I like candy
ssh-rsa somekeydata somekeyalias
# It is a very pleasant temperature outside today.
ssh-rsa otherkeydata otherkeyalias

View File

@ -0,0 +1,2 @@
dependencies:
- prepare_tests

View File

@ -0,0 +1,34 @@
# -------------------------------------------------------------
# check mode
- name: CHECK MODE | copy an existing file in place with comments
copy:
src: existing_authorized_keys
dest: "{{ output_dir | expanduser }}/authorized_keys"
- name: CHECK MODE | add key in check mode to validate return codes
authorized_key:
user: root
key: "{{ multiple_key_different_order_2 }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
check_mode: True
register: result
- name: CHECK MODE | assert that authorized_keys return values are consistent
assert:
that:
- 'result.changed == True'
- '"user" in result'
- '"key" in result'
- name: CHECK MODE | recopy authorized_keys to ensure it was not changed
copy:
src: existing_authorized_keys
dest: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: CHECK MODE | assert that the authorized_keys file was not changed
assert:
that:
- 'result.changed == False'

View File

@ -0,0 +1,50 @@
# -------------------------------------------------------------
# comments
- name: Add rsa key with existing comment
authorized_key:
user: root
key: "{{ rsa_key_basic }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: Change the comment on an existing key
authorized_key:
user: root
key: "{{ rsa_key_basic }}"
comment: user@acme.com
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: get the file content
shell: cat "{{ output_dir | expanduser }}/authorized_keys" | fgrep DATA_BASIC
changed_when: no
register: content
- name: Assert that comment on an existing key was changed
assert:
that:
- "'user@acme.com' in content.stdout"
- name: Set the same key with comment to ensure no changes are reported
authorized_key:
user: root
key: "{{ rsa_key_basic }}"
comment: user@acme.com
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: Assert that no changes were made when running again
assert:
that:
- not result.changed
- debug:
var: "{{ item }}"
verbosity: 1
with_items:
- result
- content

View File

@ -0,0 +1,32 @@
# test code for the authorized_key module
# - (c) 2014, James Cammarata <jcammarata@ansible.com>
# - (c) 2021, Hideki Saito <saito@fgrep.org>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: Setup testing environment
import_tasks: setup_steps.yml
- name: Test for multiple keys handling
import_tasks: multiple_keys.yml
- name: Test for ssh-dss key handling
import_tasks: ssh_dss.yml
- name: Test for check mode
import_tasks: check_mode.yml
- name: Test for the management of comments with key
import_tasks: comments.yml

View File

@ -0,0 +1,96 @@
# -------------------------------------------------------------
# multiple keys
- name: add multiple keys
authorized_key:
user: root
key: "{{ multiple_key_base }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == multiple_key_base'
- 'result.key_options == None'
- name: add multiple keys different order
authorized_key:
user: root
key: "{{ multiple_key_different_order }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == multiple_key_different_order'
- 'result.key_options == None'
- name: add multiple keys exclusive
authorized_key:
user: root
key: "{{ multiple_key_exclusive }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
exclusive: true
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == multiple_key_exclusive'
- 'result.key_options == None'
- name: add multiple keys in different calls
authorized_key:
user: root
key: "ecdsa-sha2-nistp521 ECDSA_DATA 4@testing"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: add multiple keys in different calls
authorized_key:
user: root
key: "ssh-rsa DATA_BASIC 1@testing"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: get the file content
shell: cat "{{ output_dir | expanduser }}/authorized_keys"
changed_when: no
register: multiple_keys_at_a_time
- name: assert that the key was added
assert:
that:
- 'result.changed == false'
- 'multiple_keys_at_a_time.stdout == multiple_key_exclusive.strip()'
- name: add multiple keys comment
authorized_key:
user: root
key: "{{ multiple_keys_comments }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
exclusive: true
register: result
- name: get the file content
shell: cat "{{ output_dir | expanduser }}/authorized_keys"
changed_when: no
register: multiple_keys_comments
- name: assert that the keys exist and comment only lines were not added
assert:
that:
- 'result.changed == False'
- 'multiple_keys_comments.stdout == multiple_key_exclusive.strip()'
- 'result.key_options == None'

View File

@ -0,0 +1,59 @@
# -------------------------------------------------------------
# Setup steps
- name: Clean up the working directory and files
file:
path: '{{ output_dir }}'
state: absent
- name: Create the working directory
file:
path: '{{ output_dir }}'
state: directory
- name: copy an existing file in place with comments
copy:
src: existing_authorized_keys
dest: "{{ output_dir | expanduser }}/authorized_keys"
- name: add multiple keys different order
authorized_key:
user: root
key: "{{ multiple_key_different_order_2 }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: get the file content
shell: cat "{{ output_dir | expanduser }}/authorized_keys"
changed_when: no
register: multiple_keys_existing
- name: assert that the key was added and comments and ordering preserved
assert:
that:
- 'result.changed == True'
- '"# I like candy" in multiple_keys_existing.stdout'
- '"# I like candy" in multiple_keys_existing.stdout_lines[0]'
- '"ssh-rsa DATA_BASIC 1@testing" in multiple_keys_existing.stdout'
# The specific index is a little fragile, but I want to verify the line shows up
# as the 3rd line in the new entries after the existing entries and comments are preserved
- '"ssh-rsa DATA_BASIC 1@testing" in multiple_keys_existing.stdout_lines[7]'
# start afresh
- name: remove file foo.txt
file:
path: "{{ output_dir | expanduser }}/authorized_keys"
state: absent
- name: touch the authorized_keys file
file:
dest: "{{ output_dir }}/authorized_keys"
state: touch
register: result
- name: assert that the authorized_keys file was created
assert:
that:
- 'result.changed == True'
- 'result.state == "file"'

View File

@ -0,0 +1,241 @@
# -------------------------------------------------------------
# basic ssh-dss key
- name: add basic ssh-dss key
authorized_key: user=root key="{{ dss_key_basic }}" state=present path="{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_basic'
- 'result.key_options == None'
- name: re-add basic ssh-dss key
authorized_key: user=root key="{{ dss_key_basic }}" state=present path="{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with an unquoted option
- name: add ssh-dss key with an unquoted option
authorized_key:
user: root
key: "{{ dss_key_unquoted_option }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_unquoted_option'
- 'result.key_options == None'
- name: re-add ssh-dss key with an unquoted option
authorized_key:
user: root
key: "{{ dss_key_unquoted_option }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with a leading command="/bin/foo"
- name: add ssh-dss key with a leading command
authorized_key:
user: root
key: "{{ dss_key_command }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_command'
- 'result.key_options == None'
- name: re-add ssh-dss key with a leading command
authorized_key:
user: root
key: "{{ dss_key_command }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with a complex quoted leading command
# ie. command="/bin/echo foo 'bar baz'"
- name: add ssh-dss key with a complex quoted leading command
authorized_key:
user: root
key: "{{ dss_key_complex_command }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_complex_command'
- 'result.key_options == None'
- name: re-add ssh-dss key with a complex quoted leading command
authorized_key:
user: root
key: "{{ dss_key_complex_command }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with a command and a single option, which are
# in a comma-separated list
- name: add ssh-dss key with a command and a single option
authorized_key:
user: root
key: "{{ dss_key_command_single_option }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_command_single_option'
- 'result.key_options == None'
- name: re-add ssh-dss key with a command and a single option
authorized_key:
user: root
key: "{{ dss_key_command_single_option }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with a command and multiple other options
- name: add ssh-dss key with a command and multiple options
authorized_key:
user: root
key: "{{ dss_key_command_multiple_options }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_command_multiple_options'
- 'result.key_options == None'
- name: re-add ssh-dss key with a command and multiple options
authorized_key:
user: root
key: "{{ dss_key_command_multiple_options }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# ssh-dss key with multiple trailing parts, which are space-
# separated and not quoted in any way
- name: add ssh-dss key with trailing parts
authorized_key:
user: root
key: "{{ dss_key_trailing }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_trailing'
- 'result.key_options == None'
- name: re-add ssh-dss key with trailing parts
authorized_key:
user: root
key: "{{ dss_key_trailing }}"
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that nothing changed
assert:
that:
- 'result.changed == False'
# -------------------------------------------------------------
# basic ssh-dss key with mutliple permit-open options
# https://github.com/ansible/ansible-modules-core/issues/1715
- name: add basic ssh-dss key with multi-opts
authorized_key:
user: root
key: "{{ dss_key_basic }}"
key_options: 'no-agent-forwarding,no-X11-forwarding,permitopen="10.9.8.1:8080",permitopen="10.9.8.1:9001"'
state: present
path: "{{ output_dir | expanduser }}/authorized_keys"
register: result
- name: assert that the key with multi-opts was added
assert:
that:
- 'result.changed == True'
- 'result.key == dss_key_basic'
- 'result.key_options == "no-agent-forwarding,no-X11-forwarding,permitopen=\"10.9.8.1:8080\",permitopen=\"10.9.8.1:9001\""'
- name: get the file content
shell: cat "{{ output_dir | expanduser }}/authorized_keys" | fgrep DATA_BASIC
changed_when: no
register: content
- name: validate content
assert:
that:
- 'content.stdout == "no-agent-forwarding,no-X11-forwarding,permitopen=\"10.9.8.1:8080\",permitopen=\"10.9.8.1:9001\" ssh-dss DATA_BASIC root@testing"'

View File

@ -0,0 +1,5 @@
destructive
shippable/posix/group1
skip/aix
skip/freebsd
skip/osx

View File

@ -0,0 +1,2 @@
dependencies:
- setup_pkg_mgr

View File

@ -0,0 +1,172 @@
# Test playbook for the firewalld module - icmp block inversion operations
# (c) 2022, Gregory Furlong <gnfzdz@fzdz.io>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Icmp block inversion enabled when icmp block inversion is truthy and state is enabled
block:
- name: Testing enable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: yes
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is enabled
assert:
that:
- result is changed
- name: Testing enable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: yes
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Icmp block inversion disabled when icmp block inversion is falsy and state is enabled
block:
- name: Testing disable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: no
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is disabled
assert:
that:
- result is changed
- name: Testing disable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: no
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is disabled (verify not changed)
assert:
that:
- result is not changed
- name: Icmp block inversion enabled when icmp block inversion is falsy and state is disabled
block:
- name: Testing enable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: no
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is enabled
assert:
that:
- result is changed
- name: Testing enable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: no
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Icmp block inversion disabled when icmp block inversion is truthy and state is disabled
block:
- name: Testing disable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: yes
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is disabled
assert:
that:
- result is changed
- name: Testing disable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: yes
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is disabled (verify not changed)
assert:
that:
- result is not changed
# Validate backwards compatible behavior until icmp block inversion is switched from string to boolean type
- name: Icmp block inversion enabled when icmp block inversion is non-boolean string and state is enabled
block:
- name: Testing enable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: 'some string'
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is enabled
assert:
that:
- result is changed
- name: Testing enable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: 'some string'
permanent: yes
state: enabled
register: result
- name: assert icmp block inversion is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Icmp block inversion disabled when icmp block inversion is non-boolean string and state is disabled
block:
- name: Testing disable icmp block inversion
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: 'some string'
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is disabled
assert:
that:
- result is changed
- name: Testing disable icmp block inversion (verify not changed)
ansible.posix.firewalld:
zone: trusted
icmp_block_inversion: 'some string'
permanent: yes
state: disabled
register: result
- name: assert icmp block inversion is disabled (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,87 @@
# Test playbook for the firewalld module - interface operations
# (c) 2022, Gregory Furlong <gnfzdz@fzdz.io>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Validate adding interface
block:
- name: Add lo interface to trusted zone
ansible.posix.firewalld:
interface: lo
zone: trusted
permanent: Yes
state: enabled
register: result
- name: assert lo was added to trusted zone
assert:
that:
- result is changed
- name: Add lo interface to trusted zone (verify not changed)
ansible.posix.firewalld:
interface: lo
zone: trusted
permanent: Yes
state: enabled
register: result
- name: assert lo was added to trusted zone (verify not changed)
assert:
that:
- result is not changed
- name: Validate moving interfaces
block:
- name: Move lo interface from trusted zone to internal zone
ansible.posix.firewalld:
interface: lo
zone: internal
permanent: Yes
state: enabled
register: result
- name: Assert lo was moved from trusted zone to internal zone
assert:
that:
- result is changed
- name: Move lo interface from trusted zone to internal zone (verify not changed)
ansible.posix.firewalld:
interface: lo
zone: internal
permanent: Yes
state: enabled
register: result
- name: assert lo was moved from trusted zone to internal zone (verify not changed)
assert:
that:
- result is not changed
- name: Validate removing interface
block:
- name: Remove lo interface from internal zone
ansible.posix.firewalld:
interface: lo
zone: internal
permanent: Yes
state: disabled
register: result
- name: Assert lo interface was removed from internal zone
assert:
that:
- result is changed
- name: Remove lo interface from internal zone (verify not changed)
ansible.posix.firewalld:
interface: lo
zone: internal
permanent: Yes
state: disabled
register: result
- name: Assert lo interface was removed from internal zone (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,50 @@
# Test playbook for the firewalld module
# (c) 2017, Adam Miller <admiller@redhat.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Run firewalld tests
block:
- name: Ensure firewalld is installed
package:
name: firewalld
state: present
# This doesn't work for CentOS 6 because firewalld doesn't exist in CentOS6
- name: Check to make sure the firewalld python module is available.
shell: "{{ansible_python.executable}} -c 'import firewall'"
register: check_output
ignore_errors: true
- name: Enable dbus-broker daemon
service:
name: dbus-broker
enabled: true
state: started
when: (ansible_distribution == 'Fedora' and ansible_distribution_major_version is version('34', '=='))
- name: Test Online Operations
block:
- name: start firewalld
service:
name: firewalld
state: started
- import_tasks: run_all_tests.yml
when: check_output.rc == 0
- name: Test Offline Operations
block:
- name: stop firewalld
service:
name: firewalld
state: stopped
- import_tasks: run_all_tests.yml
when: check_output.rc == 0
when:
- ansible_facts.os_family == "RedHat" and ansible_facts.distribution_major_version is version('7', '>=')
- not (ansible_distribution == "Ubuntu" and ansible_distribution_version is version('14.04', '=='))
# Firewalld package on OpenSUSE (15+) require Python 3, so we skip on OpenSUSE running py2 on these newer distros
- not (ansible_os_family == "Suse" and ansible_distribution_major_version|int != 42 and ansible_python.version.major != 3)
- not (ansible_facts.distribution == "CentOS" and ansible_distribution_major_version is version('7', '==')) # FIXME

View File

@ -0,0 +1,172 @@
# Test playbook for the firewalld module - masquerade operations
# (c) 2022, Gregory Furlong <gnfzdz@fzdz.io>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Masquerade enabled when masquerade is truthy and state is enabled
block:
- name: Testing enable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: yes
permanent: yes
state: enabled
register: result
- name: assert masquerade is enabled
assert:
that:
- result is changed
- name: Testing enable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: yes
permanent: yes
state: enabled
register: result
- name: assert masquerade is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Masquerade disabled when masquerade is falsy and state is enabled
block:
- name: Testing disable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: no
permanent: yes
state: enabled
register: result
- name: assert masquerade is disabled
assert:
that:
- result is changed
- name: Testing disable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: no
permanent: yes
state: enabled
register: result
- name: assert masquerade is disabled (verify not changed)
assert:
that:
- result is not changed
- name: Masquerade enabled when masquerade is falsy and state is disabled
block:
- name: Testing enable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: no
permanent: yes
state: disabled
register: result
- name: assert masquerade is enabled
assert:
that:
- result is changed
- name: Testing enable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: no
permanent: yes
state: disabled
register: result
- name: assert masquerade is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Masquerade disabled when masquerade is truthy and state is disabled
block:
- name: Testing disable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: yes
permanent: yes
state: disabled
register: result
- name: assert masquerade is disabled
assert:
that:
- result is changed
- name: Testing disable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: yes
permanent: yes
state: disabled
register: result
- name: assert masquerade is disabled (verify not changed)
assert:
that:
- result is not changed
# Validate backwards compatible behavior until masquerade is switched from string to boolean type
- name: Masquerade enabled when masquerade is non-boolean string and state is enabled
block:
- name: Testing enable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: 'some string'
permanent: yes
state: enabled
register: result
- name: assert masquerade is enabled
assert:
that:
- result is changed
- name: Testing enable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: 'some string'
permanent: yes
state: enabled
register: result
- name: assert masquerade is enabled (verify not changed)
assert:
that:
- result is not changed
- name: Masquerade disabled when masquerade is non-boolean string and state is disabled
block:
- name: Testing disable masquerade
ansible.posix.firewalld:
zone: trusted
masquerade: 'some string'
permanent: yes
state: disabled
register: result
- name: assert masquerade is disabled
assert:
that:
- result is changed
- name: Testing disable masquerade (verify not changed)
ansible.posix.firewalld:
zone: trusted
masquerade: 'some string'
permanent: yes
state: disabled
register: result
- name: assert masquerade is disabled (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,63 @@
# Test playbook for the firewalld module - port operations
# (c) 2017, Adam Miller <admiller@redhat.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: firewalld port forward test permanent enabled
firewalld:
port_forward:
- port: 8080
proto: tcp
toport: 8081
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld port test permanent enabled rerun (verify not changed)
firewalld:
port_forward:
- port: 8080
proto: tcp
toport: 8081
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld port test permanent disabled
firewalld:
port_forward:
- port: 8080
proto: tcp
toport: 8081
permanent: true
state: disabled
register: result
- name: assert firewalld port test permanent disabled worked
assert:
that:
- result is changed
- name: firewalld port test permanent disabled rerun (verify not changed)
firewalld:
port_forward:
- port: 8080
proto: tcp
toport: 8081
permanent: true
state: disabled
register: result
- name: assert firewalld port test permanent disabled rerun worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,108 @@
# Test playbook for the firewalld module - port operations
# (c) 2017, Adam Miller <admiller@redhat.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: firewalld port range test permanent enabled
firewalld:
port: 5500-6850/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port range test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld port range test permanent enabled rerun (verify not changed)
firewalld:
port: 5500-6850/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port range test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld port test permanent enabled
firewalld:
port: 6900/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld port test permanent enabled
firewalld:
port: 6900/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled worked
assert:
that:
- result is not changed
- name: firewalld port test disabled
firewalld:
port: "{{ item }}"
permanent: true
state: disabled
loop:
- 6900/tcp
- 5500-6850/tcp
- name: firewalld port test permanent enabled
firewalld:
port: 8081/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld port test permanent enabled rerun (verify not changed)
firewalld:
port: 8081/tcp
permanent: true
state: enabled
register: result
- name: assert firewalld port test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld port test permanent disabled
firewalld:
port: 8081/tcp
permanent: true
state: disabled
register: result
- name: assert firewalld port test permanent disabled worked
assert:
that:
- result is changed
- name: firewalld port test permanent disabled rerun (verify not changed)
firewalld:
port: 8081/tcp
permanent: true
state: disabled
register: result
- name: assert firewalld port test permanent disabled rerun worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,65 @@
# Test playbook for the firewalld module - protocol operations
# (c) 2022, Robért S. Guhr <rguhr@cronon.net>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: firewalld protocol test permanent enabled
firewalld:
protocol: ospf
permanent: true
state: enabled
register: result
- name: assert firewalld protocol test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld protocol test permanent enabled rerun (verify not changed)
firewalld:
protocol: ospf
permanent: true
state: enabled
register: result
- name: assert firewalld protocol test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld protocol test permanent disabled
firewalld:
protocol: ospf
permanent: true
state: disabled
register: result
- name: assert firewalld protocol test permanent disabled worked
assert:
that:
- result is changed
- name: firewalld protocol test permanent disabled rerun (verify not changed)
firewalld:
protocol: ospf
permanent: true
state: disabled
register: result
- name: assert firewalld protocol test permanent disabled rerun worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,38 @@
# Test playbook for the firewalld module
# (c) 2017, Adam Miller <admiller@redhat.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Ensure /run/firewalld exists
file:
path: /run/firewalld
state: directory
# firewalld service operation test cases
- include_tasks: service_test_cases.yml
# firewalld protocol operation test cases
- include_tasks: protocol_test_cases.yml
# firewalld port operation test cases
- include_tasks: port_test_cases.yml
# firewalld source operation test cases
- include_tasks: source_test_cases.yml
# firewalld zone operation test cases
- include_tasks: zone_test_cases.yml
# firewalld zone target operation test cases
- include_tasks: zone_target_test_cases.yml
# firewalld port forwarding operation test cases
- include_tasks: port_forward_test_cases.yml
# firewalld masquerade operation test cases
- include_tasks: masquerade_test_cases.yml
# firewalld icmp block inversion operation test cases
- include_tasks: icmp_block_inversion_test_cases.yml
# firewalld interface operation test cases
- include_tasks: interface_test_cases.yml

View File

@ -0,0 +1,65 @@
# Test playbook for the firewalld module - service operations
# (c) 2017, Adam Miller <admiller@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: firewalld service test permanent enabled
firewalld:
service: https
permanent: true
state: enabled
register: result
- name: assert firewalld service test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld service test permanent enabled rerun (verify not changed)
firewalld:
service: https
permanent: true
state: enabled
register: result
- name: assert firewalld service test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld service test permanent disabled
firewalld:
service: https
permanent: true
state: disabled
register: result
- name: assert firewalld service test permanent disabled worked
assert:
that:
- result is changed
- name: firewalld service test permanent disabled rerun (verify not changed)
firewalld:
service: https
permanent: true
state: disabled
register: result
- name: assert firewalld service test permanent disabled rerun worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,85 @@
# Test playbook for the firewalld module - source operations
# (c) 2019, Hideki Saito <saito@fgrep.org>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: firewalld source test permanent enabled
firewalld:
source: 192.0.2.0/24
zone: internal
permanent: True
state: enabled
register: result
- name: assert firewalld source test permanent enabled worked
assert:
that:
- result is changed
- name: firewalld source test permanent enabled rerun (verify not changed)
firewalld:
source: 192.0.2.0/24
zone: internal
permanent: True
state: enabled
register: result
- name: assert firewalld source test permanent enabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld source test permanent disabled
firewalld:
source: 192.0.2.0/24
zone: internal
permanent: True
state: disabled
register: result
- name: assert firewalld source test permanent disabled worked
assert:
that:
- result is changed
- name: firewalld source test permanent disabled rerun (verify not changed)
firewalld:
source: 192.0.2.0/24
zone: internal
permanent: True
state: disabled
register: result
- name: assert firewalld source test permanent disabled rerun worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld source test permanent enabled is exclusive (verify exclusive error)
firewalld:
source: 192.0.2.0/24
port: 8081/tcp
zone: internal
permanent: True
state: enabled
register: result
ignore_errors: true
- name: assert firewalld source test permanent enabled is exclusive (verify exclusive error)
assert:
that:
- result is not changed
- "result.msg == 'parameters are mutually exclusive: icmp_block|icmp_block_inversion|service|protocol|port|port_forward|rich_rule|interface|masquerade|source|target'"

View File

@ -0,0 +1,121 @@
# Test playbook for the firewalld module - source operations
# (c) 2020, Adam Miller <admiller@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: firewalld dmz zone target DROP
firewalld:
zone: dmz
permanent: True
state: present
target: DROP
register: result
- name: assert firewalld dmz zone target DROP present worked
assert:
that:
- result is changed
- name: firewalld dmz zone target DROP rerun (verify not changed)
firewalld:
zone: dmz
permanent: True
state: present
target: DROP
register: result
- name: assert firewalld dmz zone target DROP present worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld dmz zone target DROP absent
firewalld:
zone: dmz
permanent: True
state: absent
target: DROP
register: result
- name: assert firewalld dmz zone target DROP absent worked
assert:
that:
- result is changed
- name: firewalld dmz zone target DROP rerun (verify not changed)
firewalld:
zone: dmz
permanent: True
state: absent
target: DROP
register: result
- name: assert firewalld dmz zone target DROP present worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld dmz zone target %%REJECT%%
firewalld:
zone: dmz
permanent: True
state: present
target: '%%REJECT%%'
register: result
- name: assert firewalld dmz zone target %%REJECT%% present worked
assert:
that:
- result is changed
- name: firewalld dmz zone target %%REJECT%% rerun (verify not changed)
firewalld:
zone: dmz
permanent: True
state: present
target: '%%REJECT%%'
register: result
- name: assert firewalld dmz zone target %%REJECT%% present worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld dmz zone target %%REJECT%% absent
firewalld:
zone: dmz
permanent: True
state: absent
target: '%%REJECT%%'
register: result
- name: assert firewalld dmz zone target %%REJECT%% absent worked
assert:
that:
- result is changed
- name: firewalld dmz zone target %%REJECT%% rerun (verify not changed)
firewalld:
zone: dmz
permanent: True
state: absent
target: '%%REJECT%%'
register: result
- name: assert firewalld dmz zone target %%REJECT%% present worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,47 @@
- name: firewalld create zone custom
firewalld:
zone: custom
permanent: True
state: present
register: result
- name: assert firewalld custom zone created worked
assert:
that:
- result is changed
- name: firewalld create zone custom rerun (verify not changed)
firewalld:
zone: custom
permanent: True
state: present
register: result
- name: assert firewalld custom zone created worked (verify not changed)
assert:
that:
- result is not changed
- name: firewalld remove zone custom
firewalld:
zone: custom
permanent: True
state: absent
register: result
- name: assert firewalld custom zone removed worked
assert:
that:
- result is changed
- name: firewalld remove custom zone rerun (verify not changed)
firewalld:
zone: custom
permanent: True
state: absent
register: result
- name: assert firewalld custom zone removed worked (verify not changed)
assert:
that:
- result is not changed

View File

@ -0,0 +1,5 @@
destructive
shippable/posix/group3
skip/aix
skip/freebsd
skip/osx

View File

@ -0,0 +1,52 @@
# Test playbook for the firewalld_info module
# (c) 2021, Hideki Saito <saito@fgrep.org>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
# This test is based on the integration test playbook for firewalld module.
- name: Run firewalld tests
block:
- name: Ensure firewalld is installed
package:
name: firewalld
state: present
# This doesn't work for CentOS 6 because firewalld doesn't exist in CentOS6
- name: Check to make sure the firewalld python module is available.
shell: "{{ansible_python.executable}} -c 'import firewall'"
register: check_output_firewall
ignore_errors: true
- name: Check to make sure the dbus python module is available.
shell: "{{ansible_python.executable}} -c 'import dbus'"
register: check_output_dbus
ignore_errors: true
- name: Test Online Operations
block:
- name: start firewalld
service:
name: firewalld
state: started
- import_tasks: run_tests_in_started.yml
when:
- check_output_firewall.rc == 0
- check_output_dbus.rc == 0
- name: Test Offline Operations
block:
- name: stop firewalld
service:
name: firewalld
state: stopped
- import_tasks: run_tests_in_stopped.yml
when:
- check_output_firewall.rc == 0
- check_output_dbus.rc == 0
when:
- ansible_facts.os_family == "RedHat" and ansible_facts.distribution_major_version is version('7', '>=')
- not (ansible_distribution == "Ubuntu" and ansible_distribution_version is version('14.04', '=='))
# Firewalld package on OpenSUSE (15+) require Python 3, so we skip on OpenSUSE running py2 on these newer distros
- not (ansible_os_family == "Suse" and ansible_distribution_major_version|int != 42 and ansible_python.version.major != 3)

View File

@ -0,0 +1,32 @@
# Test playbook for the firewalld_info module
# (c) 2021, Hideki Saito <saito@fgrep.org>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Ensure firewalld_info without options
firewalld_info:
register: result
- name: Assert collected_zones and undefined_zones
assert:
that:
- 'result.collected_zones and not result.undefined_zones'
- name: Ensure firewalld_info with active_zones
firewalld_info:
active_zones: yes
register: result
- name: Assert turn active_zones true
assert:
that:
- name: Ensure firewalld_zones with zone list
firewalld_info:
zones:
- public
- invalid_zone
register: result
- name: Assert specified zones
assert:
that:

View File

@ -0,0 +1,40 @@
# Test playbook for the firewalld_info module
# (c) 2021, Hideki Saito <saito@fgrep.org>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
- name: Ensure firewalld_info without options
firewalld_info:
register: result
ignore_errors: yes
- name: Assert firewalld_info fails if firewalld is not running.
assert:
that:
- result.failed
- "'firewalld probably not be running,' in result.msg"
- name: Ensure firewalld_info with active_zones
firewalld_info:
active_zones: yes
register: result
ignore_errors: yes
- name: Assert firewalld_info with active_zones fails if firewalld is not running.
assert:
that:
- result.failed
- "'firewalld probably not be running,' in result.msg"
- name: Ensure firewalld_zones with zone list
firewalld_info:
zones:
- public
- invalid_zone
register: result
ignore_errors: yes
- name: Assert firewalld_info with zones list fails if firewalld is not running.
assert:
that:
- result.failed
- "'firewalld probably not be running,' in result.msg"

View File

@ -0,0 +1,4 @@
needs/privileged
needs/root
shippable/posix/group1
skip/aix

View File

@ -0,0 +1,681 @@
- name: Install dependencies
ansible.builtin.package:
name: e2fsprogs
state: present
when: ansible_system == 'Linux'
- name: Create the mount point
file:
state: directory
path: '{{ output_dir }}/mount_dest'
- name: Create a directory to bind mount
file:
state: directory
path: '{{ output_dir }}/mount_source'
- name: Put something in the directory so we see that it worked
copy:
content: 'Testing
'
dest: '{{ output_dir }}/mount_source/test_file'
register: orig_info
- name: Bind mount a filesystem (Linux)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: None
opts: bind
when: ansible_system == 'Linux'
register: bind_result_linux
- name: Bind mount a filesystem (FreeBSD)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: nullfs
when: ansible_system == 'FreeBSD'
register: bind_result_freebsd
- name: get checksum for bind mounted file
stat:
path: '{{ output_dir }}/mount_dest/test_file'
when: ansible_system in ('FreeBSD', 'Linux')
register: dest_stat
- name: assert the bind mount was successful
assert:
that:
- (ansible_system == 'Linux' and bind_result_linux['changed']) or (ansible_system == 'FreeBSD' and bind_result_freebsd['changed'])
- dest_stat['stat']['exists']
- orig_info['checksum'] == dest_stat['stat']['checksum']
when: ansible_system in ('FreeBSD', 'Linux')
- name: Bind mount a filesystem (Linux)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: None
opts: bind
when: ansible_system == 'Linux'
register: bind_result_linux
- name: Bind mount a filesystem (FreeBSD)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: nullfs
when: ansible_system == 'FreeBSD'
register: bind_result_freebsd
- name: Make sure we didn't mount a second time
assert:
that:
- (ansible_system == 'Linux' and not bind_result_linux['changed']) or (ansible_system == 'FreeBSD' and not bind_result_freebsd['changed'])
when: ansible_system in ('FreeBSD', 'Linux')
- name: Remount filesystem with different opts (Linux)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: None
opts: bind,ro
when: ansible_system == 'Linux'
register: bind_result_linux
- name: Remount filesystem with different opts (FreeBSD)
mount:
src: '{{ output_dir }}/mount_source'
name: '{{ output_dir }}/mount_dest'
state: mounted
fstype: nullfs
opts: ro
when: ansible_system == 'FreeBSD'
register: bind_result_freebsd
- name: Get mount options
shell: mount | grep mount_dest | grep -E -w '(ro|read-only)' | wc -l
register: remount_options
- name: Make sure the filesystem now has the new opts
assert:
that:
- (ansible_system == 'Linux' and bind_result_linux['changed']) or (ansible_system == 'FreeBSD' and bind_result_freebsd['changed'])
- '''1'' in remount_options.stdout'
- 1 == remount_options.stdout_lines | length
when: ansible_system in ('FreeBSD', 'Linux')
- name: Unmount the bind mount
mount:
name: '{{ output_dir }}/mount_dest'
state: absent
when: ansible_system in ('Linux', 'FreeBSD')
register: unmount_result
- name: Make sure the file no longer exists in dest
stat:
path: '{{ output_dir }}/mount_dest/test_file'
when: ansible_system in ('FreeBSD', 'Linux')
register: dest_stat
- name: Check that we unmounted
assert:
that:
- unmount_result['changed']
- not dest_stat['stat']['exists']
when: ansible_system in ('FreeBSD', 'Linux')
- name: Block to test remounted option
block:
- name: Create fstab record for the first swap file
mount:
name: none
src: /tmp/swap1
opts: sw
fstype: swap
state: present
register: swap1_created
- name: Try to create fstab record for the first swap file again
mount:
name: none
src: /tmp/swap1
opts: sw
fstype: swap
state: present
register: swap1_created_again
- name: Check that we created the swap1 record
assert:
that:
- swap1_created['changed']
- not swap1_created_again['changed']
- name: Create fstab record for the second swap file
mount:
name: none
src: /tmp/swap2
opts: sw
fstype: swap
state: present
register: swap2_created
- name: Try to create fstab record for the second swap file again
mount:
name: none
src: /tmp/swap1
opts: sw
fstype: swap
state: present
register: swap2_created_again
- name: Check that we created the swap2 record
assert:
that:
- swap2_created['changed']
- not swap2_created_again['changed']
- name: Remove the fstab record for the first swap file
mount:
name: none
src: /tmp/swap1
state: absent
register: swap1_removed
- name: Try to remove the fstab record for the first swap file again
mount:
name: none
src: /tmp/swap1
state: absent
register: swap1_removed_again
- name: Check that we removed the swap1 record
assert:
that:
- swap1_removed['changed']
- not swap1_removed_again['changed']
- name: Remove the fstab record for the second swap file
mount:
name: none
src: /tmp/swap2
state: absent
register: swap2_removed
- name: Try to remove the fstab record for the second swap file again
mount:
name: none
src: /tmp/swap2
state: absent
register: swap2_removed_again
- name: Check that we removed the swap2 record
assert:
that:
- swap2_removed['changed']
- not swap2_removed_again['changed']
- name: Create fstab record with missing last two fields
copy:
dest: /etc/fstab
content: '//nas/photo /home/jik/pictures cifs defaults,credentials=/etc/security/nas.creds,uid=jik,gid=users,forceuid,forcegid,noserverino,_netdev
'
- name: Try to change the fstab record with the missing last two fields
mount:
src: //nas/photo
path: /home/jik/pictures
fstype: cifs
opts: defaults,credentials=/etc/security/nas.creds,uid=jik,gid=users,forceuid,forcegid,noserverino,_netdev,x-systemd.mount-timeout=0
state: present
register: optional_fields_update
- name: Get the content of the fstab file
shell: cat /etc/fstab
register: optional_fields_content
- name: Check if the line containing the missing last two fields was changed
assert:
that:
- optional_fields_update['changed']
- ''' 0 0'' in optional_fields_content.stdout'
- 1 == optional_fields_content.stdout_lines | length
- name: Create empty file
community.general.filesize:
path: /tmp/myfs.img
size: 20M
- name: Format FS
community.general.filesystem:
fstype: ext3
dev: /tmp/myfs.img
- name: Mount the FS for the first time
mount:
path: /tmp/myfs
src: /tmp/myfs.img
fstype: ext2
state: mounted
- name: Get the last write time
shell: 'dumpe2fs /tmp/myfs.img 2>/dev/null | grep -i last write time: |cut -d: -f2-'
register: last_write_time
- name: Wait 2 second
pause:
seconds: 2
- name: Test if the FS is remounted
mount:
path: /tmp/myfs
state: remounted
- name: Get again the last write time
shell: 'dumpe2fs /tmp/myfs.img 2>/dev/null | grep -i last write time: |cut -d: -f2-'
register: last_write_time2
- name: Fail if they are the same
fail:
msg: Filesytem was not remounted, testing of the module failed!
when: last_write is defined and last_write_time2 is defined and last_write_time.stdout == last_write_time2.stdout
- name: Remount filesystem with different opts using remounted option (Linux only)
mount:
path: /tmp/myfs
state: remounted
opts: rw,noexec
- name: Get remounted options (Linux only)
shell: mount | grep myfs | grep -E -w 'noexec' | wc -l
register: remounted_options
- name: Make sure the filesystem now has the new opts after using remounted (Linux only)
assert:
that:
- "'1' in remounted_options.stdout"
- "1 == remounted_options.stdout_lines | length"
- name: Mount the FS again to test backup
mount:
path: /tmp/myfs
src: /tmp/myfs.img
fstype: ext2
state: mounted
backup: yes
register: mount_backup_out
- name: ensure backup_file in returned output
assert:
that:
- "'backup_file' in mount_backup_out"
always:
- name: Umount the test FS
mount:
path: /tmp/myfs
src: /tmp/myfs.img
opts: loop
state: absent
- name: Remove the test FS
file:
path: '{{ item }}'
state: absent
loop:
- /tmp/myfs.img
- /tmp/myfs
when: ansible_system in ('Linux')
- name: Block to test boot option for Linux
block:
- name: Create empty file
community.general.filesize:
path: /tmp/myfs.img
size: 20M
- name: Format FS
community.general.filesystem:
fstype: ext3
dev: /tmp/myfs.img
- name: Mount the FS with noauto option
mount:
path: /tmp/myfs
src: /tmp/myfs.img
fstype: ext3
state: mounted
boot: no
opts: rw,user,async
register: mount_info
- name: assert the mount without noauto was successful
assert:
that:
- mount_info['opts'] == 'rw,user,async,noauto'
- name: Unmount FS
mount:
path: /tmp/myfs
state: absent
- name: Remove the test FS
file:
path: '{{ item }}'
state: absent
loop:
- /tmp/myfs.img
- /tmp/myfs
when: ansible_system in ('Linux')
- name: Block to test missing newline at the EOF of fstab
block:
- name: Create empty file
community.general.filesize:
path: /tmp/myfs1.img
size: 20M
- name: Format FS
community.general.filesystem:
fstype: ext3
dev: /tmp/myfs1.img
- name: Create custom fstab file without newline
copy:
content: '#TEST COMMENT WITHOUT NEWLINE'
dest: /tmp/test_fstab
- name: Mount the FS using the custom fstab
mount:
path: /tmp/myfs1
src: /tmp/myfs1.img
fstype: ext3
state: mounted
opts: defaults
fstab: /tmp/test_fstab
- name: Unmount the mount point in the custom fstab
mount:
path: /tmp/myfs1
state: absent
fstab: /tmp/test_fstab
- name: Remove the test FS and the custom fstab
file:
path: '{{ item }}'
state: absent
loop:
- /tmp/myfs1.img
- /tmp/myfs1
- /tmp/test_fstab
when: ansible_system in ('Linux')
- name: Block to test ephemeral option
environment:
PATH: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
block:
- name: Create empty file A
community.general.filesize:
path: /tmp/myfs_A.img
size: 20M
- name: Create empty file B
community.general.filesize:
path: /tmp/myfs_B.img
size: 20M
- name: Register facts on Linux
ansible.builtin.set_fact:
ephemeral_device_A: /tmp/myfs_A.img
ephemeral_device_B: /tmp/myfs_B.img
ephemeral_fstype: ext3
ephemeral_fstab: /etc/fstab
when: ansible_system == 'Linux'
- name: Register facts on Solaris/SunOS
ansible.builtin.set_fact:
ephemeral_device_A: /dev/lofi/1
ephemeral_device_B: /dev/lofi/2
ephemeral_create_loop_dev_cmd: >
lofiadm -a /tmp/myfs_A.img /dev/lofi/1 &&
lofiadm -a /tmp/myfs_B.img /dev/lofi/2
ephemeral_remove_loop_dev_cmd: >
lofiadm -d /dev/lofi/1 &&
lofiadm -d /dev/lofi/2 || true
ephemeral_fstype: ufs
ephemeral_fstab: /etc/vfstab
when: ansible_system == 'SunOS'
- name: Register facts on FreeBSD
ansible.builtin.set_fact:
ephemeral_device_A: /dev/md1
ephemeral_device_B: /dev/md2
ephemeral_create_loop_dev_cmd: >
mdconfig -a -t vnode -f /tmp/myfs_A.img -u /dev/md1 &&
mdconfig -a -t vnode -f /tmp/myfs_B.img -u /dev/md2
ephemeral_remove_loop_dev_cmd: >
mdconfig -d -u /dev/md1 &&
mdconfig -d -u /dev/md2
ephemeral_fstype: ufs
ephemeral_fstab: /etc/fstab
when: ansible_system == 'FreeBSD'
- name: Register facts on NetBSD
ansible.builtin.set_fact:
ephemeral_device_A: /dev/vnd1
ephemeral_device_B: /dev/vnd2
ephemeral_create_loop_dev_cmd: >
vnconfig /dev/vnd1 /tmp/myfs_A.img &&
vnconfig /dev/vnd2 /tmp/myfs_B.img
ephemeral_remove_loop_dev_cmd: >
vnconfig -u /dev/vnd1 &&
vnconfig -u /dev/vnd2
ephemeral_fstype: ufs
ephemeral_fstab: /etc/fstab
when: ansible_system == 'NetBSD'
- name: Register format fs command on Non-Linux and Non-OpenBSD
ansible.builtin.set_fact:
ephemeral_format_fs_cmd: >
yes | newfs {{ ephemeral_device_A }} &&
yes | newfs {{ ephemeral_device_B }}
when: ansible_system in ('SunOS', 'FreeBSD', 'NetBSD')
- name: Register facts on OpenBSD
ansible.builtin.set_fact:
ephemeral_device_A: /dev/vnd1c
ephemeral_device_B: /dev/vnd2c
ephemeral_create_loop_dev_cmd: >
vnconfig vnd1 /tmp/myfs_A.img &&
vnconfig vnd2 /tmp/myfs_B.img
ephemeral_remove_loop_dev_cmd: >
vnconfig -u vnd1 &&
vnconfig -u vnd2
ephemeral_format_fs_cmd: >
yes | newfs /dev/rvnd1c &&
yes | newfs /dev/rvnd2c
ephemeral_fstype: ffs
ephemeral_fstab: /etc/fstab
when: ansible_system == 'OpenBSD'
##### FORMAT FS ON LINUX
- name: Block to format FS on Linux
block:
- name: Format FS A on Linux
community.general.filesystem:
fstype: ext3
dev: /tmp/myfs_A.img
- name: Format FS B on Linux
community.general.filesystem:
fstype: ext3
dev: /tmp/myfs_B.img
when: ansible_system == 'Linux'
##### FORMAT FS ON SOLARIS AND BSD
- name: Create loop devices on Solaris and BSD
ansible.builtin.shell: "{{ ephemeral_create_loop_dev_cmd }}"
when: ephemeral_create_loop_dev_cmd is defined
- name: Format FS A and B on Solaris and BSD
ansible.builtin.shell: "{{ ephemeral_format_fs_cmd }}"
when: ephemeral_format_fs_cmd is defined
##### TESTS
- name: Create fstab if it does not exist
ansible.builtin.file:
path: "{{ ephemeral_fstab }}"
state: touch
- name: Get checksum of /etc/fstab before mounting anything
stat:
path: '{{ ephemeral_fstab }}'
register: fstab_stat_before_mount
- name: Mount the FS A with ephemeral state
mount:
path: /tmp/myfs
src: '{{ ephemeral_device_A }}'
fstype: '{{ ephemeral_fstype }}'
opts: rw
state: ephemeral
register: ephemeral_mount_info
- name: Put something in the directory so we can do additional checks later on
copy:
content: 'Testing'
dest: /tmp/myfs/test_file
- name: Get checksum of /etc/fstab after an ephemeral mount
stat:
path: '{{ ephemeral_fstab }}'
register: fstab_stat_after_mount
- name: Get mountinfo
shell: mount -v | awk '{print $3}' | grep '^/tmp/myfs$' | wc -l
register: check_mountinfo
changed_when: no
- name: Assert the mount occured and the fstab is unchanged
assert:
that:
- check_mountinfo.stdout|int == 1
- ephemeral_mount_info['changed']
- fstab_stat_before_mount['stat']['checksum'] == fstab_stat_after_mount['stat']['checksum']
- name: Get first mount record
shell: mount -v | grep '/tmp/myfs'
register: ephemeral_mount_record_1
changed_when: no
- name: Try to mount FS A where FS A is already mounted (should trigger remount and changed)
mount:
path: /tmp/myfs
src: '{{ ephemeral_device_A }}'
fstype: '{{ ephemeral_fstype }}'
opts: ro
state: ephemeral
register: ephemeral_mount_info
- name: Get second mount record (should be different than the first)
shell: mount -v | grep '/tmp/myfs'
register: ephemeral_mount_record_2
changed_when: no
- name: Get mountinfo
shell: mount -v | awk '{print $3}' | grep '^/tmp/myfs$' | wc -l
register: check_mountinfo
changed_when: no
- name: Assert the FS A is still mounted, the options changed and the fstab unchanged
assert:
that:
- check_mountinfo.stdout|int == 1
- ephemeral_mount_record_1.stdout != ephemeral_mount_record_2.stdout
- ephemeral_mount_info['changed']
- fstab_stat_before_mount['stat']['checksum'] == fstab_stat_after_mount['stat']['checksum']
- name: Try to mount file B on file A mountpoint (should fail)
mount:
path: /tmp/myfs
src: '{{ ephemeral_device_B }}'
fstype: '{{ ephemeral_fstype }}'
state: ephemeral
register: ephemeral_mount_b_info
ignore_errors: true
- name: Get third mount record (should be the same than the second)
shell: mount -v | grep '/tmp/myfs'
register: ephemeral_mount_record_3
changed_when: no
- name: Get mountinfo
shell: mount -v | awk '{print $3}' | grep '^/tmp/myfs$' | wc -l
register: check_mountinfo
changed_when: no
- name: Try to stat our test file
stat:
path: /tmp/myfs/test_file
register: test_file_stat
- name: Assert that mounting FS B over FS A failed
assert:
that:
- check_mountinfo.stdout|int == 1
- ephemeral_mount_record_2.stdout == ephemeral_mount_record_3.stdout
- test_file_stat['stat']['exists']
- ephemeral_mount_b_info is failed
- name: Unmount FS with state = unmounted
mount:
path: /tmp/myfs
state: unmounted
- name: Get fstab checksum after unmounting an ephemeral mount with state = unmounted
stat:
path: '{{ ephemeral_fstab }}'
register: fstab_stat_after_unmount
- name: Get mountinfo
shell: mount -v | awk '{print $3}' | grep '^/tmp/myfs$' | wc -l
register: check_mountinfo
changed_when: no
- name: Try to stat our test file
stat:
path: /tmp/myfs/test_file
register: test_file_stat
- name: Assert that fstab is unchanged after unmounting an ephemeral mount with state = unmounted
assert:
that:
- check_mountinfo.stdout|int == 0
- not test_file_stat['stat']['exists']
- fstab_stat_before_mount['stat']['checksum'] == fstab_stat_after_unmount['stat']['checksum']
always:
- name: Unmount potential failure relicas
mount:
path: /tmp/myfs
state: unmounted
- name: Remove loop devices on Solaris and BSD
ansible.builtin.shell: "{{ ephemeral_remove_loop_dev_cmd }}"
when: ephemeral_remove_loop_dev_cmd is defined
- name: Remove the test FS
file:
path: '{{ item }}'
state: absent
loop:
- /tmp/myfs_A.img
- /tmp/myfs_B.img
- /tmp/myfs
when: ansible_system in ('Linux', 'SunOS', 'FreeBSD', 'NetBSD', 'OpenBSD')

View File

@ -0,0 +1,4 @@
destructive
shippable/posix/group1
skip/aix
disabled # fixme package

View File

@ -0,0 +1,19 @@
Stet clita kasd gubergren,no sea takimata sanctus est Lorem ipsum dolor
sit amet.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
vero eos et accusam et justo duo dolores et ea rebum.
Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
sit amet.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
vero eos et accusam et justo duo dolores et ea rebum.
Stet clita kasd gubergren,no sea takimata sanctus est Lorem ipsum dolor
sit amet.

View File

@ -0,0 +1,24 @@
--- origin.txt 2018-05-12 10:22:14.155109584 +0200
+++ result.txt 2018-05-12 10:18:07.230811204 +0200
@@ -2,18 +2,12 @@
sit amet.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
-tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
-vero eos et accusam et justo duo dolores et ea rebum.
-
-Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
-sit amet.
-
-Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
-tempor invidunt ut labore et dolore magna aliquyam erat.
+tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua.
+At vero eos et accusam et justo duo dolores et ea rebum.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
vero eos et accusam et justo duo dolores et ea rebum.
-Stet clita kasd gubergren,no sea takimata sanctus est Lorem ipsum dolor
+Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
sit amet.

View File

@ -0,0 +1,13 @@
Stet clita kasd gubergren,no sea takimata sanctus est Lorem ipsum dolor
sit amet.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua.
At vero eos et accusam et justo duo dolores et ea rebum.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
vero eos et accusam et justo duo dolores et ea rebum.
Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
sit amet.

View File

@ -0,0 +1,24 @@
--- origin.txt 2018-05-12 10:22:14.155109584 +0200
+++ result.txt 2018-05-12 10:18:07.230811204 +0200
@@ -2,18 +2,12 @@
sit amet.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
-tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
-vero eos et accusam et justo duo dolores et ea rebum.
-
-Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
-sit amet.
-
-Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
-tempor invidunt ut labore et dolore magna aliquyam erat.
+tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua.
+At vero eos et accusam et justo duo dolores et ea rebum.
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod
tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At
vero eos et accusam et justo duo dolores et ea rebum.
-Stet clita kasd gubergren,no sea takimata sanctus est Lorem ipsum dolor
+Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor
sit amet.

View File

@ -0,0 +1,3 @@
---
dependencies:
- prepare_tests

View File

@ -0,0 +1,124 @@
- name: ensure idempotency installed
package:
name: patch
when: ansible_distribution != "MacOSX"
- name: create a directory for the result
file:
dest: '{{ output_dir }}/patch'
state: directory
register: result
- name: assert the directory was created
assert:
that:
- result.state == 'directory'
- name: copy the origin file
copy:
src: ./origin.txt
dest: '{{ output_dir }}/patch/workfile.txt'
register: result
- name: patch the origin file in check mode
check_mode: true
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
- name: verify patch the origin file in check mode
assert:
that:
- result is changed
- name: patch the origin file
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
- name: verify patch the origin file
assert:
that:
- result is changed
- name: test patch the origin file idempotency
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
- name: verify test patch the origin file idempotency
assert:
that:
- result is not changed
- name: verify the resulted file matches expectations
copy:
src: ./result.txt
dest: '{{ output_dir }}/patch/workfile.txt'
register: result
failed_when: result is changed
- name: patch the workfile file in check mode state absent
check_mode: true
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
state: absent
- name: verify patch the workfile file in check mode state absent
assert:
that:
- result is changed
- name: patch the workfile file state absent
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
state: absent
- name: verify patch the workfile file state absent
assert:
that:
- result is changed
- name: patch the workfile file state absent idempotency
register: result
patch:
src: result.patch
dest: '{{ output_dir }}/patch/workfile.txt'
state: absent
- name: verify patch the workfile file state absent idempotency
assert:
that:
- result is not changed
- name: verify the resulted file matches expectations
copy:
src: ./origin.txt
dest: '{{ output_dir }}/patch/workfile.txt'
register: result
failed_when: result is changed
- name: copy the origin file whitespace
copy:
src: ./origin.txt
dest: '{{ output_dir }}/patch/workfile_whitespace.txt'
register: result
- name: patch the origin file
register: result
patch:
src: result_whitespace.patch
dest: '{{ output_dir }}/patch/workfile_whitespace.txt'
ignore_whitespace: yes
- name: verify patch the origin file
assert:
that:
- result is changed
- name: test patch the origin file idempotency
register: result
patch:
src: result_whitespace.patch
dest: '{{ output_dir }}/patch/workfile_whitespace.txt'
ignore_whitespace: yes
- name: verify test patch the origin file idempotency
assert:
that:
- result is not changed
- name: verify the resulted file matches expectations
copy:
src: ./result_whitespace.txt
dest: '{{ output_dir }}/patch/workfile_whitespace.txt'
register: result
failed_when: result is changed

View File

@ -0,0 +1,3 @@
needs/root
shippable/posix/group1
skip/aix

View File

@ -0,0 +1,22 @@
# (c) 2017, Martin Krizek <mkrizek@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- include: seboolean.yml
when:
- ansible_selinux is defined
- ansible_selinux != False
- ansible_selinux.status == 'enabled'

View File

@ -0,0 +1,86 @@
# (c) 2017, Martin Krizek <mkrizek@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- name: install requirements for RHEL 7 and earlier
package:
name: policycoreutils-python
when:
- ansible_distribution == 'RedHat' and ansible_distribution_major_version is version('7', '<=')
- name: install requirements for RHEL 8 and later
package:
name: policycoreutils-python-utils
when:
- ansible_distribution == 'RedHat' and ansible_distribution_major_version is version('8', '>=')
- name: Cleanup
shell: setsebool -P httpd_can_network_connect 0
##########################################################################################
- name: set flag and don't keep it persistent
seboolean:
name: httpd_can_network_connect
state: yes
register: output
- name: get getsebool output
shell: semanage boolean -l | grep 'httpd_can_network_connect\W'
register: getsebool_output
- name: check output
assert:
that:
- output is changed
- output is not failed
- output.name == 'httpd_can_network_connect'
- getsebool_output.stdout.startswith('httpd_can_network_connect (on , off)')
##########################################################################################
- name: unset flag
seboolean:
name: httpd_can_network_connect
state: no
- name: get getsebool output
shell: semanage boolean -l | grep 'httpd_can_network_connect\W'
register: getsebool_output
- name: check output
assert:
that:
- output is changed
- output is not failed
- output.name == 'httpd_can_network_connect'
- getsebool_output.stdout.startswith('httpd_can_network_connect (off , off)')
##########################################################################################
- name: set flag and keep it persistent
seboolean:
name: httpd_can_network_connect
state: yes
persistent: yes
register: output
- name: get getsebool output
shell: semanage boolean -l | grep 'httpd_can_network_connect\W'
register: getsebool_output
- name: check output
assert:
that:
- output is changed
- output is not failed
- output.name == 'httpd_can_network_connect'
- getsebool_output.stdout.startswith('httpd_can_network_connect (on , on)')
##########################################################################################

View File

@ -0,0 +1,3 @@
needs/root
shippable/posix/group1
skip/aix

View File

@ -0,0 +1,36 @@
# (c) 2017, Sam Doran <sdoran@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
- debug:
msg: SELinux is disabled
when: ansible_selinux is defined and ansible_selinux == False
- debug:
msg: SELinux is {{ ansible_selinux.status }}
when: ansible_selinux is defined and ansible_selinux != False
- include: selinux.yml
when:
- ansible_selinux is defined
- ansible_selinux != False
- ansible_selinux.status == 'enabled'
- include: selogin.yml
when:
- ansible_selinux is defined
- ansible_selinux != False
- ansible_selinux.status == 'enabled'

View File

@ -0,0 +1,521 @@
# (c) 2017, Sam Doran <sdoran@redhat.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# First Test
# ##############################################################################
# Test changing the state, which requires a reboot
- name: TEST 1 | Make sure grubby is present
package:
name: grubby
state: present
- name: TEST 1 | Get current SELinux config file contents
slurp:
src: /etc/sysconfig/selinux
register: selinux_config_original_base64
- name: TEST 1 | Register SELinux config and SELinux status
set_fact:
selinux_config_original_raw: "{{ selinux_config_original_base64.content | b64decode }}"
before_test_sestatus: "{{ ansible_selinux }}"
- name: TEST 1 | Split by line and register original config
set_fact:
selinux_config_original: "{{ selinux_config_original_raw.split('\n') }}"
- debug:
var: "{{ item }}"
verbosity: 1
with_items:
- selinux_config_original
- before_test_sestatus
- ansible_selinux
- name: TEST 1 | Setup SELinux configuration for tests
selinux:
state: enforcing
policy: targeted
- name: TEST 1 | Disable SELinux
selinux:
state: disabled
policy: targeted
register: _disable_test1
- debug:
var: _disable_test1
verbosity: 1
- name: Before gathering the fact
debug:
msg: "{{ ansible_selinux }}"
- name: TEST 1 | Re-gather facts
setup:
- name: After gathering the fact
debug:
msg: "{{ ansible_selinux }}"
- name: TEST 1 | Assert that status was changed, reboot_required is True, a warning was displayed, and SELinux is configured properly
assert:
that:
- _disable_test1 is changed
- _disable_test1.reboot_required
- (_disable_test1.warnings | length ) >= 1
- ansible_selinux.config_mode == 'disabled'
- ansible_selinux.type == 'targeted'
- debug:
var: ansible_selinux
verbosity: 1
- name: TEST 1 | Disable SELinux again
selinux:
state: disabled
policy: targeted
register: _disable_test2
- debug:
var: _disable_test2
verbosity: 1
- name: TEST 1 | Assert that no change is reported, a warning was displayed, and reboot_required is True
assert:
that:
- _disable_test2 is not changed
- (_disable_test1.warnings | length ) >= 1
- _disable_test2.reboot_required
- name: TEST 1 | Get modified config file
slurp:
src: /etc/sysconfig/selinux
register: selinux_config_after_base64
- name: TEST 1 | Register modified config
set_fact:
selinux_config_after_raw: "{{ selinux_config_after_base64.content | b64decode }}"
- name: TEST 1 | Split by line and register modified config
set_fact:
selinux_config_after: "{{ selinux_config_after_raw.split('\n') }}"
- debug:
var: selinux_config_after
verbosity: 1
- name: TEST 1 | Ensure SELinux config file is properly formatted
assert:
that:
- selinux_config_original | length == selinux_config_after | length
- selinux_config_after[selinux_config_after.index('SELINUX=disabled')] is search("^SELINUX=\w+$")
- selinux_config_after[selinux_config_after.index('SELINUXTYPE=targeted')] is search("^SELINUXTYPE=\w+$")
- name: TEST 1 | Disable SELinux again, with kernel arguments update
selinux:
state: disabled
policy: targeted
update_kernel_param: true
register: _disable_test2
- name: Check kernel command-line arguments
ansible.builtin.command: grubby --info=DEFAULT
register: _grubby_test1
- name: TEST 1 | Assert that kernel cmdline contains selinux=0
assert:
that:
- "' selinux=0' in _grubby_test1.stdout"
- name: TEST 1 | Enable SELinux, without kernel arguments update
selinux:
state: disabled
policy: targeted
register: _disable_test2
- name: Check kernel command-line arguments
ansible.builtin.command: grubby --info=DEFAULT
register: _grubby_test1
- name: TEST 1 | Assert that kernel cmdline still contains selinux=0
assert:
that:
- "' selinux=0' in _grubby_test1.stdout"
- name: TEST 1 | Reset SELinux configuration for next test (also kernel args)
selinux:
state: enforcing
update_kernel_param: true
policy: targeted
- name: Check kernel command-line arguments
ansible.builtin.command: grubby --info=DEFAULT
register: _grubby_test2
- name: TEST 1 | Assert that kernel cmdline doesn't contain selinux=0
assert:
that:
- "' selinux=0' not in _grubby_test2.stdout"
# Second Test
# ##############################################################################
# Test changing only the policy, which does not require a reboot
- name: TEST 2 | Make sure the policy is present
package:
name: selinux-policy-mls
state: present
- name: TEST 2 | Set SELinux policy
selinux:
state: enforcing
policy: mls
register: _state_test1
- debug:
var: _state_test1
verbosity: 1
- name: TEST 2 | Re-gather facts
setup:
- debug:
var: ansible_selinux
tags: debug
- name: TEST 2 | Assert that status was changed, reboot_required is False, no warnings were displayed, and SELinux is configured properly
assert:
that:
- _state_test1 is changed
- not _state_test1.reboot_required
- _state_test1.warnings is not defined
- ansible_selinux.config_mode == 'enforcing'
- ansible_selinux.type == 'mls'
- name: TEST 2 | Set SELinux policy again
selinux:
state: enforcing
policy: mls
register: _state_test2
- debug:
var: _state_test2
verbosity: 1
- name: TEST 2 | Assert that no change was reported, no warnings were displayed, and reboot_required is False
assert:
that:
- _state_test2 is not changed
- _state_test2.warnings is not defined
- not _state_test2.reboot_required
- name: TEST 2 | Get modified config file
slurp:
src: /etc/sysconfig/selinux
register: selinux_config_after_base64
- name: TEST 2 | Register modified config
set_fact:
selinux_config_after_raw: "{{ selinux_config_after_base64.content | b64decode }}"
- name: TEST 2 | Split by line and register modified config
set_fact:
selinux_config_after: "{{ selinux_config_after_raw.split('\n') }}"
- debug:
var: selinux_config_after
verbosity: 1
- name: TEST 2 | Ensure SELinux config file is properly formatted
assert:
that:
- selinux_config_original | length == selinux_config_after | length
- selinux_config_after[selinux_config_after.index('SELINUX=enforcing')] is search("^SELINUX=\w+$")
- selinux_config_after[selinux_config_after.index('SELINUXTYPE=mls')] is search("^SELINUXTYPE=\w+$")
- name: TEST 2 | Reset SELinux configuration for next test
selinux:
state: enforcing
policy: targeted
# Third Test
# ##############################################################################
# Test changing non-existing policy
- name: TEST 3 | Set SELinux policy
selinux:
state: enforcing
policy: non-existing-selinux-policy
register: _state_test1
ignore_errors: yes
- debug:
var: _state_test1
verbosity: 1
- name: TEST 3 | Re-gather facts
setup:
- debug:
var: ansible_selinux
tags: debug
- name: TEST 3 | Assert that status was not changed, the task failed, the msg contains proper information and SELinux was not changed
assert:
that:
- _state_test1 is not changed
- _state_test1 is failed
- _state_test1.msg == 'Policy non-existing-selinux-policy does not exist in /etc/selinux/'
- ansible_selinux.config_mode == 'enforcing'
- ansible_selinux.type == 'targeted'
# Fourth Test
# ##############################################################################
# Test if check mode returns correct changed values and
# doesn't make any changes
- name: TEST 4 | Set SELinux to enforcing
selinux:
state: enforcing
policy: targeted
register: _check_mode_test1
- debug:
var: _check_mode_test1
verbosity: 1
- name: TEST 4 | Set SELinux to enforcing in check mode
selinux:
state: enforcing
policy: targeted
register: _check_mode_test1
check_mode: yes
- name: TEST 4 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
tags: debug
- name: TEST 4 | Assert that check mode is idempotent
assert:
that:
- _check_mode_test1 is success
- not _check_mode_test1.reboot_required
- ansible_selinux.config_mode == 'enforcing'
- ansible_selinux.type == 'targeted'
- name: TEST 4 | Set SELinux to permissive in check mode
selinux:
state: permissive
policy: targeted
register: _check_mode_test2
check_mode: yes
- name: TEST 4 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
tags: debug
- name: TEST 4 | Assert that check mode doesn't set state permissive and returns changed
assert:
that:
- _check_mode_test2 is changed
- not _check_mode_test2.reboot_required
- ansible_selinux.config_mode == 'enforcing'
- ansible_selinux.type == 'targeted'
- name: TEST 4 | Disable SELinux in check mode
selinux:
state: disabled
register: _check_mode_test3
check_mode: yes
- name: TEST 4 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
tags: debug
- name: TEST 4 | Assert that check mode didn't change anything, status is changed, reboot_required is True, a warning was displayed
assert:
that:
- _check_mode_test3 is changed
- _check_mode_test3.reboot_required
- (_check_mode_test3.warnings | length ) >= 1
- ansible_selinux.config_mode == 'enforcing'
- ansible_selinux.type == 'targeted'
- name: TEST 4 | Set SELinux to permissive
selinux:
state: permissive
policy: targeted
register: _check_mode_test4
- debug:
var: _check_mode_test4
verbosity: 1
- name: TEST 4 | Disable SELinux in check mode
selinux:
state: disabled
register: _check_mode_test4
check_mode: yes
- name: TEST 4 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
tags: debug
- name: TEST 4 | Assert that check mode didn't change anything, status is changed, reboot_required is True, a warning was displayed
assert:
that:
- _check_mode_test4 is changed
- _check_mode_test4.reboot_required
- (_check_mode_test3.warnings | length ) >= 1
- ansible_selinux.config_mode == 'permissive'
- ansible_selinux.type == 'targeted'
- name: TEST 4 | Set SELinux to enforcing
selinux:
state: enforcing
policy: targeted
register: _check_mode_test5
- debug:
var: _check_mode_test5
verbosity: 1
- name: TEST 4 | Disable SELinux
selinux:
state: disabled
register: _check_mode_test5
- name: TEST 4 | Disable SELinux in check mode
selinux:
state: disabled
register: _check_mode_test5
check_mode: yes
- name: TEST 4 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
tags: debug
- name: TEST 4 | Assert that in check mode status was not changed, reboot_required is True, a warning was displayed, and SELinux is configured properly
assert:
that:
- _check_mode_test5 is success
- _check_mode_test5.reboot_required
- (_check_mode_test5.warnings | length ) >= 1
- ansible_selinux.config_mode == 'disabled'
- ansible_selinux.type == 'targeted'
# Fifth Test
# ##############################################################################
# Remove SELINUX and SELINUXTYPE keys from /etc/selinux/config and make
# sure the module re-adds the expected lines
- name: TEST 5 | Remove SELINUX key from /etc/selinux/config
lineinfile:
path: /etc/selinux/config
regexp: '^SELINUX='
state: absent
backup: yes
register: _lineinfile_out1
- debug:
var: _lineinfile_out1
verbosity: 1
- name: TEST 5 | Set SELinux to enforcing
selinux:
state: enforcing
policy: targeted
register: _set_enforcing1
- name: TEST 5 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
- name: TEST 5 | Assert that SELINUX key is populated
assert:
that:
- _set_enforcing1 is success
- _set_enforcing1 is changed
- _set_enforcing1.state == 'enforcing'
- ansible_selinux.config_mode == 'enforcing'
- name: TEST 5 | Remove SELINUXTYPE key from /etc/selinux/config
lineinfile:
path: /etc/selinux/config
regexp: '^SELINUXTYPE='
state: absent
register: _lineinfile_out2
- debug:
var: _lineinfile_out2
verbosity: 1
- name: TEST 5 | Set SELinux Policy to targeted
selinux:
state: enforcing
policy: targeted
register: _set_policy2
- name: TEST 5 | Re-gather facts
setup:
- debug:
var: ansible_selinux
verbosity: 1
- name: TEST 5 | Assert that SELINUXTYPE key is populated
assert:
that:
- _set_policy2 is success
- _set_policy2 is changed
- _set_policy2.policy == 'targeted'
- ansible_selinux.type == 'targeted'
- name: TEST 5 | Restore original SELinux config file /etc/selinux/config
copy:
dest: /etc/selinux/config
src: "{{ _lineinfile_out1['backup'] }}"
remote_src: yes

View File

@ -0,0 +1,70 @@
- name: create user for testing
user:
name: seuser
- name: attempt to add mapping without 'seuser'
register: selogin_error
ignore_errors: true
community.general.system.selogin:
login: seuser
- name: verify failure
assert:
that:
- selogin_error is failed
- name: map login to SELinux user
register: selogin_new_mapping
check_mode: '{{ item }}'
with_items:
- true
- false
- true
- false
community.general.system.selogin:
login: seuser
seuser: staff_u
- name: new mapping- verify functionality and check_mode
assert:
that:
- selogin_new_mapping.results[0] is changed
- selogin_new_mapping.results[1] is changed
- selogin_new_mapping.results[2] is not changed
- selogin_new_mapping.results[3] is not changed
- name: change SELinux user login mapping
register: selogin_mod_mapping
check_mode: '{{ item }}'
with_items:
- true
- false
- true
- false
community.general.system.selogin:
login: seuser
seuser: user_u
- name: changed mapping- verify functionality and check_mode
assert:
that:
- selogin_mod_mapping.results[0] is changed
- selogin_mod_mapping.results[1] is changed
- selogin_mod_mapping.results[2] is not changed
- selogin_mod_mapping.results[3] is not changed
- name: remove SELinux user mapping
register: selogin_del_mapping
check_mode: '{{ item }}'
with_items:
- true
- false
- true
- false
community.general.system.selogin:
login: seuser
state: absent
- name: delete mapping- verify functionality and check_mode
assert:
that:
- selogin_del_mapping.results[0] is changed
- selogin_del_mapping.results[1] is changed
- selogin_del_mapping.results[2] is not changed
- selogin_del_mapping.results[3] is not changed
- name: remove test user
user:
name: seuser
state: absent

View File

@ -0,0 +1,17 @@
---
####################################################################
# WARNING: These are designed specifically for Ansible tests #
# and should not be used as examples of how to write Ansible roles #
####################################################################
- set_fact:
pkg_mgr: community.general.pkgng
ansible_pkg_mgr: community.general.pkgng
cacheable: yes
when: ansible_os_family == "FreeBSD"
- set_fact:
pkg_mgr: community.general.zypper
ansible_pkg_mgr: community.general.zypper
cacheable: yes
when: ansible_os_family == "Suse"

View File

@ -0,0 +1 @@
shippable/posix/group1

View File

@ -0,0 +1,2 @@
dependencies:
- prepare_tests

View File

@ -0,0 +1,310 @@
- name: install rsync
package:
name: rsync
when: ansible_distribution != "MacOSX"
- name: Clean up the working directory and files
file:
path: '{{ output_dir }}'
state: absent
- name: Create the working directory
file:
path: '{{ output_dir }}'
state: directory
- name: create test new files
copy:
dest: '{{output_dir}}/{{item}}'
mode: '0644'
content: 'hello world'
with_items:
- foo.txt
- bar.txt
- name: synchronize file to new filename
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- '''cmd'' in sync_result'
- '''rsync'' in sync_result.cmd'
- '''msg'' in sync_result'
- sync_result.msg.startswith('>f+')
- 'sync_result.msg.endswith(''+ foo.txt
'')'
- name: test that the file was really copied over
stat:
path: '{{ output_dir }}/foo.result'
register: stat_result
- assert:
that:
- stat_result.stat.exists == True
- stat_result.stat.checksum == '2aae6c35c94fcfb415dbe95f408b9ce91ee846ed'
- name: test that the file is not copied a second time
synchronize:
src='{{output_dir}}/foo.txt'
dest='{{output_dir}}/foo.result'
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- sync_result.changed == False
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- foo.result
- bar.result
- name: Synchronize using the mode=push param
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
mode: push
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- '''cmd'' in sync_result'
- '''rsync'' in sync_result.cmd'
- '''msg'' in sync_result'
- sync_result.msg.startswith('>f+')
- 'sync_result.msg.endswith(''+ foo.txt
'')'
- name: test that the file was really copied over
stat:
path: '{{ output_dir }}/foo.result'
register: stat_result
- assert:
that:
- stat_result.stat.exists == True
- stat_result.stat.checksum == '2aae6c35c94fcfb415dbe95f408b9ce91ee846ed'
- name: test that the file is not copied a second time
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
mode: push
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- sync_result.changed == False
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- foo.result
- bar.result
- name: Synchronize using the mode=pull param
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
mode: pull
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- '''cmd'' in sync_result'
- '''rsync'' in sync_result.cmd'
- '''msg'' in sync_result'
- sync_result.msg.startswith('>f+')
- 'sync_result.msg.endswith(''+ foo.txt
'')'
- name: test that the file was really copied over
stat:
path: '{{ output_dir }}/foo.result'
register: stat_result
- assert:
that:
- stat_result.stat.exists == True
- stat_result.stat.checksum == '2aae6c35c94fcfb415dbe95f408b9ce91ee846ed'
- name: test that the file is not copied a second time
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
mode: pull
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- sync_result.changed == False
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- foo.result
- bar.result
- name: synchronize files using with_items (issue#5965)
synchronize:
src: '{{output_dir}}/{{item}}'
dest: '{{output_dir}}/{{item}}.result'
with_items:
- foo.txt
- bar.txt
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- sync_result.changed
- sync_result.msg == 'All items completed'
- '''results'' in sync_result'
- sync_result.results|length == 2
- 'sync_result.results[0].msg.endswith(''+ foo.txt
'')'
- 'sync_result.results[1].msg.endswith(''+ bar.txt
'')'
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}.result'
with_items:
- foo.txt
- bar.txt
- name: synchronize files using rsync_path (issue#7182)
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.rsync_path'
rsync_path: 'sudo rsync'
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- '''cmd'' in sync_result'
- '''rsync'' in sync_result.cmd'
- '''rsync_path'' in sync_result.cmd'
- '''msg'' in sync_result'
- sync_result.msg.startswith('>f+')
- 'sync_result.msg.endswith(''+ foo.txt
'')'
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- foo.rsync_path
- name: add subdirectories for link-dest test
file:
path: '{{output_dir}}/{{item}}/'
state: directory
mode: '0755'
with_items:
- directory_a
- directory_b
- name: copy foo.txt into the first directory
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/{{item}}/foo.txt'
with_items:
- directory_a
delegate_to: '{{ inventory_hostname }}'
- name: synchronize files using link_dest
synchronize:
src: '{{output_dir}}/directory_a/foo.txt'
dest: '{{output_dir}}/directory_b/foo.txt'
link_dest:
- '{{output_dir}}/directory_a'
register: sync_result
delegate_to: '{{ inventory_hostname }}'
- name: get stat information for directory_a
stat:
path: '{{ output_dir }}/directory_a/foo.txt'
register: stat_result_a
- name: get stat information for directory_b
stat:
path: '{{ output_dir }}/directory_b/foo.txt'
register: stat_result_b
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- stat_result_a.stat.inode == stat_result_b.stat.inode
- name: synchronize files using link_dest that would be recursive
synchronize:
src: '{{output_dir}}/foo.txt'
dest: '{{output_dir}}/foo.result'
link_dest:
- '{{output_dir}}'
register: sync_result
ignore_errors: true
delegate_to: '{{ inventory_hostname }}'
- assert:
that:
- sync_result is not changed
- sync_result is failed
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- directory_b/foo.txt
- directory_a/foo.txt
- directory_a
- directory_b
- name: setup - test for source with working dir with spaces in path
file:
state: directory
path: '{{output_dir}}/{{item}}'
delegate_to: '{{ inventory_hostname }}'
with_items:
- 'directory a'
- 'directory b'
- name: setup - create test new files
copy:
dest: '{{output_dir}}/directory a/{{item}}'
mode: '0644'
content: 'hello world'
with_items:
- foo.txt
delegate_to: '{{ inventory_hostname }}'
- name: copy source with spaces in dir path
synchronize:
src: '{{output_dir}}/directory a/foo.txt'
dest: '{{output_dir}}/directory b/'
delegate_to: '{{ inventory_hostname }}'
register: sync_result
ignore_errors: true
- name: get stat information for directory_b
stat:
path: '{{ output_dir }}/directory b/foo.txt'
register: stat_result_b
- assert:
that:
- '''changed'' in sync_result'
- sync_result.changed == true
- stat_result_b.stat.exists == True
- stat_result_b.stat.checksum == '2aae6c35c94fcfb415dbe95f408b9ce91ee846ed'
- name: Cleanup
file:
state: absent
path: '{{output_dir}}/{{item}}'
with_items:
- 'directory b/foo.txt'
- 'directory a/foo.txt'
- 'directory a'
- 'directory b'

View File

@ -0,0 +1,4 @@
shippable/posix/group1
skip/aix
skip/freebsd
skip/osx

View File

@ -0,0 +1,12 @@
# sysctl settings are defined through files in
# /usr/lib/sysctl.d/, /run/sysctl.d/, and /etc/sysctl.d/.
#
# Vendors settings live in /usr/lib/sysctl.d/.
# To override a whole file, create a new file with the same in
# /etc/sysctl.d/ and put new settings there. To override
# only specific settings, add a file with a lexically later
# name in /etc/sysctl.d/ and put new settings there.
#
# For more information, see sysctl.conf(5) and sysctl.d(5).
vm.swappiness=1
kernel.panic=2

View File

@ -0,0 +1,2 @@
dependencies:
- prepare_tests

View File

@ -0,0 +1,312 @@
# Test code for the sysctl module.
# (c) 2017, James Tanner <tanner.jc@gmail.com>
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# NOTE: Testing sysctl inside an unprivileged container means that we cannot
# apply sysctl, or it will always fail, because of that in most cases (except
# those when it should fail) we have to use `reload=no`.
- name: Test inside Docker
when:
- ansible_facts.virtualization_type == 'docker' or ansible_facts.virtualization_type == 'container'
block:
- set_fact:
output_dir_test: "{{ output_dir }}/test_sysctl"
- name: make sure our testing sub-directory does not exist
file:
path: "{{ output_dir_test }}"
state: absent
- name: create our testing sub-directory
file:
path: "{{ output_dir_test }}"
state: directory
##
## sysctl - file manipulation
##
- name: copy the example conf to the test dir
copy:
src: sysctl.conf
dest: "{{ output_dir_test }}"
- name: Set vm.swappiness to 5
sysctl:
name: vm.swappiness
value: 5
state: present
reload: no
sysctl_file: "{{ output_dir_test }}/sysctl.conf"
register: sysctl_test0
- debug:
var: sysctl_test0
verbosity: 1
- name: get file content
shell: "cat {{ output_dir_test }}/sysctl.conf | egrep -v ^\\#"
register: sysctl_content0
- debug:
var: sysctl_content0
verbosity: 1
- name: Set vm.swappiness to 5 again
sysctl:
name: vm.swappiness
value: 5
state: present
reload: no
sysctl_file: "{{ output_dir_test }}/sysctl.conf"
register: sysctl_test1
- name: validate results
assert:
that:
- sysctl_test0 is changed
- sysctl_test1 is not changed
- 'sysctl_content0.stdout_lines[sysctl_content0.stdout_lines.index("vm.swappiness=5")] == "vm.swappiness=5"'
- name: Remove kernel.panic
sysctl:
name: kernel.panic
value: 2
reload: no
state: absent
sysctl_file: "{{ output_dir_test }}/sysctl.conf"
register: sysctl_test2
- name: get file content
shell: "cat {{ output_dir_test }}/sysctl.conf | egrep -v ^\\#"
register: sysctl_content2
- debug:
var: item
verbosity: 1
with_items:
- "{{ sysctl_test2 }}"
- "{{ sysctl_content2 }}"
- name: Validate results for key removal
assert:
that:
- sysctl_test2 is changed
- "'kernel.panic' not in sysctl_content2.stdout_lines"
- name: Test remove kernel.panic again
sysctl:
name: kernel.panic
value: 2
state: absent
reload: no
sysctl_file: "{{ output_dir_test }}/sysctl.conf"
register: sysctl_test2_change_test
- name: Assert that no change was made
assert:
that:
- sysctl_test2_change_test is not changed
- name: Try sysctl with an invalid name
sysctl:
name: test.invalid
value: 1
register: sysctl_test3
ignore_errors: yes
- debug:
var: sysctl_test3
verbosity: 1
- name: validate results for test 3
assert:
that:
- sysctl_test3 is failed
##
## sysctl - sysctl_set
##
- name: set net.ipv4.ip_forward
sysctl:
name: net.ipv4.ip_forward
value: 1
sysctl_set: yes
reload: no
register: sysctl_test3
- name: check with sysctl command
shell: sysctl net.ipv4.ip_forward
register: sysctl_check3
- debug:
var: item
verbosity: 1
with_items:
- "{{ sysctl_test3 }}"
- "{{ sysctl_check3 }}"
- name: validate results for test 3
assert:
that:
- sysctl_test3 is changed
- 'sysctl_check3.stdout_lines == ["net.ipv4.ip_forward = 1"]'
- name: Try sysctl with no name
sysctl:
name: ""
value: 1
sysctl_set: yes
ignore_errors: True
register: sysctl_no_name
- name: validate nameless results
assert:
that:
- sysctl_no_name is failed
- "sysctl_no_name.msg == 'name cannot be blank'"
- name: Try sysctl with no value
sysctl:
name: Foo
value:
sysctl_set: yes
ignore_errors: True
register: sysctl_no_value
- name: validate nameless results
assert:
that:
- sysctl_no_value is failed
- "sysctl_no_value.msg == 'value cannot be None'"
- name: Try sysctl with an invalid name
sysctl:
name: test.invalid
value: 1
sysctl_set: yes
register: sysctl_test4
ignore_errors: yes
- debug:
var: sysctl_test4
verbosity: 1
- name: validate results for test 4
assert:
that:
- sysctl_test4 is failed
- name: Test on RHEL VMs
when:
- ansible_facts.virtualization_type != 'docker'
- ansible_facts.distribution == 'RedHat'
block:
# Test reload: yes
- name: Set sysctl property using module
sysctl:
name: vm.swappiness
value: '22'
state: present
reload: yes
register: sysctl_set1
- name: Change sysctl property using command
command: sysctl vm.swappiness=33
- name: Set sysctl property using module
sysctl:
name: vm.swappiness
value: '22'
state: present
reload: yes
register: sysctl_set2
- name: Read /etc/sysctl.conf
command: 'egrep -v ^# /etc/sysctl.conf'
register: sysctl_conf_content
- name: Get current value of vm.swappiness
command: sysctl -n vm.swappiness
register: sysctl_current_vm_swappiness
- name: Ensure changes were made appropriately
assert:
that:
- sysctl_set1 is changed
- sysctl_set2 is changed
- "'vm.swappiness=22' in sysctl_conf_content.stdout_lines"
- sysctl_current_vm_swappiness.stdout == '22'
# Test reload: yes in check mode
- name: Set the same value using module in check mode
sysctl:
name: vm.swappiness
value: '22'
state: present
reload: yes
check_mode: yes
register: sysctl_check_mode1
- name: Set a different value using module in check mode
sysctl:
name: vm.swappiness
value: '44'
state: present
reload: yes
check_mode: yes
register: sysctl_check_mode2
- name: Read /etc/sysctl.conf
command: 'egrep -v ^# /etc/sysctl.conf'
register: sysctl_check_mode_conf_content
- name: Get current value of vm.swappiness
command: sysctl -n vm.swappiness
register: sysctl_check_mode_current_vm_swappiness
- name: Ensure no changes were made in check mode
assert:
that:
- sysctl_check_mode1 is success
- sysctl_check_mode2 is changed
- "'vm.swappiness=22' in sysctl_check_mode_conf_content.stdout_lines"
- sysctl_check_mode_current_vm_swappiness.stdout == '22'
# Test sysctl: invalid value
- name: Set invalid sysctl property using module
sysctl:
name: vm.mmap_rnd_bits
value: '1024'
state: present
reload: yes
sysctl_set: True
ignore_errors: True
register: sysctl_invalid_set1
- name: Read /etc/sysctl.conf
command: 'cat /etc/sysctl.conf'
register: sysctl_invalid_conf_content
- name: Ensure changes were not made
assert:
that:
- sysctl_invalid_set1 is failed
- "'vm.mmap_rnd_bits' not in sysctl_invalid_conf_content.stdout"

View File

@ -0,0 +1,4 @@
integration_tests_dependencies:
- community.general
unit_tests_dependencies:
- community.general

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:blacklisted-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:blacklisted-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:disallowed-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:disallowed-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:disallowed-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:disallowed-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,5 @@
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter

View File

@ -0,0 +1,8 @@
plugins/modules/synchronize.py pylint:blacklisted-name
plugins/modules/synchronize.py use-argspec-type-path
plugins/modules/synchronize.py validate-modules:doc-default-does-not-match-spec
plugins/modules/synchronize.py validate-modules:nonexistent-parameter-documented
plugins/modules/synchronize.py validate-modules:parameter-type-not-in-doc
plugins/modules/synchronize.py validate-modules:undocumented-parameter
tests/utils/shippable/check_matrix.py replace-urlopen
tests/utils/shippable/timing.py shebang

View File

@ -0,0 +1,34 @@
# (c) 2014, Toshio Kuratomi <tkuratomi@ansible.com>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
#
# Compat for python2.7
#
# One unittest needs to import builtins via __import__() so we need to have
# the string that represents it
try:
import __builtin__
except ImportError:
BUILTINS = 'builtins'
else:
BUILTINS = '__builtin__'
__all__ = ['__builtin__']

View File

@ -0,0 +1,122 @@
# (c) 2014, Toshio Kuratomi <tkuratomi@ansible.com>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
'''
Compat module for Python3.x's unittest.mock module
'''
import sys
# Python 2.7
# Note: Could use the pypi mock library on python3.x as well as python2.x. It
# is the same as the python3 stdlib mock library
try:
# Allow wildcard import because we really do want to import all of mock's
# symbols into this compat shim
# pylint: disable=wildcard-import,unused-wildcard-import
from unittest.mock import *
except ImportError:
# Python 2
# pylint: disable=wildcard-import,unused-wildcard-import
try:
from mock import *
except ImportError:
print('You need the mock library installed on python2.x to run tests')
# Prior to 3.4.4, mock_open cannot handle binary read_data
if sys.version_info >= (3,) and sys.version_info < (3, 4, 4):
file_spec = None
def _iterate_read_data(read_data):
# Helper for mock_open:
# Retrieve lines from read_data via a generator so that separate calls to
# readline, read, and readlines are properly interleaved
sep = b'\n' if isinstance(read_data, bytes) else '\n'
data_as_list = [l + sep for l in read_data.split(sep)]
if data_as_list[-1] == sep:
# If the last line ended in a newline, the list comprehension will have an
# extra entry that's just a newline. Remove this.
data_as_list = data_as_list[:-1]
else:
# If there wasn't an extra newline by itself, then the file being
# emulated doesn't have a newline to end the last line remove the
# newline that our naive format() added
data_as_list[-1] = data_as_list[-1][:-1]
for line in data_as_list:
yield line
def mock_open(mock=None, read_data=''):
"""
A helper function to create a mock to replace the use of `open`. It works
for `open` called directly or used as a context manager.
The `mock` argument is the mock object to configure. If `None` (the
default) then a `MagicMock` will be created for you, with the API limited
to methods or attributes available on standard file handles.
`read_data` is a string for the `read` methoddline`, and `readlines` of the
file handle to return. This is an empty string by default.
"""
def _readlines_side_effect(*args, **kwargs):
if handle.readlines.return_value is not None:
return handle.readlines.return_value
return list(_data)
def _read_side_effect(*args, **kwargs):
if handle.read.return_value is not None:
return handle.read.return_value
return type(read_data)().join(_data)
def _readline_side_effect():
if handle.readline.return_value is not None:
while True:
yield handle.readline.return_value
for line in _data:
yield line
global file_spec
if file_spec is None:
import _io
file_spec = list(set(dir(_io.TextIOWrapper)).union(set(dir(_io.BytesIO))))
if mock is None:
mock = MagicMock(name='open', spec=open)
handle = MagicMock(spec=file_spec)
handle.__enter__.return_value = handle
_data = _iterate_read_data(read_data)
handle.write.return_value = None
handle.read.return_value = None
handle.readline.return_value = None
handle.readlines.return_value = None
handle.read.side_effect = _read_side_effect
handle.readline.side_effect = _readline_side_effect()
handle.readlines.side_effect = _readlines_side_effect
mock.return_value = handle
return mock

View File

@ -0,0 +1,38 @@
# (c) 2014, Toshio Kuratomi <tkuratomi@ansible.com>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
'''
Compat module for Python2.7's unittest module
'''
import sys
# Allow wildcard import because we really do want to import all of
# unittests's symbols into this compat shim
# pylint: disable=wildcard-import,unused-wildcard-import
if sys.version_info < (2, 7):
try:
# Need unittest2 on python2.6
from unittest2 import *
except ImportError:
print('You need unittest2 installed on python2.6.x to run tests')
else:
from unittest import *

View File

@ -0,0 +1,116 @@
# (c) 2012-2014, Michael DeHaan <michael.dehaan@gmail.com>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
import os
from ansible.errors import AnsibleParserError
from ansible.parsing.dataloader import DataLoader
from ansible.module_utils._text import to_bytes, to_text
class DictDataLoader(DataLoader):
def __init__(self, file_mapping=None):
file_mapping = {} if file_mapping is None else file_mapping
assert type(file_mapping) == dict
super(DictDataLoader, self).__init__()
self._file_mapping = file_mapping
self._build_known_directories()
self._vault_secrets = None
def load_from_file(self, path, cache=True, unsafe=False):
path = to_text(path)
if path in self._file_mapping:
return self.load(self._file_mapping[path], path)
return None
# TODO: the real _get_file_contents returns a bytestring, so we actually convert the
# unicode/text it's created with to utf-8
def _get_file_contents(self, file_name):
path = to_text(file_name)
if path in self._file_mapping:
return (to_bytes(self._file_mapping[path]), False)
else:
raise AnsibleParserError("file not found: %s" % path)
def path_exists(self, path):
path = to_text(path)
return path in self._file_mapping or path in self._known_directories
def is_file(self, path):
path = to_text(path)
return path in self._file_mapping
def is_directory(self, path):
path = to_text(path)
return path in self._known_directories
def list_directory(self, path):
ret = []
path = to_text(path)
for x in (list(self._file_mapping.keys()) + self._known_directories):
if x.startswith(path):
if os.path.dirname(x) == path:
ret.append(os.path.basename(x))
return ret
def is_executable(self, path):
# FIXME: figure out a way to make paths return true for this
return False
def _add_known_directory(self, directory):
if directory not in self._known_directories:
self._known_directories.append(directory)
def _build_known_directories(self):
self._known_directories = []
for path in self._file_mapping:
dirname = os.path.dirname(path)
while dirname not in ('/', ''):
self._add_known_directory(dirname)
dirname = os.path.dirname(dirname)
def push(self, path, content):
rebuild_dirs = False
if path not in self._file_mapping:
rebuild_dirs = True
self._file_mapping[path] = content
if rebuild_dirs:
self._build_known_directories()
def pop(self, path):
if path in self._file_mapping:
del self._file_mapping[path]
self._build_known_directories()
def clear(self):
self._file_mapping = dict()
self._known_directories = []
def get_basedir(self):
return os.getcwd()
def set_vault_secrets(self, vault_secrets):
self._vault_secrets = vault_secrets

View File

@ -0,0 +1,9 @@
from __future__ import absolute_import, division, print_function
__metaclass__ = type
from ansible_collections.ansible.posix.tests.unit.compat.mock import MagicMock
from ansible.utils.path import unfrackpath
mock_unfrackpath_noop = MagicMock(spec_set=unfrackpath, side_effect=lambda x, *args, **kwargs: x)

View File

@ -0,0 +1,90 @@
# (c) 2016, Matt Davis <mdavis@ansible.com>
# (c) 2016, Toshio Kuratomi <tkuratomi@ansible.com>
#
# This file is part of Ansible
#
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
import sys
import json
from contextlib import contextmanager
from io import BytesIO, StringIO
from ansible_collections.ansible.posix.tests.unit.compat import unittest
from ansible.module_utils.six import PY3
from ansible.module_utils._text import to_bytes
@contextmanager
def swap_stdin_and_argv(stdin_data='', argv_data=tuple()):
"""
context manager that temporarily masks the test runner's values for stdin and argv
"""
real_stdin = sys.stdin
real_argv = sys.argv
if PY3:
fake_stream = StringIO(stdin_data)
fake_stream.buffer = BytesIO(to_bytes(stdin_data))
else:
fake_stream = BytesIO(to_bytes(stdin_data))
try:
sys.stdin = fake_stream
sys.argv = argv_data
yield
finally:
sys.stdin = real_stdin
sys.argv = real_argv
@contextmanager
def swap_stdout():
"""
context manager that temporarily replaces stdout for tests that need to verify output
"""
old_stdout = sys.stdout
if PY3:
fake_stream = StringIO()
else:
fake_stream = BytesIO()
try:
sys.stdout = fake_stream
yield fake_stream
finally:
sys.stdout = old_stdout
class ModuleTestCase(unittest.TestCase):
def setUp(self, module_args=None):
if module_args is None:
module_args = {'_ansible_remote_tmp': '/tmp', '_ansible_keep_remote_files': False}
args = json.dumps(dict(ANSIBLE_MODULE_ARGS=module_args))
# unittest doesn't have a clean place to use a context manager, so we have to enter/exit manually
self.stdin_swap = swap_stdin_and_argv(stdin_data=args)
self.stdin_swap.__enter__()
def tearDown(self):
# unittest doesn't have a clean place to use a context manager, so we have to enter/exit manually
self.stdin_swap.__exit__(None, None, None)

View File

@ -0,0 +1,39 @@
# Ansible is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# Ansible is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with Ansible. If not, see <http://www.gnu.org/licenses/>.
# Make coding more python3-ish
from __future__ import (absolute_import, division, print_function)
__metaclass__ = type
from ansible.module_utils._text import to_bytes
from ansible.parsing.vault import VaultSecret
class TextVaultSecret(VaultSecret):
'''A secret piece of text. ie, a password. Tracks text encoding.
The text encoding of the text may not be the default text encoding so
we keep track of the encoding so we encode it to the same bytes.'''
def __init__(self, text, encoding=None, errors=None, _bytes=None):
super(TextVaultSecret, self).__init__()
self.text = text
self.encoding = encoding or 'utf-8'
self._bytes = _bytes
self.errors = errors or 'strict'
@property
def bytes(self):
'''The text encoded with encoding, unless we specifically set _bytes.'''
return self._bytes or to_bytes(self.text, encoding=self.encoding, errors=self.errors)

View File

@ -0,0 +1,125 @@
from __future__ import absolute_import, division, print_function
__metaclass__ = type
import io
import yaml
from ansible.module_utils.six import PY3
from ansible.parsing.yaml.loader import AnsibleLoader
from ansible.parsing.yaml.dumper import AnsibleDumper
class YamlTestUtils(object):
"""Mixin class to combine with a unittest.TestCase subclass."""
def _loader(self, stream):
"""Vault related tests will want to override this.
Vault cases should setup a AnsibleLoader that has the vault password."""
return AnsibleLoader(stream)
def _dump_stream(self, obj, stream, dumper=None):
"""Dump to a py2-unicode or py3-string stream."""
if PY3:
return yaml.dump(obj, stream, Dumper=dumper)
else:
return yaml.dump(obj, stream, Dumper=dumper, encoding=None)
def _dump_string(self, obj, dumper=None):
"""Dump to a py2-unicode or py3-string"""
if PY3:
return yaml.dump(obj, Dumper=dumper)
else:
return yaml.dump(obj, Dumper=dumper, encoding=None)
def _dump_load_cycle(self, obj):
# Each pass though a dump or load revs the 'generation'
# obj to yaml string
string_from_object_dump = self._dump_string(obj, dumper=AnsibleDumper)
# wrap a stream/file like StringIO around that yaml
stream_from_object_dump = io.StringIO(string_from_object_dump)
loader = self._loader(stream_from_object_dump)
# load the yaml stream to create a new instance of the object (gen 2)
obj_2 = loader.get_data()
# dump the gen 2 objects directory to strings
string_from_object_dump_2 = self._dump_string(obj_2,
dumper=AnsibleDumper)
# The gen 1 and gen 2 yaml strings
self.assertEqual(string_from_object_dump, string_from_object_dump_2)
# the gen 1 (orig) and gen 2 py object
self.assertEqual(obj, obj_2)
# again! gen 3... load strings into py objects
stream_3 = io.StringIO(string_from_object_dump_2)
loader_3 = self._loader(stream_3)
obj_3 = loader_3.get_data()
string_from_object_dump_3 = self._dump_string(obj_3, dumper=AnsibleDumper)
self.assertEqual(obj, obj_3)
# should be transitive, but...
self.assertEqual(obj_2, obj_3)
self.assertEqual(string_from_object_dump, string_from_object_dump_3)
def _old_dump_load_cycle(self, obj):
'''Dump the passed in object to yaml, load it back up, dump again, compare.'''
stream = io.StringIO()
yaml_string = self._dump_string(obj, dumper=AnsibleDumper)
self._dump_stream(obj, stream, dumper=AnsibleDumper)
yaml_string_from_stream = stream.getvalue()
# reset stream
stream.seek(0)
loader = self._loader(stream)
# loader = AnsibleLoader(stream, vault_password=self.vault_password)
obj_from_stream = loader.get_data()
stream_from_string = io.StringIO(yaml_string)
loader2 = self._loader(stream_from_string)
# loader2 = AnsibleLoader(stream_from_string, vault_password=self.vault_password)
obj_from_string = loader2.get_data()
stream_obj_from_stream = io.StringIO()
stream_obj_from_string = io.StringIO()
if PY3:
yaml.dump(obj_from_stream, stream_obj_from_stream, Dumper=AnsibleDumper)
yaml.dump(obj_from_stream, stream_obj_from_string, Dumper=AnsibleDumper)
else:
yaml.dump(obj_from_stream, stream_obj_from_stream, Dumper=AnsibleDumper, encoding=None)
yaml.dump(obj_from_stream, stream_obj_from_string, Dumper=AnsibleDumper, encoding=None)
yaml_string_stream_obj_from_stream = stream_obj_from_stream.getvalue()
yaml_string_stream_obj_from_string = stream_obj_from_string.getvalue()
stream_obj_from_stream.seek(0)
stream_obj_from_string.seek(0)
if PY3:
yaml_string_obj_from_stream = yaml.dump(obj_from_stream, Dumper=AnsibleDumper)
yaml_string_obj_from_string = yaml.dump(obj_from_string, Dumper=AnsibleDumper)
else:
yaml_string_obj_from_stream = yaml.dump(obj_from_stream, Dumper=AnsibleDumper, encoding=None)
yaml_string_obj_from_string = yaml.dump(obj_from_string, Dumper=AnsibleDumper, encoding=None)
assert yaml_string == yaml_string_obj_from_stream
assert yaml_string == yaml_string_obj_from_stream == yaml_string_obj_from_string
assert (yaml_string == yaml_string_obj_from_stream == yaml_string_obj_from_string == yaml_string_stream_obj_from_stream ==
yaml_string_stream_obj_from_string)
assert obj == obj_from_stream
assert obj == obj_from_string
assert obj == yaml_string_obj_from_stream
assert obj == yaml_string_obj_from_string
assert obj == obj_from_stream == obj_from_string == yaml_string_obj_from_stream == yaml_string_obj_from_string
return {'obj': obj,
'yaml_string': yaml_string,
'yaml_string_from_stream': yaml_string_from_stream,
'obj_from_stream': obj_from_stream,
'obj_from_string': obj_from_string,
'yaml_string_obj_from_string': yaml_string_obj_from_string}

View File

@ -0,0 +1,32 @@
# Copyright (c) 2017 Ansible Project
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
from __future__ import absolute_import, division, print_function
__metaclass__ = type
import json
import pytest
from ansible.module_utils.six import string_types
from ansible.module_utils._text import to_bytes
from ansible.module_utils.common._collections_compat import MutableMapping
@pytest.fixture
def patch_ansible_module(request, mocker):
if isinstance(request.param, string_types):
args = request.param
elif isinstance(request.param, MutableMapping):
if 'ANSIBLE_MODULE_ARGS' not in request.param:
request.param = {'ANSIBLE_MODULE_ARGS': request.param}
if '_ansible_remote_tmp' not in request.param['ANSIBLE_MODULE_ARGS']:
request.param['ANSIBLE_MODULE_ARGS']['_ansible_remote_tmp'] = '/tmp'
if '_ansible_keep_remote_files' not in request.param['ANSIBLE_MODULE_ARGS']:
request.param['ANSIBLE_MODULE_ARGS']['_ansible_keep_remote_files'] = False
args = json.dumps(request.param)
else:
raise Exception('Malformed data to the patch_ansible_module pytest fixture')
mocker.patch('ansible.module_utils.basic._ANSIBLE_ARGS', to_bytes(args))

View File

@ -0,0 +1,63 @@
from __future__ import absolute_import, division, print_function
__metaclass__ = type
import os
import tempfile
from ansible_collections.ansible.posix.tests.unit.compat import unittest
from ansible_collections.ansible.posix.tests.unit.compat.mock import MagicMock
from ansible.module_utils._text import to_bytes
from ansible_collections.ansible.posix.plugins.modules.mount import (
get_linux_mounts,
_set_mount_save_old,
set_mount,
)
class LinuxMountsTestCase(unittest.TestCase):
def _create_file(self, content):
tmp_file = tempfile.NamedTemporaryFile(prefix='ansible-test-', delete=False)
tmp_file.write(to_bytes(content))
tmp_file.close()
self.addCleanup(os.unlink, tmp_file.name)
return tmp_file.name
def test_code_comment(self):
path = self._create_file(
'140 136 253:2 /rootfs / rw - ext4 /dev/sdb2 rw\n'
'141 140 253:2 /rootfs/tmp/aaa /tmp/bbb rw - ext4 /dev/sdb2 rw\n'
)
mounts = get_linux_mounts(None, path)
self.assertEqual(mounts['/tmp/bbb']['src'], '/tmp/aaa')
def test_set_mount_save_old(self):
module = MagicMock(name='AnsibleModule')
module.check_mode = True
module.params = {'backup': False}
fstab_data = [
'UUID=8ac075e3-1124-4bb6-bef7-a6811bf8b870 / xfs defaults 0 0\n',
'/swapfile none swap defaults 0 0\n'
]
path = self._create_file("".join(fstab_data))
args = {
'fstab': path,
'name': '/data',
'src': '/dev/sdb1',
'fstype': 'ext4',
'opts': 'defaults',
'dump': '0',
'passno': '0',
}
name, changed = set_mount(module, args)
self.assertEqual(name, '/data')
self.assertTrue(changed)
name, backup_lines, changed = _set_mount_save_old(module, args)
self.assertEqual(backup_lines, fstab_data)
self.assertEqual(name, '/data')
self.assertTrue(changed)

View File

@ -0,0 +1,51 @@
from __future__ import absolute_import, division, print_function
__metaclass__ = type
import json
from ansible_collections.ansible.posix.tests.unit.compat import unittest
from ansible_collections.ansible.posix.tests.unit.compat.mock import patch
from ansible.module_utils import basic
from ansible.module_utils._text import to_bytes
def set_module_args(args):
if '_ansible_remote_tmp' not in args:
args['_ansible_remote_tmp'] = '/tmp'
if '_ansible_keep_remote_files' not in args:
args['_ansible_keep_remote_files'] = False
args = json.dumps({'ANSIBLE_MODULE_ARGS': args})
basic._ANSIBLE_ARGS = to_bytes(args)
class AnsibleExitJson(Exception):
pass
class AnsibleFailJson(Exception):
pass
def exit_json(*args, **kwargs):
if 'changed' not in kwargs:
kwargs['changed'] = False
raise AnsibleExitJson(kwargs)
def fail_json(*args, **kwargs):
kwargs['failed'] = True
raise AnsibleFailJson(kwargs)
class ModuleTestCase(unittest.TestCase):
def setUp(self):
self.mock_module = patch.multiple(basic.AnsibleModule, exit_json=exit_json, fail_json=fail_json)
self.mock_module.start()
self.mock_sleep = patch('time.sleep')
self.mock_sleep.start()
set_module_args({})
self.addCleanup(self.mock_module.stop)
self.addCleanup(self.mock_sleep.stop)

View File

@ -0,0 +1,17 @@
fixtures:
taskvars_in: taskvars_in.json
taskvars_out: taskvars_out.json
connection:
transport: 'ssh'
hostvars:
'127.0.0.1': {}
'::1': {}
'localhost': {}
asserts:
- "hasattr(SAM._connection, 'ismock')"
- "SAM._connection.transport == 'local'"
- "self._play_context.shell == 'sh'"
- "self.execute_called"
- "self.final_module_args['_local_rsync_path'] == 'rsync'"
- "self.final_module_args['src'] == '/tmp/deleteme'"
- "self.final_module_args['dest'] == 'root@el6host:/tmp/deleteme'"

View File

@ -0,0 +1,5 @@
{
"dest": "root@el6host:/tmp/deleteme",
"src": "/tmp/deleteme",
"_local_rsync_path": "rsync"
}

View File

@ -0,0 +1,151 @@
{
"ansible_pipelining": false,
"ansible_docker_extra_args": "",
"ansible_scp_extra_args": "",
"ansible_user": "root",
"ansible_play_hosts": [
"el6host"
],
"ansible_connection": "smart",
"ansible_ssh_common_args": "",
"environment": [],
"inventory_hostname": "el6host",
"vars": {
"ansible_check_mode": false,
"inventory_hostname": "el6host",
"inventory_file": "inventory",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"role_names": [],
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"environment": [],
"play_hosts": [
"el6host"
],
"ansible_play_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"group_names": [
"ungrouped"
],
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_user": "root"
},
"ansible_accelerate_port": 5099,
"roledir": null,
"ansible_ssh_extra_args": "",
"ansible_host": "el6host",
"ansible_current_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"group_names": [
"ungrouped"
],
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_ssh_pipelining": false,
"inventory_file": "inventory",
"ansible_module_compression": "ZIP_DEFLATED",
"ansible_failed_hosts": [],
"ansible_check_mode": false,
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"ansible_host": "el6host",
"ansible_shell_executable": "/bin/sh",
"inventory_hostname_short": "el6host",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"role_names": [],
"play_hosts": [
"el6host"
],
"ansible_sftp_extra_args": ""
}

View File

@ -0,0 +1,156 @@
{
"ansible_pipelining": false,
"ansible_docker_extra_args": "",
"ansible_scp_extra_args": "",
"ansible_user": "root",
"ansible_play_hosts": [
"el6host"
],
"ansible_connection": "smart",
"ansible_ssh_common_args": "",
"environment": [],
"inventory_hostname": "el6host",
"vars": {
"ansible_check_mode": false,
"inventory_hostname": "el6host",
"inventory_file": "inventory",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"role_names": [],
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"environment": [],
"play_hosts": [
"el6host"
],
"ansible_play_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host",
"::1"
],
"all": [
"el6host",
"::1"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"group_names": [
"ungrouped"
],
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_user": "root"
},
"ansible_accelerate_port": 5099,
"roledir": null,
"ansible_ssh_extra_args": "",
"ansible_host": "el6host",
"ansible_current_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host",
"::1"
],
"all": [
"el6host",
"::1"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"group_names": [
"ungrouped"
],
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_ssh_pipelining": false,
"inventory_file": "inventory",
"ansible_module_compression": "ZIP_DEFLATED",
"ansible_failed_hosts": [],
"ansible_check_mode": false,
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"ansible_host": "el6host",
"ansible_shell_executable": "/bin/sh",
"inventory_hostname_short": "el6host",
"omit": "__omit_place_holder__03600813b83569c710bf5cb2a040d6e01da927c6",
"ansible_python_interpreter": "/usr/bin/python",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"role_names": [],
"play_hosts": [
"el6host"
],
"ansible_sftp_extra_args": ""
}

View File

@ -0,0 +1,39 @@
task_args:
src: /tmp/deleteme
dest: /tmp/deleteme
#rsync_path: rsync
_task:
become: True
become_method: None
fixtures:
taskvars_in: task_vars_in.json
taskvars_out: task_vars_out.json
connection:
transport: 'ssh'
_play_context:
become: True
become_method: sudo
remote_addr: el6host
remote_user: root
hostvars:
'127.0.0.1': {}
'::1': {}
'localhost': {}
asserts:
- "hasattr(SAM._connection, 'ismock')"
- "SAM._connection.transport == 'local'"
- "self.execute_called"
- "self.final_module_args['_local_rsync_path'] == 'rsync'"
# this is a crucial aspect of this scenario ...
# note: become_user None -> root
- "self.final_module_args['rsync_path'] == 'sudo -u root rsync'"
- "self.final_module_args['src'] == '/tmp/deleteme'"
- "self.final_module_args['dest'] == 'root@el6host:/tmp/deleteme'"
- "self.task.become == True"
- "self.task.become_user == None"
- "self._play_context.shell == 'sh'"
- "self._play_context.remote_addr == 'el6host'"
- "self._play_context.remote_user == 'root'"
- "self._play_context.become == False"
- "self._play_context.become_user == 'root'"
- "self._play_context.password == None"

View File

@ -0,0 +1,6 @@
{
"dest": "root@el6host:/tmp/deleteme",
"src": "/tmp/deleteme",
"rsync_path": "sudo rsync",
"_local_rsync_path": "rsync"
}

View File

@ -0,0 +1,151 @@
{
"ansible_pipelining": false,
"ansible_docker_extra_args": "",
"ansible_scp_extra_args": "",
"ansible_user": "root",
"ansible_play_hosts": [
"el6host"
],
"ansible_connection": "smart",
"ansible_ssh_common_args": "",
"environment": [],
"inventory_hostname": "el6host",
"vars": {
"ansible_check_mode": false,
"inventory_hostname": "el6host",
"inventory_file": "inventory",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"role_names": [],
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"environment": [],
"play_hosts": [
"el6host"
],
"ansible_play_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"group_names": [
"ungrouped"
],
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_user": "root"
},
"ansible_accelerate_port": 5099,
"roledir": null,
"ansible_ssh_extra_args": "",
"ansible_host": "el6host",
"ansible_current_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"group_names": [
"ungrouped"
],
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_ssh_pipelining": false,
"inventory_file": "inventory",
"ansible_module_compression": "ZIP_DEFLATED",
"ansible_failed_hosts": [],
"ansible_check_mode": false,
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"ansible_host": "el6host",
"ansible_shell_executable": "/bin/sh",
"inventory_hostname_short": "el6host",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"role_names": [],
"play_hosts": [
"el6host"
],
"ansible_sftp_extra_args": ""
}

View File

@ -0,0 +1,156 @@
{
"ansible_pipelining": false,
"ansible_docker_extra_args": "",
"ansible_scp_extra_args": "",
"ansible_user": "root",
"ansible_play_hosts": [
"el6host"
],
"ansible_connection": "smart",
"ansible_ssh_common_args": "",
"environment": [],
"inventory_hostname": "el6host",
"vars": {
"ansible_check_mode": false,
"inventory_hostname": "el6host",
"inventory_file": "inventory",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"role_names": [],
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"environment": [],
"play_hosts": [
"el6host"
],
"ansible_play_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host",
"::1"
],
"all": [
"el6host",
"::1"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"group_names": [
"ungrouped"
],
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_user": "root"
},
"ansible_accelerate_port": 5099,
"roledir": null,
"ansible_ssh_extra_args": "",
"ansible_host": "el6host",
"ansible_current_hosts": [
"el6host"
],
"hostvars": {
"el6host": {
"inventory_file": "inventory",
"group_names": [
"ungrouped"
],
"groups": {
"ungrouped": [
"el6host",
"::1"
],
"all": [
"el6host",
"::1"
]
},
"inventory_hostname": "el6host",
"inventory_hostname_short": "el6host",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"ansible_check_mode": false,
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
}
}
},
"group_names": [
"ungrouped"
],
"ansible_version": {
"major": 2,
"full": "2.2.0",
"string": "2.2.0",
"minor": 2,
"revision": 0
},
"ansible_ssh_pipelining": false,
"inventory_file": "inventory",
"ansible_module_compression": "ZIP_DEFLATED",
"ansible_failed_hosts": [],
"ansible_check_mode": false,
"groups": {
"ungrouped": [
"el6host"
],
"all": [
"el6host"
]
},
"ansible_host": "el6host",
"ansible_shell_executable": "/bin/sh",
"inventory_hostname_short": "el6host",
"omit": "__omit_place_holder__b3ac1e6ebeed06f4be0c1edca3dca34036cf7f57",
"ansible_python_interpreter": "/usr/bin/python",
"inventory_dir": "/home/jtanner/workspace/issues/AP-15905",
"playbook_dir": "/home/jtanner/workspace/issues/AP-15905",
"ansible_user": "root",
"role_names": [],
"play_hosts": [
"el6host"
],
"ansible_sftp_extra_args": ""
}

View File

@ -0,0 +1,39 @@
task_args:
src: /tmp/deleteme
dest: /tmp/deleteme
#rsync_path: rsync
_task:
become: None
become_method: None
fixtures:
taskvars_in: task_vars_in.json
taskvars_out: task_vars_out.json
connection:
transport: 'ssh'
_play_context:
become: True
become_method: sudo
remote_addr: el6host
remote_user: root
hostvars:
'127.0.0.1': {}
'::1': {}
'localhost': {}
asserts:
- "hasattr(SAM._connection, 'ismock')"
- "SAM._connection.transport == 'local'"
- "self.execute_called"
- "self.final_module_args['_local_rsync_path'] == 'rsync'"
# this is a crucial aspect of this scenario ...
# note: become_user None -> root
- "self.final_module_args['rsync_path'] == 'sudo -u root rsync'"
- "self.final_module_args['src'] == '/tmp/deleteme'"
- "self.final_module_args['dest'] == 'root@el6host:/tmp/deleteme'"
- "self.task.become == None"
- "self.task.become_user == None"
- "self._play_context.shell == 'sh'"
- "self._play_context.remote_addr == 'el6host'"
- "self._play_context.remote_user == 'root'"
- "self._play_context.become == False"
- "self._play_context.become_user == 'root'"
- "self._play_context.password == None"

Some files were not shown because too many files have changed in this diff Show More