phpmultithreadingnginxhigh-load

How php-fpm manages workers with dynamic process manager?


I would like to clarify how php-fpm manages workers with dynamic process manager.

Let's assume we have following config:

pm = dynamic
pm.max_children = 100
pm.start_servers = 30
pm.min_spare_servers = 20
pm.max_spare_servers = 60
  1. when php-fpm starts, it spawns 30 processes
  2. there are no connections. Will the php-fpm shut down 10 workers according to min_spare_servers setting? If yes, after what time will it happen?
  3. There are 40 connections to nginx. Will php-fpm serve each connection with separate worker, and immediately spawn additional workers to satisfy remaining connections?
  4. There are 80 connections to nginx. How will php-fpm behave after it has launched 60 workers? The same as in (3)?
  5. There are 120 connections to nginx. What happens after assigning 100 workers to 100 connections? Does php-fpm use some queue for the connections? Will it limit nginx? Will php-fpm start dropping connections with message "server reached pm.max_children setting"?
    1. There are 50 connections to nginx. Will nginx go back to 60 connections from 100? Or to 50? Will it immediately kill 40 workers or will it wait some time?

As you see, this is rather a generalized question about how php-fpm manages processes. More specifically, I would like to understand the difference between pm.max_children and pm.max_spare_servers in php-fpm.


Solution

  • First of all, let's assume that instead of nginx connection we speak about connection/request to upstream, that php-fpm serves.

    1. there are no connections. Will the php-fpm shut down 10 workers according to min_spare_servers setting? If yes, after what time will it happen?

    No, according to my test, master process does not terminate extra workers according to min_spare_servers number. Probably, it is good practice to specify start_servers equal to min_spare_servers.

    1. There are 40 connections to nginx. Will php-fpm serve each connection with separate worker, and immediately spawn additional workers to satisfy remaining connections?

    Correct, simultaneous connections to php-fpm will be served with separate worker. If number of requests is more than start_servers master process will fork additional workers (fpm_children_make call), up to max_spare_servers.

    1. There are 80 connections to nginx. How will php-fpm behave after it has launched 60 workers? The same as in (3)?

    It will fork as many workers as necessary to process all requests simultaneously, until it will reach max_children number; fpm master process performs maintenance every second (fpm_pctl_perform_idle_server_maintenance call): if number of spawned workers are more than max_spare_servers, workers in idle state will send SIGCHLD signal to master process (fpm_got_signal and fpm_children_bury calls).

    1. There are 120 connections to nginx. What happens after assigning 100 workers to 100 connections? Does php-fpm use some queue for the connections? Will it limit nginx? Will php-fpm start dropping connections with message "server reached pm.max_children setting"?

    Correct, you will follow message in debug mode: seems busy (you may need to increase pm.start_servers, or pm.min/max_spare_servers

    1. There are 50 connections to nginx. Will nginx go back to 60 connections from 100? Or to 50? Will it immediately kill 40 workers or will it wait some time?

    All workers in idle state will be terminated, and master process will stop termination after number max_spare_servers is reached.
    Parameters min_spare_servers and max_spare_servers are responsible for min and max numbers of workers that can be alive in idle state at the same time.


    In order to understand dipper, try to turn on debug logging in php-fpm.conf: ... error_log = /var/log/php5-fpm/fpm-daemon.log ... log_level = debug ... Follow log file: tail -f /var/log/php5-fpm/fpm-daemon.log and use Apache benchmark tool ab to understand behavior.