角色功能说明:
- 该角色实现对客户端主机的安全加固和规避以及回滚功能
角色部署:
- 创建目录结构,创建软连接,关联默认变量文件
WorkDir=~/devops/ansible/os_init && cd ${WorkDir}
RoleName=security_reinforce
mkdir -pv roles/${RoleName}/{defaults,files,handlers,meta,tasks,templates,vars}
ln -s ${WorkDir}/defaults_var.yml roles/${RoleName}/defaults/main.yml
- 配置系统密码加固模版文件
cat >roles/${RoleName}/templates/login.defs_centos6.j2<<EOF
MAIL_DIR /var/spool/mail
PASS_MAX_DAYS 90
PASS_MIN_DAYS 7
PASS_MIN_LEN 8
PASS_WARN_AGE 30
UID_MIN 500
UID_MAX 60000
GID_MIN 500
GID_MAX 60000
CREATE_HOME yes
UMASK 077
USERGROUPS_ENAB yes
ENCRYPT_METHOD SHA512
EOF
cat >roles/${RoleName}/templates/login.defs_centos7.j2<<EOF
MAIL_DIR /var/spool/mail
PASS_MAX_DAYS 90
PASS_MIN_DAYS 7
PASS_MIN_LEN 8
PASS_WARN_AGE 30
UID_MIN 1000
UID_MAX 60000
SYS_UID_MIN 201
SYS_UID_MAX 999
GID_MIN 1000
GID_MAX 60000
SYS_GID_MIN 201
SYS_GID_MAX 999
CREATE_HOME yes
UMASK 077
USERGROUPS_ENAB yes
ENCRYPT_METHOD SHA512
EOF
- 配置系统密码pam加固模版文件
cat >roles/${RoleName}/templates/system-auth-ac_centos6.j2<<EOF
auth required pam_env.so
auth sufficient pam_unix.so nullok try_first_pass
auth requisite pam_succeed_if.so uid >= 500 quiet
auth required pam_deny.so
account required pam_unix.so
account sufficient pam_localuser.so
account sufficient pam_succeed_if.so uid < 500 quiet
account required pam_permit.so
password requisite pam_cracklib.so minlen=8 dcredit=-1 ucredit=-1 ocredit=-1 lcredit=-1 enforce_for_root try_first_pass retry=3 type=
password required pam_pwhistory.so use_authtok remember=3 enforce_for_root
password sufficient pam_unix.so sha512 shadow nullok try_first_pass use_authtok
password required pam_deny.so
session optional pam_keyinit.so revoke
session required pam_limits.so
session [success=1 default=ignore] pam_succeed_if.so service in crond quiet use_uid
session required pam_unix.so
EOF
cat >roles/${RoleName}/templates/system-auth-ac_centos7.j2<<EOF
auth required pam_env.so
auth required pam_faildelay.so delay=2000000
auth sufficient pam_unix.so nullok try_first_pass
auth requisite pam_succeed_if.so uid >= 1000 quiet_success
auth required pam_deny.so
account required pam_unix.so
account sufficient pam_localuser.so
account sufficient pam_succeed_if.so uid < 1000 quiet
account required pam_permit.so
password requisite pam_pwquality.so minlen=8 dcredit=-1 ucredit=-1 ocredit=-1 lcredit=-1 enforce_for_root try_first_pass local_users_only retry=3 authtok_type=
password required pam_pwhistory.so use_authtok remember=3 enforce_for_root
password sufficient pam_unix.so sha512 shadow nullok try_first_pass use_authtok
password required pam_deny.so
session optional pam_keyinit.so revoke
session required pam_limits.so
-session optional pam_systemd.so
session [success=1 default=ignore] pam_succeed_if.so service in crond quiet use_uid
session required pam_unix.so
EOF
- 配置sshd pam加固模版文件
cat >roles/${RoleName}/templates/sshd_centos6.j2<<EOF
auth required pam_tally2.so even_deny_root deny=4 unlock_time=120 root_unlock_time=600
auth required pam_sepermit.so
auth include password-auth
account required pam_nologin.so
account include password-auth
password include password-auth
session required pam_selinux.so close
session required pam_loginuid.so
session required pam_selinux.so open env_params
session required pam_namespace.so
session optional pam_keyinit.so force revoke
session include password-auth
EOF
cat >roles/${RoleName}/templates/sshd_centos7.j2<<EOF
auth required pam_tally2.so even_deny_root deny=4 unlock_time=120 root_unlock_time=600
auth required pam_sepermit.so
auth substack password-auth
auth include postlogin
-auth optional pam_reauthorize.so prepare
account required pam_nologin.so
account include password-auth
password include password-auth
session required pam_selinux.so close
session required pam_loginuid.so
session required pam_selinux.so open env_params
session required pam_namespace.so
session optional pam_keyinit.so force revoke
session include password-auth
session include postlogin
-session optional pam_reauthorize.so prepare
EOF
- 配置su pam加固模版文件
cat >roles/${RoleName}/templates/su_centos6.j2<<EOF
auth sufficient pam_rootok.so
auth required pam_wheel.so use_uid
auth include system-auth
account sufficient pam_succeed_if.so uid = 0 use_uid quiet
account include system-auth
password include system-auth
session include system-auth
session optional pam_xauth.so
EOF
cat >roles/${RoleName}/templates/su_centos7.j2<<EOF
auth sufficient pam_rootok.so
auth required pam_wheel.so use_uid
auth substack system-auth
auth include postlogin
account sufficient pam_succeed_if.so uid = 0 use_uid quiet
account include system-auth
password include system-auth
session include system-auth
session include postlogin
session optional pam_xauth.so
EOF
- 创建系统密码规避策略脚本
cat >roles/${RoleName}/files/userPass.sh<<EOF
#!/bin/bash
source ~/.bash_profile
ChangeDateStr=\$(date +%F)
ExpireDateStr=\$(date -d'90 days' +%F)
for user in \$(grep bash /etc/passwd|awk -F':' '{print \$1}')
do chage -d \${ChangeDateStr} -E \${ExpireDateStr} \${user};done
EOF
- 创建角色任务
cat >roles/${RoleName}/tasks/main.yml<<\EOF
---
- name: "系统用户密码加固"
template:
src: login.defs_centos{{ ansible_distribution_major_version }}.j2
dest: /etc/login.defs
backup: yes
force: yes
owner: root
group: root
mode: 0644
- name: "已存在系统用户密码加固"
shell:
"for user in $(grep bash /etc/passwd|awk -F':' '{print $1}'); \
do chage -m 7 -M 90 -W 30 -d $(date +%F) -E $(date -d'90 days' +%F) ${user};done"
- name: "分发系统用户密码加固脚本"
copy:
src: userPass.sh
dest: /root/checkOS
owner: root
group: root
mode: 0644
- name: "部署系统用户密码加固规避任务"
cron:
name: "userPass"
job: "/bin/bash /root/checkOS/userPass.sh"
minute: "0"
- name: "系统用户密码pam加固"
template:
src: system-auth-ac_centos{{ ansible_distribution_major_version }}.j2
dest: /etc/pam.d/system-auth-ac
backup: yes
force: yes
owner: root
group: root
mode: 0644
- name: "sshd 防暴力破解pam加固"
template:
src: sshd_centos{{ ansible_distribution_major_version }}.j2
dest: /etc/pam.d/sshd
backup: yes
force: yes
owner: root
group: root
mode: 0644
- name: "创建sudoler用户"
user:
name: sudoler
createhome: yes
groups: wheel
- name: "分发ssh公钥到sudoler用户"
authorized_key:
user: sudoler
key: "{{ lookup('file', '~/.ssh/id_rsa.pub') }}"
state: present
- name: "限制su pam加固"
template:
src: su_centos{{ ansible_distribution_major_version }}.j2
dest: /etc/pam.d/su
backup: yes
force: yes
owner: root
group: root
mode: 0644
- name: "限制root ssh登陆"
lineinfile:
path: /etc/ssh/sshd_config
regexp: "^PermitRootLogin"
line: "PermitRootLogin no"
- name: "关闭最后一次ssh登陆信息打印"
lineinfile:
path: /etc/ssh/sshd_config
regexp: "^PrintLastLog"
line: "PrintLastLog no"
- name: "打开ssh登陆后的公告信息"
lineinfile:
path: /etc/ssh/sshd_config
regexp: "^PrintMotd"
line: "PrintMotd yes"
- name: "配置公告信息内容"
copy:
dest: /etc/motd
content: "##################################################\n\
#\t{{ target_hostname_prefix }}-{{ ansible_ssh_host }} 登陆成功\n\
##################################################\n"
- name: "重启sshd服务生效加固项"
service:
name: sshd
state: restarted
- name: "会话超时自动退出"
lineinfile:
path: /etc/profile
line: "export TMOUT=180"
- name: "关闭命令历史记录"
lineinfile:
path: /etc/profile
regexp: "^HISTSIZE"
line: "HISTSIZE=0"
- name: "不回应ping命令"
lineinfile:
path: /etc/sysctl.conf
regexp: "^net.ipv4.icmp_echo_ignore_all"
line: "net.ipv4.icmp_echo_ignore_all = 1"
- name: "执行命令使配置生效"
shell:
"source /etc/profile && sysctl -p"
EOF
- 创建任务playbook并执行
cat >os-init-6.1-${RoleName}-root-setupAll.yml<<EOF
---
- hosts: all
remote_user: root
gather_facts: true
become: no
roles:
- ${RoleName}
EOF
ansible-playbook -i inventory/hosts os-init-6.1-${RoleName}-root-setupAll.yml
重要功能补充:
- 加固项中最为关键的是root ssh远程登陆限制,该项加固回滚策略为:
ansible all -i inventory/hosts -u sudoler -b --become-method=su --become-user=root \
-m lineinfile -a "path=/etc/ssh/sshd_config regexp='^PermitRootLogin' line='PermitRootLogin yes'" -K
ansible all -i inventory/hosts -u sudoler -b --become-method=su --become-user=root \
-m service -a "name=sshd state=restarted" -K
-
注意:安全加固后,sudoler用户只能通过ssh免密登陆,无法通过密码登陆
-
技巧:可以使用-e传入密码来代替-K操作实现非交互
ansible all -i inventory/hosts -u sudoler -b --become-method=su --become-user=root -e 'ansible_become_pass'="vincent" \
-m lineinfile -a "path=/etc/ssh/sshd_config regexp='^PermitRootLogin' line='PermitRootLogin yes'"
ansible all -i inventory/hosts -u sudoler -b --become-method=su --become-user=root -e 'ansible_become_pass'="vincent" \
-m service -a "name=sshd state=restarted"
- 执行过安全加固后,root用户ssh登陆被限制,需要修改os-init.yml后才能再次执行
- 如果是第一次执行,则不能使用sudoler作为执行用户,因为安全加固之前没有该用户
cat >os-init-6.2-${RoleName}-sudoler-resetupAll.yml<<EOF
---
- hosts: all
remote_user: sudoler
gather_facts: true
become: yes
become_user: root
become_method: su
roles:
- ${RoleName}
EOF
ansible-playbook -i inventory/hosts os-init-6.2-${RoleName}-sudoler-resetupAll.yml
- 以playbook的方式回滚掉root远程登陆限制:
cat >os-init-6.3-${RoleName}-sudoler-rollbackRootssh.yml<<EOF
---
- hosts: all
remote_user: sudoler
gather_facts: false
become: yes
become_user: root
become_method: su
tasks:
- name: "剔除sshd配置"
lineinfile:
path: /etc/ssh/sshd_config
regexp: '^PermitRootLogin'
line: 'PermitRootLogin yes'
- name: "重启sshd服务"
service:
name: sshd
state: restarted
EOF
ansible-playbook -i inventory/hosts -e 'ansible_become_pass'="vincent" os-init-6.3-${RoleName}-sudoler-rollbackRootssh.yml
- 重新设置root远程登陆限制:
cat >os-init-6.4-${RoleName}-sudoler-resetupRootssh.yml<<EOF
---
- hosts: all
remote_user: sudoler
gather_facts: false
become: yes
become_user: root
become_method: su
tasks:
- name: "添加sshd配置"
lineinfile:
path: /etc/ssh/sshd_config
regexp: '^PermitRootLogin'
line: 'PermitRootLogin no'
- name: "重启sshd服务"
service:
name: sshd
state: restarted
EOF
ansible-playbook -i inventory/hosts -e 'ansible_become_pass'="vincent" os-init-6.4-${RoleName}-sudoler-resetupRootssh.yml
TOC
346

被折叠的 条评论
为什么被折叠?



