0

I am trying to create a playbook to run the mysql_secure_installation command.

This command ask several questions. I am using pexpect, but not sure how to simulate an "enter" The first question it asks is "enter a root password" I dont want to enter a root password. The sql server will only be local.

- name: "Secure MariaDB"
  expect:
    command: /bin/mysql_secure_installation
    responses:
      Question:
        - ''          #I want to have ansible hit enter
        - 'n'         # Type n
        - 'y'         # Type y
        - 'y'         # Type y
        - 'y'         # Type y
        - 'y'         # Type y

I have tried with a '', the command /bin/bash -c "echo" and even just a blank line and I keep getting the response below.

FAILED! => {"changed": true, "cmd": "/bin/mysql_secure_installation", "delta": "0:00:30.128184", "end": "2018-08-29 18:54:30.983455", "msg": "non-zero return code", "rc": 1, "start": "2018-08-29 18:54:00.855271", "stdout": "\r\nNOTE: RUNNING ALL PARTS OF THIS SCRIPT IS RECOMMENDED FOR ALL MariaDB\r\n      SERVERS IN PRODUCTION USE!  PLEASE READ EACH STEP CAREFULLY!\r\n\r\nIn order to log into MariaDB to secure it, we'll need the current\r\npassword for the root user.  If you've just installed MariaDB, and\r\nyou haven't set the root password yet, the password will be blank,\r\nso you should just press enter here.\r\n\r\nEnter current password for root (enter for none): ", "stdout_lines": ["", "NOTE: RUNNING ALL PARTS OF THIS SCRIPT IS RECOMMENDED FOR ALL MariaDB", "      SERVERS IN PRODUCTION USE!  PLEASE READ EACH STEP CAREFULLY!", "", "In order to log into MariaDB to secure it, we'll need the current", "password for the root user.  If you've just installed MariaDB, and", "you haven't set the root password yet, the password will be blank,", "so you should just press enter here.", "", "Enter current password for root (enter for none): "]}
1

According to this and this, you need only specify an empty string; Ansible will be automatically follow it with "enter".

If that doesn't work, there is another suggestion here to use /bin/bash -c "echo" for the answer.

1

Got it working. As it turns out some of the stuff was being recoginzed as regex special characters.

- name: "Secure MariaDB"
  expect:
    command: /bin/mysql_secure_installation
    responses:
      'Enter current password for root \(enter for none\): ': ''
      'Set root password\? \[Y\/n\] ': 'n'
      'Remove anonymous users\? \[Y\/n\] ': 'y'
      'Disallow root login remotely\? \[Y\/n\] ': 'y'
      'Remove test database and access to it\? \[Y\/n\] ': 'y'
      'Reload privilege tables now\? \[Y\/n\] ': 'y'
    echo: yes
0

According to the module documentation expect is flagged as preview so may change, and the module is very simple. It may be more sensible to use an expect script; this would allow the detection of each question and the ability to fail out should the questions change in some new version of mysql_secure_installation (or to fail out if someone snuck in and put a password on the root mysql account, or ...)

This is, however, more work as an expect package may need to be installed and the script copied to the system, details will vary depending on the ports or package system involved and where exactly local scripts get installed (hopefully to somewhere untrusted local users cannot read or run them...)

- name: install packages for centos
  yum: name={{ item }} state=present
  with_items:
    - expect
    ...
- name: copy script
  copy: src=root/bin/do-setup-mysql dest=/root/bin/do-setup-mysql ...
- name: initial setup of mysql
  command: /root/bin/do-setup-mysql
  args:
    creates: /todofixme

And then the script do-setup-mysql might start along the lines of:

#!/usr/bin/env expect
proc die {msg} { puts stderr $msg; exit 1 }
#log_file /root/do-setup-mysql.log
spawn -noecho mysql_secure_installation
expect "Enter current password for root"
send "\r"
expect {
    timeout { die "timeout before response" }
    "Access denied" { die "root password already set" }
    "Setting the root password" {}
}
expect "Change the root password"
send "n\r"
...

And so forth for the remainder of the questions. The script must create /todofixme, or that file could instead be something known created by mysql_secure_installation so that the initial setup does not run each and every ansible run.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.