├── tests ├── inventory └── test.yml ├── templates ├── root-my-cnf.j2 └── my.cnf.j2 ├── handlers └── main.yml ├── tasks ├── main.yml ├── percona.yml ├── repo.yml ├── createdatabase.yml └── install.yml ├── meta └── main.yml ├── defaults └── main.yml ├── .gitignore ├── .travis.yml └── README.md /tests/inventory: -------------------------------------------------------------------------------- 1 | localhost 2 | -------------------------------------------------------------------------------- /templates/root-my-cnf.j2: -------------------------------------------------------------------------------- 1 | [client] 2 | user=root 3 | password={{ root_password }} 4 | -------------------------------------------------------------------------------- /handlers/main.yml: -------------------------------------------------------------------------------- 1 | --- 2 | - name: restart percona 3 | action: service name=mysql state=restarted 4 | -------------------------------------------------------------------------------- /tasks/main.yml: -------------------------------------------------------------------------------- 1 | --- 2 | - include: percona.yml 3 | when: ansible_distribution in ['Debian', 'Ubuntu'] 4 | -------------------------------------------------------------------------------- /tasks/percona.yml: -------------------------------------------------------------------------------- 1 | --- 2 | # file: tasks/percona.yml 3 | 4 | - include: repo.yml 5 | - include: install.yml 6 | - include: createdatabase.yml 7 | when: create_app_db 8 | -------------------------------------------------------------------------------- /tests/test.yml: -------------------------------------------------------------------------------- 1 | --- 2 | - hosts: all 3 | user: vagrant 4 | sudo: true 5 | vars: 6 | - db_name: mydb 7 | - db_user: test 8 | - db_host: localhost 9 | - db_user_password: password 10 | - sqldebug: false 11 | roles: 12 | - ansible-percona 13 | -------------------------------------------------------------------------------- /meta/main.yml: -------------------------------------------------------------------------------- 1 | --- 2 | galaxy_info: 3 | author: "Juan Mesa" 4 | company: gochos 5 | license: BSD 6 | min_ansible_version: 1.4 7 | platforms: 8 | - name: Ubuntu 9 | versions: 10 | - saucy 11 | - precise 12 | - name: Debian 13 | versions: 14 | - wheezy 15 | - squeeze 16 | categories: 17 | - database 18 | dependecies: [] 19 | -------------------------------------------------------------------------------- /tasks/repo.yml: -------------------------------------------------------------------------------- 1 | --- 2 | # file: tasks/repo.tml 3 | 4 | - name: Obtaining percona public key 5 | apt_key: url=http://www.percona.com/downloads/RPM-GPG-KEY-percona 6 | state=present 7 | 8 | - name: Adding percona repository 9 | apt_repository: repo='deb http://repo.percona.com/apt {{ ansible_distribution_release }} main' 10 | state=present 11 | 12 | - name: Adding percona source repository 13 | apt_repository: repo='deb-src http://repo.percona.com/apt {{ ansible_distribution_release }} main' 14 | state=present 15 | 16 | - name: Update apt cache 17 | apt: update_cache=yes 18 | 19 | -------------------------------------------------------------------------------- /defaults/main.yml: -------------------------------------------------------------------------------- 1 | --- 2 | # Define root password for percona server 3 | root_password: reallylongpassword 4 | 5 | # Some defaults variables for percona server config file 6 | port: 3306 7 | bind_address: 0.0.0.0 8 | max_allowed_packet: 16M 9 | key_buffer: 16M 10 | thread_stack: 192K 11 | thread_cache_size: 8 12 | # Uncomment following vars if you want to log queries 13 | sqldebug: true 14 | log_slow_queries: log_slow_queries = /var/log/mysql/mysql-slow.log 15 | long_query_time: long_query_time = 2 16 | log_queries_not_using_indexes: log-queries-not-using-indexes 17 | 18 | # Define is a database must be created 19 | create_app_db: true 20 | db_name: mydatabase 21 | db_collation: utf8_general_ci 22 | db_user: myuser 23 | db_user_password: anotherreallylongpassword 24 | db_host: "%" 25 | db_dump_file: "" 26 | -------------------------------------------------------------------------------- /tasks/createdatabase.yml: -------------------------------------------------------------------------------- 1 | --- 2 | - name: Create application database 3 | mysql_db: name={{ db_name }} state=present collation={{ db_collation }} 4 | tags: 5 | - createdatabase 6 | 7 | - name: Copy SQL dump file to the server 8 | copy: src={{ db_dump_file }} dest=/tmp 9 | when: db_dump_file != "" 10 | tags: 11 | - copydumpfile 12 | - dumpfile 13 | 14 | - name: Dump file into the database 15 | mysql_db: name={{ db_name }} state=import target=/tmp/{{ db_dump_file | basename }} 16 | when: db_dump_file != "" 17 | tags: 18 | - dumpfile 19 | 20 | - name: Create Application user database 21 | mysql_user: name={{ db_user }} password={{ db_user_password }} priv={{ db_name }}.*:ALL host={{ db_host }} state=present 22 | tags: 23 | - createuserdatabase 24 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Test files 2 | dump.sql.bz2 3 | 4 | # VIM specific files 5 | [._]*.s[a-w][a-z] 6 | [._]s[a-w][a-z] 7 | *.un~ 8 | Session.vim 9 | .netrwhist 10 | *~ 11 | 12 | # Byte-compiled / optimized / DLL files 13 | __pycache__/ 14 | *.py[cod] 15 | 16 | # C extensions 17 | *.so 18 | 19 | # Distribution / packaging 20 | .Python 21 | env/ 22 | bin/ 23 | build/ 24 | develop-eggs/ 25 | dist/ 26 | eggs/ 27 | lib/ 28 | lib64/ 29 | parts/ 30 | sdist/ 31 | var/ 32 | *.egg-info/ 33 | .installed.cfg 34 | *.egg 35 | 36 | # Installer logs 37 | pip-log.txt 38 | pip-delete-this-directory.txt 39 | 40 | # Unit test / coverage reports 41 | htmlcov/ 42 | .tox/ 43 | .coverage 44 | .cache 45 | nosetests.xml 46 | coverage.xml 47 | 48 | # Translations 49 | *.mo 50 | 51 | # Mr Developer 52 | .mr.developer.cfg 53 | .project 54 | .pydevproject 55 | 56 | # Rope 57 | .ropeproject 58 | 59 | # Django stuff: 60 | *.log 61 | *.pot 62 | 63 | # Sphinx documentation 64 | docs/_build/ 65 | 66 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | --- 2 | language: python 3 | python: "2.7" 4 | 5 | before_install: 6 | - sudo apt-get update -qq 7 | # Remove MySQL 8 | - sudo apt-get -f install -o Dpkg::Options::="--force-overwrite" 9 | - sudo apt-get remove --purge -s mysql\* 10 | - sudo apt-get autoremove 11 | - sudo apt-get autoclean 12 | - sudo rm -rf /var/lib/mysql 13 | - sudo truncate -s 0 /var/log/mysql/error.log 14 | 15 | install: 16 | - pip install ansible 17 | 18 | - "{ echo '[defaults]'; echo 'roles_path = ../'; } >> ansible.cfg" 19 | 20 | script: 21 | # Check role systax 22 | - "ansible-playbook -i tests/inventory tests/test.yml --syntax-check" 23 | # Run role with ansible-playbook 24 | - "ansible-playbook -i tests/inventory tests/test.yml --connection=local" 25 | # Test role idempotence 26 | - > 27 | ansible-playbook -i tests/inventory tests/test.yml --connection=local 28 | | grep -q 'changed=0.*failed=0' 29 | && (echo 'Idempotence test: pass' && exit 0) 30 | || (echo 'Idempotence test: fail' && exit 1) 31 | # Test MySQL connection 32 | - > 33 | mysql -u root -preallylongpassword -e 'show databases;' 34 | | grep -q 'performance_schema' 35 | && (echo 'MySQL running normally' && exit 0) 36 | || (echo 'MySQL not running' && exit 1) 37 | -------------------------------------------------------------------------------- /tasks/install.yml: -------------------------------------------------------------------------------- 1 | --- 2 | - name: Ensure MySQL server is uninstalled 3 | action: apt pkg={{ item }} state=absent 4 | with_items: 5 | - mysql-server-core-5.5 6 | - mysql-client 7 | - mysql-client-5.5 8 | - mysql-client-core-5.5 9 | 10 | - name: Install percona database server 11 | action: apt pkg={{ item }} state=latest 12 | with_items: 13 | - percona-server-server-5.5 14 | - percona-server-client-5.5 15 | - percona-toolkit 16 | - percona-xtrabackup 17 | - python-mysqldb 18 | 19 | - name: Copy .my.cnf file into the root home folder 20 | template: src=root-my-cnf.j2 dest=/root/.my.cnf owner=root mode=0600 21 | 22 | - name: Update MySQL root password 23 | mysql_user: name=root host={{ item }} password={{ root_password }} login_user=root login_password={{ root_password }} check_implicit_admin=yes 24 | with_items: 25 | - "{{ ansible_hostname }}" 26 | - 127.0.0.1 27 | - localhost 28 | 29 | - name: Ensure anonymous users are not in the database 30 | mysql_user: name='' host={{ item }} state=absent 31 | with_items: 32 | - "{{ ansible_hostname }}" 33 | - localhost 34 | 35 | - name: remove test database 36 | mysql_db: name=test state=absent 37 | 38 | - name: Create fnv1a_64 39 | shell: /usr/bin/mysql -e "CREATE FUNCTION fnv1a_64 RETURNS INTEGER SONAME 'libfnv1a_udf.so'" && touch /var/log/libfnv1a_udf.so.done creates=/var/log/libfnv1a_udf.so.done 40 | 41 | - name: Create fnv_64 42 | shell: /usr/bin/mysql -e "CREATE FUNCTION fnv_64 RETURNS INTEGER SONAME 'libfnv_udf.so'" && touch /var/log/libfnv_udf.so.done creates=/var/log/libfnv_udf.so.done 43 | 44 | - name: Create murmur_hash 45 | shell: /usr/bin/mysql -e "CREATE FUNCTION murmur_hash RETURNS INTEGER SONAME 'libmurmur_udf.so'" && touch /var/log/libmurmur_udf.so.done creates=/var/log/libmurmur_udf.so.done 46 | 47 | - name: Write custom server configuration 48 | template: src=my.cnf.j2 dest=/etc/mysql/my.cnf owner=root mode=0644 49 | notify: 50 | - restart percona 51 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Ansible Role: Percona 2 | 3 | Ansible playbook to install percona MySQL server in Debian/Ubuntu servers 4 | 5 | [![Build Status](https://api.travis-ci.org/overdrive3000/ansible-percona.svg)](https://travis-ci.org/overdrive3000/ansible-percona/) 6 | 7 | ## Requirements 8 | 9 | None. 10 | 11 | ## Role Variables 12 | 13 | Available variables are listed below with its default values. 14 | 15 | root_password: reallylongpassword 16 | 17 | Define the MySQL root password, this password will be used to create a **/root/.my.cnf** to allow root mysql connections without password 18 | 19 | port: 3306 20 | bind_address: 0.0.0.0 21 | 22 | Define port and bind address for MySQL connections 23 | 24 | max_allowed_packet: 16M 25 | key_buffer: 16M 26 | thread_stack: 192K 27 | thread_cache_size: 8 28 | 29 | Define some values to tuning the database server 30 | 31 | sqldebug: true 32 | log_slow_queries: log_slow_queries = /var/log/mysql/mysql-slow.log 33 | long_query_time: long_query_time = 2 34 | log_queries_not_using_indexes: log-queries-not-using-indexes 35 | 36 | If **sqldebug** is true this playbook will configure Percona MySQL with slow queries debug logs, if you want to disable this debug information you have to set **sqldebug: false** 37 | 38 | create_app_db: true 39 | db_name: mydatabase 40 | db_collation: utf8_general_ci 41 | db_user: myuser 42 | db_user_password: anotherreallylongpassword 43 | db_host: "%" 44 | db_dump_file: "" 45 | 46 | If **create_app_db** is true this playbook will configura an application database, you can set a path for a SQL dump file if you want to restore data in the new application database 47 | 48 | ## Dependencies 49 | 50 | None. 51 | 52 | ## Example Playbook 53 | 54 | --- 55 | - hosts: all 56 | user: vagrant 57 | sudo: true 58 | vars: 59 | - db_name: mydb 60 | - db_user: myuser 61 | - db_host: localhost 62 | - db_user_password: mypassword 63 | - db_dump_file: /tmp/dump.sql.bz2 64 | roles: 65 | - overdrive3000.ansible-percona 66 | 67 | ## License 68 | 69 | MIT / BSD 70 | 71 | ## Notes 72 | 73 | This is my first playbook it is a beta version and can be improved, please help me to improve and fix bugs for this playbook. 74 | 75 | Thanks. 76 | -------------------------------------------------------------------------------- /templates/my.cnf.j2: -------------------------------------------------------------------------------- 1 | # NOTE: This file is automaticaly generated by Ansible 2 | # please do not change any variable in this config file 3 | # or will be override by ansible 4 | # 5 | # The MySQL database server configuration file. 6 | # 7 | # You can copy this to one of: 8 | # - "/etc/mysql/my.cnf" to set global options, 9 | # - "~/.my.cnf" to set user-specific options. 10 | # 11 | # One can use all long options that the program supports. 12 | # Run program with --help to get a list of available options and with 13 | # --print-defaults to see which it would actually understand and use. 14 | # 15 | # For explanations see 16 | # http://dev.mysql.com/doc/mysql/en/server-system-variables.html 17 | 18 | # This will be passed to all mysql clients 19 | # It has been reported that passwords should be enclosed with ticks/quotes 20 | # escpecially if they contain "#" chars... 21 | # Remember to edit /etc/mysql/debian.cnf when changing the socket location. 22 | [client] 23 | port = {{ port }} 24 | socket = /var/run/mysqld/mysqld.sock 25 | 26 | # Here is entries for some specific programs 27 | # The following values assume you have at least 32M ram 28 | 29 | # This was formally known as [safe_mysqld]. Both versions are currently parsed. 30 | [mysqld_safe] 31 | socket = /var/run/mysqld/mysqld.sock 32 | nice = 0 33 | 34 | [mysqld] 35 | # 36 | # * Basic Settings 37 | # 38 | user = mysql 39 | pid-file = /var/run/mysqld/mysqld.pid 40 | socket = /var/run/mysqld/mysqld.sock 41 | port = {{ port }} 42 | basedir = /usr 43 | datadir = /var/lib/mysql 44 | tmpdir = /tmp 45 | lc-messages-dir = /usr/share/mysql 46 | skip-external-locking 47 | # 48 | # Instead of skip-networking the default is now to listen only on 49 | # localhost which is more compatible and is not less secure. 50 | bind-address = {{ bind_address }} 51 | # 52 | # * Fine Tuning 53 | # 54 | key_buffer = {{ key_buffer }} # 16M 55 | max_allowed_packet = {{ max_allowed_packet }} # 16M 56 | thread_stack = {{ thread_stack }} # 192K 57 | thread_cache_size = {{ thread_cache_size }} # 8 58 | # This replaces the startup script and checks MyISAM tables if needed 59 | # the first time they are touched 60 | myisam-recover = BACKUP 61 | #max_connections = 100 62 | #table_cache = 64 63 | #thread_concurrency = 10 64 | # 65 | # * Query Cache Configuration 66 | # 67 | query_cache_limit = 1M 68 | query_cache_size = 16M 69 | # 70 | # * Logging and Replication 71 | # 72 | # Both location gets rotated by the cronjob. 73 | # Be aware that this log type is a performance killer. 74 | # As of 5.1 you can enable the log at runtime! 75 | #general_log_file = /var/log/mysql/mysql.log 76 | #general_log = 1 77 | # 78 | # Error logging goes to syslog due to /etc/mysql/conf.d/mysqld_safe_syslog.cnf. 79 | # 80 | # Here you can see queries with especially long duration 81 | {% if sqldebug %} 82 | {{ log_slow_queries }} 83 | {{ long_query_time }} 84 | {{ log_queries_not_using_indexes }} 85 | {% endif -%} 86 | # 87 | # The following can be used as easy to replay backup logs or for replication. 88 | # note: if you are setting up a replication slave, see README.Debian about 89 | # other settings you may need to change. 90 | #server-id = 1 91 | #log_bin = /var/log/mysql/mysql-bin.log 92 | expire_logs_days = 10 93 | max_binlog_size = 100M 94 | #binlog_do_db = include_database_name 95 | #binlog_ignore_db = include_database_name 96 | # 97 | # * InnoDB 98 | # 99 | # InnoDB is enabled by default with a 10MB datafile in /var/lib/mysql/. 100 | # Read the manual for more InnoDB related options. There are many! 101 | # 102 | # * Security Features 103 | # 104 | # Read the manual, too, if you want chroot! 105 | # chroot = /var/lib/mysql/ 106 | # 107 | # For generating SSL certificates I recommend the OpenSSL GUI "tinyca". 108 | # 109 | # ssl-ca=/etc/mysql/cacert.pem 110 | # ssl-cert=/etc/mysql/server-cert.pem 111 | # ssl-key=/etc/mysql/server-key.pem 112 | 113 | 114 | 115 | [mysqldump] 116 | quick 117 | quote-names 118 | max_allowed_packet = 16M 119 | 120 | [mysql] 121 | #no-auto-rehash # faster start of mysql but no tab completition 122 | 123 | [isamchk] 124 | key_buffer = 16M 125 | 126 | # 127 | # * IMPORTANT: Additional settings that can override those from this file! 128 | # The files must end with '.cnf', otherwise they'll be ignored. 129 | # 130 | !includedir /etc/mysql/conf.d/ 131 | --------------------------------------------------------------------------------