如何使用Ansible为MariaDB / MySQL数据库设置随机(32个字符的字母数字)root密码并将其保存到~/.my.cnf
文件(以允许命令查找此密码)?
它应该只配置一次,并且如果多次运行该剧本,则不会每次都更改密码。
This使用变量中的密码。
如果我使用它,它会在每次运行剧本时更改密码:(并且无法保存密码 - 如果在此任务之后剧照被中断,则密码丢失)
- name: "Change database root user password"
mysql_user:
name: root
password: "{{ lookup('password','/dev/null chars=ascii_letters,digits length=32') }}"
host: "{{ item }}"
check_implicit_admin: yes
priv: "*.*:ALL,GRANT"
state: present
when: mysql_root_result.stat.exists == False
with_items:
- localhost
- "::1"
- 127.0.0.1
答案 0 :(得分:1)
一些假设:
'root'@'localhost'
充分覆盖,并且需要删除其他本地root用户~/.my.cnf
扩展为/root/.my.cnf
~/.my.cnf
获取密码(所有常规工具都可以,只要他们以正确的用户身份运行,在这种情况下为root
)概述:
~/.my.cnf.new
(确保它在设置之前在服务器上可用。如果中断,则允许(手动)恢复)mv
's functionality in two tasks - 硬链接并删除)(link
和unlink
)'root'@'127.0.0.1'
,'root'@'::1'
,'root'@'<hostname>'
(使用一些事实来确保大多数可能性被击中)密码配置模板:(&#39; templates / my_passwd.cnf.j2&#39;相对于角色目录)
[client]
user={{ item.user }}
password={{ item.password }}
任务:
# MariaDB: Set up secure root password
# Set up (and save) secure root password
# Check for /root/.my.cnf
# All the other things are skipped if this file already exists
- name: "Check if we already have a root password config"
stat:
path: /root/.my.cnf
register: mysql_root_result
# Generate password
# This uses https://docs.ansible.com/ansible/latest/plugins/lookup/password.html
# to generate a 32 character random alphanumeric password
- name: "Generate database root password if needed"
set_fact:
mysql_root_passwd: "{{ lookup('password','/dev/null chars=ascii_letters,digits length=32') }}"
when: mysql_root_result.stat.exists == False
# Generate /root/.my.cnf.new
# A temporary file is used to keep it from breaking further commands
# It also ensures that the password is on the server if the critical
# parts are interrupted
- name: "Save new root password in temporary file"
template:
src: my_passwd.cnf.j2
dest: /root/.my.cnf.new
owner: root
group: root
mode: 0400
when: mysql_root_result.stat.exists == False
with_items:
- user: root
password: "{{ mysql_root_passwd }}"
# START of area that you don't want to interrupt
# If this is interrupted after the first task
# it can be fixed by manually running this on the server
# mv /root/.my.cnf.new /root/.my.cnf
# If the playbook is reran before that. The password would be lost!
# Add DB user
- name: "Add database root user"
mysql_user:
name: root
password: "{{ mysql_root_passwd }}"
host: "{{ item }}"
check_implicit_admin: yes
priv: "*.*:ALL,GRANT"
state: present
when: mysql_root_result.stat.exists == False
with_items:
- localhost
# Now move the config in place
- name: "Rename config with root password to correct name - Step 1 - link"
file:
state: hard
src: /root/.my.cnf.new
dest: /root/.my.cnf
force: yes
when: mysql_root_result.stat.exists == False
# END of area that you don't want to interrupt
# Interrupting before this task will leave a temporary file around
# Everything will work as it should though
- name: "Rename config with root password to correct name - Step 2 - unlink"
file:
state: absent
path: /root/.my.cnf.new
when: mysql_root_result.stat.exists == False
# Remove additional root users - these don't have the password set
# You might want to ensure that none of these variables are `localhost`
# All return somewhat different values on my test system
- name: "Clean up additional root users"
mysql_user:
name: root
host: "{{ item }}"
check_implicit_admin: yes
state: absent
with_items:
- "::1"
- 127.0.0.1
- "{{ ansible_fqdn }}"
- "{{ inventory_hostname }}"
- "{{ ansible_hostname }}"