mirror of
https://github.com/willshersystems/ansible-sshd
synced 2024-11-24 12:00:19 +01:00
Add support for managing selinux and firewall on RHEL
This commit is contained in:
parent
788a3d8668
commit
04f056867c
9 changed files with 258 additions and 0 deletions
34
README.md
34
README.md
|
@ -45,6 +45,21 @@ Tested on:
|
|||
It will likely work on other flavours and more direct support via suitable
|
||||
[vars/](vars/) files is welcome.
|
||||
|
||||
|
||||
### Optional requirements
|
||||
|
||||
If you want to use advanced functionality of this role that can configure
|
||||
firewall and selinux for you, which is mostly useful when custom port is used,
|
||||
the role requires additional collections which are specified in
|
||||
`meta/collection-requirements.yml`. These are not automatically installed.
|
||||
You must install them like this:
|
||||
```
|
||||
ansible-galaxy install -vv -r meta/collection-requirements.yml
|
||||
```
|
||||
|
||||
For more information, see `sshd_manage_firewall` and `sshd_manage_selinux`
|
||||
options below. These roles are supported only on Red Hat based Linux.
|
||||
|
||||
Role variables
|
||||
---------------
|
||||
|
||||
|
@ -93,6 +108,25 @@ Using these variables, you can use your own custom templates. With the above
|
|||
default templates, the name of the installed ssh service will be provided by
|
||||
the `sshd_service` variable.
|
||||
|
||||
* `sshd_manage_firewall`
|
||||
|
||||
If set to *true*, the the SSH port(s) will be opened in firewall. Note, this
|
||||
works only on Red Hat based OS. The default is *false*.
|
||||
|
||||
NOTE: `sshd_manage_firewall` is limited to *adding* ports. It cannot be used
|
||||
for *removing* ports. If you want to remove ports, you will need to use the
|
||||
firewall system role directly.
|
||||
|
||||
* `sshd_manage_selinux`
|
||||
|
||||
If set to *true*, the the selinux will be configured to allow sshd listening
|
||||
on the given SSH port(s). Note, this works only on Red Hat based OS.
|
||||
The default is *false*.
|
||||
|
||||
NOTE: `sshd_manage_selinux` is limited to *adding* policy. It cannot be used
|
||||
for *removing* policy. If you want to remove ports, you will need to use the
|
||||
selinux system role directly.
|
||||
|
||||
* `sshd`
|
||||
|
||||
A dict containing configuration. e.g.
|
||||
|
|
|
@ -73,3 +73,11 @@ sshd_hostkey_mode: "{{ __sshd_hostkey_mode }}"
|
|||
# instead of replacing the whole configuration file, just add a specified
|
||||
# snippet
|
||||
sshd_config_namespace: null
|
||||
|
||||
# If this option is enabled, the role will configure firewall to open the ports
|
||||
# defined in the configuration. This works only on Red Hat based systems.
|
||||
sshd_manage_firewall: false
|
||||
|
||||
# If this option is enabled, the role will configure selinux to allow sshd to
|
||||
# bind the ports defined in the configuration. This works only on Red Hat based systems.
|
||||
sshd_manage_selinux: false
|
||||
|
|
3
meta/collection-requirements.yml
Normal file
3
meta/collection-requirements.yml
Normal file
|
@ -0,0 +1,3 @@
|
|||
---
|
||||
collections:
|
||||
- name: fedora.linux_system_roles
|
26
tasks/find_ports.yml
Normal file
26
tasks/find_ports.yml
Normal file
|
@ -0,0 +1,26 @@
|
|||
---
|
||||
- name: Find the port the ssh service is going to use
|
||||
vars:
|
||||
# This mimics the macro body_option() in sshd_config.j2
|
||||
# The explicit to_json filter is needed for Python 2 compatibility
|
||||
__sshd_ports_from_config_tmp: >-
|
||||
{% if sshd_Port is defined %}
|
||||
{{ sshd_Port | to_json }}
|
||||
{% elif sshd['Port'] is defined %}
|
||||
{{ sshd['Port'] | to_json }}
|
||||
{% elif __sshd_defaults['Port'] is defined and not sshd_skip_defaults %}
|
||||
{{ __sshd_defaults['Port'] | to_json }}
|
||||
{% else %}
|
||||
{{ [22] | to_json }}
|
||||
{% endif %}
|
||||
ansible.builtin.set_fact:
|
||||
__sshd_ports_from_config: >-
|
||||
{% if __sshd_ports_from_config_tmp | from_json is string or __sshd_ports_from_config_tmp | from_json is number %}
|
||||
{{ [__sshd_ports_from_config_tmp | from_json] | to_json }}
|
||||
{% else %}
|
||||
{{ __sshd_ports_from_config_tmp }}
|
||||
{% endif %}
|
||||
when:
|
||||
- sshd_manage_firewall | bool or sshd_manage_selinux | bool
|
||||
- ansible_facts['os_family'] == 'RedHat'
|
||||
- ansible_virtualization_type|default(None) not in __sshd_skip_virt_env
|
25
tasks/firewall.yml
Normal file
25
tasks/firewall.yml
Normal file
|
@ -0,0 +1,25 @@
|
|||
---
|
||||
- name: Ensure the ssh service or custom ports are opened in firewall
|
||||
block:
|
||||
- name: Enable the ssh service on default port
|
||||
ansible.builtin.include_role:
|
||||
name: fedora.linux_system_roles.firewall
|
||||
vars:
|
||||
firewall:
|
||||
- service: ssh
|
||||
state: enabled
|
||||
when:
|
||||
- __sshd_ports_from_config | from_json == [22]
|
||||
|
||||
- name: Enable the non-default port(s)
|
||||
ansible.builtin.include_role:
|
||||
name: fedora.linux_system_roles.firewall
|
||||
vars:
|
||||
firewall:
|
||||
- port: "{{ sshd_item }}/tcp"
|
||||
state: enabled
|
||||
loop: "{{ __sshd_ports_from_config | from_json | d([]) }}"
|
||||
loop_control:
|
||||
loop_var: sshd_item # avoid conflicts with the firewall loops
|
||||
when:
|
||||
- __sshd_ports_from_config | from_json != [22]
|
|
@ -121,6 +121,24 @@
|
|||
when:
|
||||
- __sshd_runtime_directory is not none
|
||||
|
||||
- name: Find SSHD ports
|
||||
ansible.builtin.include_tasks: find_ports.yml
|
||||
|
||||
- name: Configure firewall
|
||||
ansible.builtin.include_tasks: firewall.yml
|
||||
when:
|
||||
- sshd_manage_firewall | bool
|
||||
- ansible_facts['os_family'] == 'RedHat'
|
||||
- ansible_facts['distribution_version'] is version('7', '>=')
|
||||
- ansible_virtualization_type|default(None) not in __sshd_skip_virt_env
|
||||
|
||||
- name: Configure selinux
|
||||
ansible.builtin.include_tasks: selinux.yml
|
||||
when:
|
||||
- sshd_manage_selinux | bool
|
||||
- ansible_facts['os_family'] == 'RedHat'
|
||||
- ansible_virtualization_type|default(None) not in __sshd_skip_virt_env
|
||||
|
||||
- name: Create the complete configuration file
|
||||
ansible.builtin.include_tasks: install_config.yml
|
||||
when: sshd_config_namespace is none
|
||||
|
|
16
tasks/selinux.yml
Normal file
16
tasks/selinux.yml
Normal file
|
@ -0,0 +1,16 @@
|
|||
---
|
||||
- name: Ensure the custom ports are configured in selinux
|
||||
ansible.builtin.include_role:
|
||||
name: fedora.linux_system_roles.selinux
|
||||
vars:
|
||||
selinux_ports:
|
||||
- ports: "{{ sshd_item }}"
|
||||
proto: tcp
|
||||
setype: ssh_port_t
|
||||
state: present
|
||||
local: true
|
||||
loop: "{{ __sshd_ports_from_config | from_json | d([]) }}"
|
||||
loop_control:
|
||||
loop_var: sshd_item # avoid conflicts with the selinux loops
|
||||
when:
|
||||
- __sshd_ports_from_config | from_json != [22]
|
|
@ -1,3 +1,4 @@
|
|||
---
|
||||
collections:
|
||||
- name: ansible.posix
|
||||
- name: fedora.linux_system_roles
|
||||
|
|
127
tests/tests_firewall_selinux.yml
Normal file
127
tests/tests_firewall_selinux.yml
Normal file
|
@ -0,0 +1,127 @@
|
|||
---
|
||||
- hosts: all
|
||||
vars:
|
||||
__sshd_test_backup_files:
|
||||
- /etc/ssh/sshd_config
|
||||
- /etc/ssh/sshd_config.d/00-ansible_system_role.conf
|
||||
tasks:
|
||||
- name: "Backup configuration files"
|
||||
ansible.builtin.include_tasks: tasks/backup.yml
|
||||
|
||||
##########
|
||||
# First test: default port
|
||||
##########
|
||||
- name: Configure the role on default port and let it handle firewall settings
|
||||
ansible.builtin.include_role:
|
||||
name: ansible-sshd
|
||||
vars:
|
||||
sshd_manage_selinux: true
|
||||
sshd_manage_firewall: true
|
||||
sshd:
|
||||
Port: 22
|
||||
|
||||
- name: Verify the options are correctly set
|
||||
block:
|
||||
- name: Flush handlers
|
||||
ansible.builtin.meta: flush_handlers
|
||||
|
||||
- name: Print current configuration file
|
||||
ansible.builtin.slurp:
|
||||
src: "{{ main_sshd_config }}"
|
||||
register: config
|
||||
|
||||
- name: Check the options are in configuration file
|
||||
ansible.builtin.assert:
|
||||
that:
|
||||
- "'Port 22' in config.content | b64decode"
|
||||
tags: tests::verify
|
||||
|
||||
##########
|
||||
# Second test: non-default port
|
||||
##########
|
||||
# is this going to break some tests running ansible through ssh?
|
||||
- name: Configure the role on another port and let it handle firewall settings
|
||||
ansible.builtin.include_role:
|
||||
name: ansible-sshd
|
||||
vars:
|
||||
sshd_manage_firewall: true
|
||||
sshd_manage_selinux: true
|
||||
sshd:
|
||||
Port: 222
|
||||
|
||||
- name: Verify the options are correctly set
|
||||
block:
|
||||
- name: Flush handlers
|
||||
ansible.builtin.meta: flush_handlers
|
||||
|
||||
- name: Print current configuration file
|
||||
ansible.builtin.slurp:
|
||||
src: "{{ main_sshd_config }}"
|
||||
register: config
|
||||
|
||||
- name: Check the options are in configuration file
|
||||
ansible.builtin.assert:
|
||||
that:
|
||||
- "'Port 222' in config.content | b64decode"
|
||||
tags: tests::verify
|
||||
|
||||
##########
|
||||
# Third test: multiple ports
|
||||
##########
|
||||
- name: Configure the role on several ports and let it handle firewall settings
|
||||
ansible.builtin.include_role:
|
||||
name: ansible-sshd
|
||||
vars:
|
||||
sshd_manage_firewall: true
|
||||
sshd_manage_selinux: true
|
||||
sshd:
|
||||
Port:
|
||||
- 22
|
||||
- 222
|
||||
|
||||
- name: Verify the options are correctly set
|
||||
block:
|
||||
- name: Flush handlers
|
||||
ansible.builtin.meta: flush_handlers
|
||||
|
||||
- name: Print current configuration file
|
||||
ansible.builtin.slurp:
|
||||
src: "{{ main_sshd_config }}"
|
||||
register: config
|
||||
|
||||
- name: Check the options are in configuration file
|
||||
ansible.builtin.assert:
|
||||
that:
|
||||
- "'Port 222' in config.content | b64decode"
|
||||
tags: tests::verify
|
||||
|
||||
##########
|
||||
# Cleanup
|
||||
##########
|
||||
- name: "Restore configuration files"
|
||||
ansible.builtin.include_tasks: tasks/restore.yml
|
||||
|
||||
- name: Remove the modification to the firewall rules
|
||||
ansible.builtin.include_role:
|
||||
name: fedora.linux_system_roles.firewall
|
||||
vars:
|
||||
firewall:
|
||||
- port: "222/tcp"
|
||||
state: disabled
|
||||
when:
|
||||
- ansible_facts['os_family'] == 'RedHat'
|
||||
- ansible_virtualization_type|default(None) not in __sshd_skip_virt_env
|
||||
|
||||
- name: Remove the modification to the selinux policy
|
||||
ansible.builtin.include_role:
|
||||
name: fedora.linux_system_roles.firewall
|
||||
vars:
|
||||
selinux:
|
||||
port: 222
|
||||
proto: tcp
|
||||
setype: ssh_port_t
|
||||
state: absent
|
||||
local: true
|
||||
when:
|
||||
- ansible_facts['os_family'] == 'RedHat'
|
||||
- ansible_virtualization_type|default(None) not in __sshd_skip_virt_env
|
Loading…
Reference in a new issue