From f1377d1df3e69061f62de75a6b8fcd5296d57cfb Mon Sep 17 00:00:00 2001 From: Scott Walkinshaw Date: Mon, 24 Jul 2023 23:27:47 -0400 Subject: [PATCH 1/2] Add PHP-FPM conf and tuning settings (#1496) Allows customization of the PHP-FPM service configuration. Previously only the _pool_ configuration was exposed in Trellis. This allows for more advanced performance tuning. The PHP-FPM php.ini template is the default values as a starting point. Co-authored-by: Paul Brzeski --- roles/php/defaults/main.yml | 7 + roles/php/tasks/main.yml | 8 +- roles/php/templates/php-fpm.conf.j2 | 153 ++++++++++++++++++ roles/wordpress-setup/tasks/main.yml | 2 +- ...conf.j2 => php-fpm-pool-wordpress.conf.j2} | 0 5 files changed, 168 insertions(+), 2 deletions(-) create mode 100644 roles/php/templates/php-fpm.conf.j2 rename roles/wordpress-setup/templates/{php-fpm.conf.j2 => php-fpm-pool-wordpress.conf.j2} (100%) diff --git a/roles/php/defaults/main.yml b/roles/php/defaults/main.yml index 73a40e58c4..31cd8a096f 100644 --- a/roles/php/defaults/main.yml +++ b/roles/php/defaults/main.yml @@ -31,3 +31,10 @@ php_opcache_max_accelerated_files: 4000 php_opcache_memory_consumption: 128 php_opcache_revalidate_freq: 60 php_opcache_validate_timestamps: 1 + +php_fpm_set_emergency_restart_threshold: false +php_fpm_emergency_restart_threshold: 0 +php_fpm_set_emergency_restart_interval: false +php_fpm_emergency_restart_interval: 0 +php_fpm_set_process_control_timeout: false +php_fpm_process_control_timeout: 0 diff --git a/roles/php/tasks/main.yml b/roles/php/tasks/main.yml index e5fce88125..9606170c88 100644 --- a/roles/php/tasks/main.yml +++ b/roles/php/tasks/main.yml @@ -42,11 +42,17 @@ state: started enabled: true -- name: Copy PHP-FPM configuration file +- name: Copy PHP-FPM php.ini file template: src: php-fpm.ini.j2 dest: /etc/php/{{ php_version }}/fpm/php.ini mode: '0644' + +- name: Copy PHP-FPM configuration file + template: + src: php-fpm.conf.j2 + dest: /etc/php/{{ php_version }}/fpm/php-fpm.conf + mode: '0644' notify: reload php-fpm - name: Copy PHP CLI configuration file diff --git a/roles/php/templates/php-fpm.conf.j2 b/roles/php/templates/php-fpm.conf.j2 new file mode 100644 index 0000000000..57c5fc4922 --- /dev/null +++ b/roles/php/templates/php-fpm.conf.j2 @@ -0,0 +1,153 @@ +; {{ ansible_managed }} + +;;;;;;;;;;;;;;;;;;;;; +; FPM Configuration ; +;;;;;;;;;;;;;;;;;;;;; + +; All relative paths in this configuration file are relative to PHP's install +; prefix (/usr). This prefix can be dynamically changed by using the +; '-p' argument from the command line. + +;;;;;;;;;;;;;;;;;; +; Global Options ; +;;;;;;;;;;;;;;;;;; + +[global] +; Pid file +; Note: the default prefix is /var +; Default Value: none +; Warning: if you change the value here, you need to modify systemd +; service PIDFile= setting to match the value here. +pid = /run/php/php{{ php_version }}-fpm.pid + +; Error log file +; If it's set to "syslog", log is sent to syslogd instead of being written +; into a local file. +; Note: the default prefix is /var +; Default Value: log/php-fpm.log +error_log = /var/log/php{{ php_version }}-fpm.log + +; syslog_facility is used to specify what type of program is logging the +; message. This lets syslogd specify that messages from different facilities +; will be handled differently. +; See syslog(3) for possible values (ex daemon equiv LOG_DAEMON) +; Default Value: daemon +;syslog.facility = daemon + +; syslog_ident is prepended to every message. If you have multiple FPM +; instances running on the same server, you can change the default value +; which must suit common needs. +; Default Value: php-fpm +;syslog.ident = php-fpm + +; Log level +; Possible Values: alert, error, warning, notice, debug +; Default Value: notice +;log_level = notice + +; Log limit on number of characters in the single line (log entry). If the +; line is over the limit, it is wrapped on multiple lines. The limit is for +; all logged characters including message prefix and suffix if present. However +; the new line character does not count into it as it is present only when +; logging to a file descriptor. It means the new line character is not present +; when logging to syslog. +; Default Value: 1024 +;log_limit = 4096 + +; Log buffering specifies if the log line is buffered which means that the +; line is written in a single write operation. If the value is false, then the +; data is written directly into the file descriptor. It is an experimental +; option that can potentionaly improve logging performance and memory usage +; for some heavy logging scenarios. This option is ignored if logging to syslog +; as it has to be always buffered. +; Default value: yes +;log_buffering = no + +; If this number of child processes exit with SIGSEGV or SIGBUS within the time +; interval set by emergency_restart_interval then FPM will restart. A value +; of '0' means 'Off'. +; Default Value: 0 +{% if php_fpm_set_emergency_restart_threshold %} +emergency_restart_threshold = {{ php_fpm_emergency_restart_threshold }} +{% endif %} + +; Interval of time used by emergency_restart_interval to determine when +; a graceful restart will be initiated. This can be useful to work around +; accidental corruptions in an accelerator's shared memory. +; Available Units: s(econds), m(inutes), h(ours), or d(ays) +; Default Unit: seconds +; Default Value: 0 +{% if php_fpm_set_emergency_restart_interval %} +emergency_restart_interval = {{ php_fpm_emergency_restart_interval }} +{% endif %} + +; Time limit for child processes to wait for a reaction on signals from master. +; Available units: s(econds), m(inutes), h(ours), or d(ays) +; Default Unit: seconds +; Default Value: 0 +{% if php_fpm_set_process_control_timeout %} +process_control_timeout = {{ php_fpm_process_control_timeout }} +{% endif %} + +; The maximum number of processes FPM will fork. This has been designed to control +; the global number of processes when using dynamic PM within a lot of pools. +; Use it with caution. +; Note: A value of 0 indicates no limit +; Default Value: 0 +; process.max = 128 + +; Specify the nice(2) priority to apply to the master process (only if set) +; The value can vary from -19 (highest priority) to 20 (lowest priority) +; Note: - It will only work if the FPM master process is launched as root +; - The pool process will inherit the master process priority +; unless specified otherwise +; Default Value: no set +; process.priority = -19 + +; Send FPM to background. Set to 'no' to keep FPM in foreground for debugging. +; Default Value: yes +;daemonize = yes + +; Set open file descriptor rlimit for the master process. +; Default Value: system defined value +;rlimit_files = 1024 + +; Set max core size rlimit for the master process. +; Possible Values: 'unlimited' or an integer greater or equal to 0 +; Default Value: system defined value +;rlimit_core = 0 + +; Specify the event mechanism FPM will use. The following is available: +; - select (any POSIX os) +; - poll (any POSIX os) +; - epoll (linux >= 2.5.44) +; - kqueue (FreeBSD >= 4.1, OpenBSD >= 2.9, NetBSD >= 2.0) +; - /dev/poll (Solaris >= 7) +; - port (Solaris >= 10) +; Default Value: not set (auto detection) +;events.mechanism = epoll + +; When FPM is built with systemd integration, specify the interval, +; in seconds, between health report notification to systemd. +; Set to 0 to disable. +; Available Units: s(econds), m(inutes), h(ours) +; Default Unit: seconds +; Default value: 10 +;systemd_interval = 10 + +;;;;;;;;;;;;;;;;;;;; +; Pool Definitions ; +;;;;;;;;;;;;;;;;;;;; + +; Multiple pools of child processes may be started with different listening +; ports and different management options. The name of the pool will be +; used in logs and stats. There is no limitation on the number of pools which +; FPM can handle. Your system will tell you anyway :) + +; Include one or more files. If glob(3) exists, it is used to include a bunch of +; files from a glob(3) pattern. This directive can be used everywhere in the +; file. +; Relative path can also be used. They will be prefixed by: +; - the global prefix if it's been set (-p argument) +; - /usr otherwise +include=/etc/php/{{ php_version }}/fpm/pool.d/*.conf diff --git a/roles/wordpress-setup/tasks/main.yml b/roles/wordpress-setup/tasks/main.yml index dcdf09df96..890d7078aa 100644 --- a/roles/wordpress-setup/tasks/main.yml +++ b/roles/wordpress-setup/tasks/main.yml @@ -27,7 +27,7 @@ - name: Create WordPress php-fpm configuration file template: - src: php-fpm.conf.j2 + src: php-fpm-pool-wordpress.conf.j2 dest: /etc/php/{{ php_version }}/fpm/pool.d/wordpress.conf mode: '0644' notify: reload php-fpm diff --git a/roles/wordpress-setup/templates/php-fpm.conf.j2 b/roles/wordpress-setup/templates/php-fpm-pool-wordpress.conf.j2 similarity index 100% rename from roles/wordpress-setup/templates/php-fpm.conf.j2 rename to roles/wordpress-setup/templates/php-fpm-pool-wordpress.conf.j2 From e0cdc3d2b1be384c769b48e66d9e5e32acbf5beb Mon Sep 17 00:00:00 2001 From: Scott Walkinshaw Date: Tue, 25 Jul 2023 22:52:50 -0400 Subject: [PATCH 2/2] Add MariaDB server config for optimizatons (#1497) Co-authored-by: Paul Brzeski --- roles/mariadb/defaults/main.yml | 8 +- roles/mariadb/tasks/main.yml | 7 ++ roles/mariadb/templates/50-server.cnf.j2 | 132 +++++++++++++++++++++++ 3 files changed, 146 insertions(+), 1 deletion(-) create mode 100644 roles/mariadb/templates/50-server.cnf.j2 diff --git a/roles/mariadb/defaults/main.yml b/roles/mariadb/defaults/main.yml index b2c4de073e..12a81ad2af 100644 --- a/roles/mariadb/defaults/main.yml +++ b/roles/mariadb/defaults/main.yml @@ -1,6 +1,7 @@ +mariadb_version: 10.6 mariadb_keyserver: "hkp://keyserver.ubuntu.com:80" mariadb_keyserver_id: "0xF1656F24C74CD1D8" -mariadb_ppa: "deb https://mirror.rackspace.com/mariadb/repo/10.6/ubuntu {{ ansible_distribution_release }} main" +mariadb_ppa: "deb https://mirror.rackspace.com/mariadb/repo/{{ mariadb_version }}/ubuntu {{ ansible_distribution_release }} main" mariadb_client_package: mariadb-client mariadb_server_package: mariadb-server @@ -9,3 +10,8 @@ mysql_binary_logging_disabled: true mysql_root_user: root sites_using_remote_db: "[{% for name, site in wordpress_sites.items() | list if site.env is defined and site.env.db_host | default('localhost') != 'localhost' %}'{{ name }}',{% endfor %}]" + +mariadb_set_innodb_buffer_pool_size: false +mariadb_innodb_buffer_pool_size: 128M +mariadb_set_innodb_log_file_size: false +mariadb_innodb_log_file_size: 96M diff --git a/roles/mariadb/tasks/main.yml b/roles/mariadb/tasks/main.yml index 1b2028a308..de3b9fb072 100644 --- a/roles/mariadb/tasks/main.yml +++ b/roles/mariadb/tasks/main.yml @@ -41,6 +41,13 @@ group: root mode: '0600' + - name: Copy server config file with MariaDB optimisations. + template: + src: 50-server.cnf.j2 + dest: /etc/mysql/mariadb.conf.d/50-server.cnf + mode: '0644' + notify: restart mysql server + - name: Set root user password mysql_user: name: root diff --git a/roles/mariadb/templates/50-server.cnf.j2 b/roles/mariadb/templates/50-server.cnf.j2 new file mode 100644 index 0000000000..f46ee20525 --- /dev/null +++ b/roles/mariadb/templates/50-server.cnf.j2 @@ -0,0 +1,132 @@ +# {{ ansible_managed }} +# +# These groups are read by MariaDB server. +# Use it for options that only the server (but not clients) should see + +# this is read by the standalone daemon and embedded servers +[server] + +# this is only for the mysqld standalone daemon +[mysqld] + +# +# * Basic Settings +# + +user = mysql +pid-file = /run/mysqld/mysqld.pid +basedir = /usr +datadir = /var/lib/mysql +tmpdir = /tmp +lc-messages-dir = /usr/share/mysql +lc-messages = en_US +skip-external-locking + +# Broken reverse DNS slows down connections considerably and name resolve is +# safe to skip if there are no "host by domain name" access grants +#skip-name-resolve + +# Instead of skip-networking the default is now to listen only on +# localhost which is more compatible and is not less secure. +bind-address = 127.0.0.1 + +# +# * Fine Tuning +# + +#key_buffer_size = 128M +#max_allowed_packet = 1G +#thread_stack = 192K +#thread_cache_size = 8 +# This replaces the startup script and checks MyISAM tables if needed +# the first time they are touched +#myisam_recover_options = BACKUP +#max_connections = 100 +#table_cache = 64 + +# +# * Logging and Replication +# + +# Both location gets rotated by the cronjob. +# Be aware that this log type is a performance killer. +# Recommend only changing this at runtime for short testing periods if needed! +#general_log_file = /var/log/mysql/mysql.log +#general_log = 1 + +# When running under systemd, error logging goes via stdout/stderr to journald +# and when running legacy init error logging goes to syslog due to +# /etc/mysql/conf.d/mariadb.conf.d/50-mysqld_safe.cnf +# Enable this if you want to have error logging into a separate file +#log_error = /var/log/mysql/error.log +# Enable the slow query log to see queries with especially long duration +#slow_query_log_file = /var/log/mysql/mariadb-slow.log +#long_query_time = 10 +#log_slow_verbosity = query_plan,explain +#log-queries-not-using-indexes +#min_examined_row_limit = 1000 + +# The following can be used as easy to replay backup logs or for replication. +# note: if you are setting up a replication slave, see README.Debian about +# other settings you may need to change. +#server-id = 1 +#log_bin = /var/log/mysql/mysql-bin.log +expire_logs_days = 10 +#max_binlog_size = 100M + +# +# * SSL/TLS +# + +# For documentation, please read +# https://mariadb.com/kb/en/securing-connections-for-client-and-server/ +#ssl-ca = /etc/mysql/cacert.pem +#ssl-cert = /etc/mysql/server-cert.pem +#ssl-key = /etc/mysql/server-key.pem +#require-secure-transport = on + +# +# * Character sets +# + +# MySQL/MariaDB default is Latin1, but in Debian we rather default to the full +# utf8 4-byte character set. See also client.cnf +character-set-server = utf8mb4 +collation-server = utf8mb4_general_ci + +# +# * InnoDB +# + +# InnoDB is enabled by default with a 10MB datafile in /var/lib/mysql/. +# Read the manual for more InnoDB related options. There are many! +# Most important is to give InnoDB 80 % of the system RAM for buffer use: +# https://mariadb.com/kb/en/innodb-system-variables/#innodb_buffer_pool_size + +# Amount of RAM to allocate to database buffering. +# - Max is 80% of total RAM. i.e. 80% of 8G, 6.4G is the max. +# - On server doing PHP and MySQL, don't allocate more than 50% because the rest needs to go to PHP. +# - Default is 128M +{% if mariadb_set_innodb_buffer_pool_size %} +innodb_buffer_pool_size = {{ mariadb_innodb_buffer_pool_size }} +{% endif %} + +# Amount of disk space to allocate to database redo file +# - Should be 25% of buffer pool size as per MySQL Tuner (https://github.com/major/MySQLTuner-perl) +# - Default is 96M +{% if mariadb_set_innodb_log_file_size %} +innodb_log_file_size = {{ mariadb_innodb_log_file_size }} +{% endif %} + +# this is only for embedded server +[embedded] + +# This group is only read by MariaDB servers, not by MySQL. +# If you use the same .cnf file for MySQL and MariaDB, +# you can put MariaDB-only options here +[mariadb] + +# This group is only read by MariaDB-{{mariadb_version}} servers. +# If you use the same .cnf file for MariaDB of different versions, +# use this group for options that older servers don't understand +[mariadb-{{mariadb_version}}]