php fpm网站上的文档称,php fpm是自5.3.3 起coe php的一部分
我正在运行5.3.10,如何检查它是否正常工作?我以为这是一项在端口上运行的服务?
假设您在Linux上,通过搜索进程列表来检查php-fpm是否正在运行:
ps aux | grep php-fpm
如果在IP上运行(而不是在Unix套接字上运行),那么您也可以检查端口:
netstat -an | grep :9000
或者使用nmap:
nmap localhost -p 9000
最后,我读到你可以请求状态,但根据我的经验,这被证明是不可靠的:
/etc/init.d/php5-fpm status
对于php7.0-fpm,我调用:
service php7.0-fpm status
php7.0-fpm启动/运行,进程25993
现在注意好的部分。进程名称实际上是php-fpm7.0
echo `/bin/pidof php-fpm7.0`
26334 26297 26286 26285 26282
以下是如何使用php fpm 7 上的套接字实现这一点
install socat
apt-get install socat
#!/bin/sh
if echo /dev/null | socat UNIX:/var/run/php/php7.0-fpm.sock - ; then
echo "$home/run/php-fpm.sock connect OK"
else
echo "$home/run/php-fpm.sock connect ERROR"
fi
您还可以检查服务是否像这样运行。
service php7.0-fpm status | grep running
它将返回
活动:自周日起活动(运行)2017-04-09 12:48:09 PDT;48秒前
如果它在amilinux上帮助安装了php5.6和php-fpm的人,它是:
sudo /etc/init.d/php-fpm-5.6 status
PHP-FPM是一种在需要时生成新PHP进程的服务,通常通过nginx等快速cgi模块。您可以通过检查init.d脚本来判断(有一定的误差),例如"sudo/etc/init.d/php-fpm status"
使用的端口或unix文件套接字取决于配置,但通常只是TCP端口9000。即127.0.0.1:9000
判断它是否正确运行的最好方法是让nginx运行,并设置一个虚拟主机,将cgi快速传递到PHP-FPM,然后用wget或浏览器进行检查。
我在运行cPanel和WHM的Centos 7服务器上挣扎了一段时间,PHP-FPM有时会变得没有响应。PHP-FPM服务显示它正在运行,但不响应请求。
我的数据中心团队也在努力帮助我找到一个永久性的解决方案,但到目前为止,我们运气不佳。
在此期间,我开发了一个Node.js监控系统,该系统通过打开一个在PHP FPM上运行的测试文件来运行。系统在引用服务器的IP地址和站点主机名时同时使用HTTP://和HTTPS://调用,以防止由于网络、DNS或其他相关错误而导致的任何不必要的重新启动。如果系统没有收到有效的响应,它会重新启动PHP FPM并给我发一封电子邮件。
下面是代码和方法,如果有人觉得它有用的话。
在您的服务器上创建一个文件夹,例如/home/itilth/monitor/,并在该文件夹中创建一个名为monitor.js和init.php的文件。在可以在服务器上测试的域上创建一个testFPM.php文件。
---节点进程(monitor.js),您需要安装的唯一模块是axios(例如npm安装axios)
const axios = require('axios');
const { execSync } = require('child_process');
const failureEmail = "[your email address]";
const serverIP = "[server ip]"; //e.g. 8.8.8.8
const testDomain = "[your domain name]"; //e.g. example.com
const testFile = "testFPM.php";
const restartFPMCommand = "/scripts/restartsrv_apache_php_fpm";
const failedEmailCommand = 'mail -s '"FPM Restarted'" '+failureEmail+' < /dev/null';
function date(str,timestamp){
var ret = "";
if(!timestamp){
var timestamp = Math.floor(new Date().getTime() / 1000);
timestamp = timestamp;
}
else{
timestamp = parseInt(timestamp);
}
var d = new Date(timestamp*1000);
if(!str){var str = "Y-m-d H:i:s";}
str = str.split("");
var strc = str.length;
for(var a=0;a<strc;a++){
switch(str[a]) {
case "d":
var m = d.getDate()+""; if(m.length < 2){m = "0"+m;}
ret = ret + m;
break;
case "j":
var m = d.getDate()+"";
ret = ret + m;
break;
case "D":
var m = d.getDay();
if(m == 0){m = "Sun";}
if(m == 1){m = "Mon";}
if(m == 2){m = "Tue";}
if(m == 3){m = "Wed";}
if(m == 4){m = "Thu";}
if(m == 5){m = "Fri";}
if(m == 6){m = "Sat";}
ret = ret + m;
break;
case "N":
var m = d.getDay();
if(m == 0){m = 7;}
ret = ret + m + "";
break;
case "w":
var m = d.getDay();
ret = ret + m + "";
break;
case "z":
var start = new Date(d.getFullYear(), 0, 0);
var diff = d - start;
var daytime = 1000 * 60 * 60 * 24;
var m = Math.floor(diff / daytime) - 1;
ret = ret + m + "";
break;
case "S":
var m = d.getDate();
if(m == 1 || m == 21 || m == 31){m = "st";}
if(m == 2 || m == 22){m = "nd";}
if(m == 3 || m == 23){m = "rd";}
if((m > 3 && m < 21) || (m > 23 && m < 31)){m = "th";}
ret = ret + m;
break;
case "l":
var m = d.getDay();
if(m == 0){m = "Sunday";}
if(m == 1){m = "Monday";}
if(m == 2){m = "Tuesday";}
if(m == 3){m = "Wednesday";}
if(m == 4){m = "Thursday";}
if(m == 5){m = "Friday";}
if(m == 6){m = "Saturday";}
ret = ret + m;
break;
case "W":
var dd = new Date(Date.UTC(d.getFullYear(), d.getMonth(), d.getDate()));
dd.setUTCDate(dd.getUTCDate() + 4 - (dd.getUTCDay()||7));
var year_start = new Date(Date.UTC(dd.getUTCFullYear(),0,1));
var week_no = Math.ceil((((dd-year_start)/86400000)+1)/7);
var m = week_no + "";
ret = ret + m;
break;
case "F":
var m = (d.getMonth()+1);
if(m == 1){m = "January";}
if(m == 2){m = "February";}
if(m == 3){m = "March";}
if(m == 4){m = "April";}
if(m == 5){m = "May";}
if(m == 6){m = "June";}
if(m == 7){m = "July";}
if(m == 8){m = "August";}
if(m == 9){m = "September";}
if(m == 10){m = "October";}
if(m == 11){m = "November";}
if(m == 12){m = "December";}
ret = ret + m;
break;
case "m":
var m = (d.getMonth()+1)+""; if(m.length < 2){m = "0"+m;}
ret = ret + m;
break;
case "M":
var m = (d.getMonth()+1);
if(m == 1){m = "Jan";}
if(m == 2){m = "Feb";}
if(m == 3){m = "Mar";}
if(m == 4){m = "Apr";}
if(m == 5){m = "May";}
if(m == 6){m = "Jun";}
if(m == 7){m = "Jul";}
if(m == 8){m = "Aug";}
if(m == 9){m = "Sep";}
if(m == 10){m = "Oct";}
if(m == 11){m = "Nov";}
if(m == 12){m = "Dec";}
ret = ret + m;
break;
case "n":
var m = (d.getMonth()+1)+"";
ret = ret + m;
break;
case "t":
var m = new Date(d.getFullYear(), d.getMonth()+1, 0);
m = m.getDate();
ret = ret + m + "";
break;
case "L":
var m = new Date(d.getFullYear(), 1, 0);
m = m.getDate();
if(m == 29){m = "1";}
else{m = "0";}
ret = ret + m + "";
break;
case "o":
ret = ret + d.getFullYear()+"";
break;
case "Y":
ret = ret + d.getFullYear()+"";
break;
case "y":
var m = d.getFullYear()+"";
m = m.substr((m.length-2),2);
ret = ret + m + "";
break;
case "a":
var m = d.getHours();
if(m < 12){m = "am"}
else{m = "pm"};
ret = ret + m + "";
break;
case "A":
var m = d.getHours();
if(m < 12){m = "AM"}
else{m = "PM"};
ret = ret + m + "";
break;
case "B":
var m = Math.floor((((d.getUTCHours() + 1) % 24) + d.getUTCMinutes() / 60 + d.getUTCSeconds() / 3600) * 1000 / 24);
ret = ret + m + "";
break;
case "g":
var m = d.getHours();
if(m > 12){m = m - 12;}
ret = ret + m + "";
break;
case "G":
var m = d.getHours();
ret = ret + m + "";
break;
case "h":
var m = d.getHours();
if(m > 12){m = m - 12;}
m = m + ""; if(m.length < 2){m = "0"+m;}
ret = ret + m + "";
break;
case "H":
var m = d.getHours();
m = m + ""; if(m.length < 2){m = "0"+m;}
ret = ret + m + "";
break;
case "i":
var m = d.getMinutes();
m = m + ""; if(m.length < 2){m = "0"+m;}
ret = ret + m + "";
break;
case "s":
var m = d.getSeconds();
m = m + ""; if(m.length < 2){m = "0"+m;}
ret = ret + m + "";
break;
default:
ret = ret + str[a] + "";
}
}
return ret;
}
function log(message){
console.log(date("Y-m-d H:i:s") + " - "+message)
}
var checking = false;
async function checkStatus(host,type){
const startTime = Date.now();
var r = "";
try {
const res = await axios.get(type+serverIP+'/'+testFile, {
timeout: 4000,
headers: {
'Host': host,
// other headers
}
})
const endTime = Date.now();
const elapsedTime = endTime - startTime;
if (res.status >= 200 && res.status < 306) {
if(res.data == "fpm-fcgi"){
r = 'UP in '+elapsedTime+" => "+res.data;
}
else{
r = 'DOWN ' + res.status + " in "+elapsedTime+" => "+res.data;
}
} else {
r = 'DOWN ' + res.status + " in "+elapsedTime;
}
} catch (err) {
r = 'DOWN ' + err.message;
}
return r;
}
async function checkAStatus(){
if(!checking){
checking = true;
var httpStatus = await checkStatus(testDomain,"http://");
var httpsStatus = await checkStatus(testDomain,"https://");
if(httpStatus.substring(0,4) == "DOWN" || httpsStatus.substring(0,4) == "DOWN"){
log("Restarting FPM...");
try {
const output = execSync(restartFPMCommand);
console.log(output.toString());
} catch (error) {
console.error(`execSync error: ${error}`);
}
try {
execSync(failedEmailCommand);
} catch (error) {
console.error(`execSync error: ${error}`);
}
}
log("HTTP: "+httpStatus+" | HTTPS: "+httpsStatus);
checking = false;
}
else{
log("Already checking.");
}
}
// Check the website status every 10 seconds
setInterval(checkAStatus, 10000);
--PHP测试文件(testFPM.PHP)
<?php
$sapiType = php_sapi_name();
echo $sapiType;
?>
--PHP INIT脚本(INIT.PHP),可用于通过cron启动/停止/重新启动和检查监视器进程。此脚本还将监视器日志输出到同一文件夹中的log.log中,可以按如下方式使用。
php/home/itilth/monitor/init.php检查
php/home/itilt/monitor/init.php停止
php/home/itilth/monitor/init.php启动
php/home/itilth/monitor/init.php重新启动
查看日志文件:tail-f/home/itilth/monitor/log.log
#!/usr/bin/php -q
<?
$command = $argv[1];
global $node_process;
global $pid_file;
global $log_file;
global $log_levels;
global $first_log;
$log_levels = array();
$log_levels["error"] = true;
$log_levels["info"] = false;
$log_levels["general"] = true;
$node_process = "node ".__DIR__."/monitor.js";
$pid_file = __DIR__."/pid";
$log_file = __DIR__."/log";
$first_log = true;
function write_log($data,$type="info",$add=false,$nodate=false){
global $log_file;
global $log_levels;
global $first_log;
if($log_levels[$type]){
$date_string = "";
$color = "'x1b[2m";
if($type == "general"){$color = "'x1b[36m";}
if($type == "error"){$color = "'x1b[31m";}
if(!$nodate){
$date = "INIT - ".date("D M d Y H:i:s 'G'M'TO (T) ");
}
else{
$date = "";
}
$string = "";
if(!$add && !$first_log){$string .= "'n";}
$string .= $color;
if(!$add){$string .= $date;}
$string .= $data;
$string .= "'x1b[0m";
if($add){
$string .= "'n";
}
file_put_contents($log_file.".log",$string,FILE_APPEND);
$first_log = false;
}
}
function pid(){
return "test";
}
function is_running(){
global $node_process;
write_log("Checking if process is running.");
$pid = pid();
if($pid != ""){
exec("ps aux | grep node",$output,$result);
$outputc = count($output);
$found = false;
for($a=0;$a<$outputc;$a++){
write_log($output[$a]);
if(strpos($output[$a],$node_process) !== false){
$found = true;
}
}
if($found){
return true;
}
else{
return false;
}
}
else{
return false;
}
}
function start(){
global $node_process;
global $client_user;
if(!is_running()){
write_log("Starting Node Process:");
exec("nohup ".$node_process." >> ".__DIR__."/log".".log 2>&1 &");
write_log("-----------------------------------------------------------------------------------","general",false,true);
write_log("Starting Node Server... ","general");
sleep(1);
if(is_running()){
write_log("[OK]","general",true);
}
else{
write_log("[FAILED]","error",true);
}
}
else{
write_log("Process already running");
}
}
function stop(){
global $node_process;
if(!is_running()){
write_log("Process not running.");
}
else{
write_log("Stopping process...","general");
$pid = "";
$nout = array();
$output = array();
$result = array();
exec("ps aux | grep '".$node_process."'",$output,$result);
$outputc = count($output);
$found = false;
for($a=0;$a<$outputc;$a++){
if(strpos($output[$a],$node_process) !== false && strpos($output[$a],"grep") === false){
/*write_log($output[$a],"general",true);*/
$found = true;
$out = explode(" ",$output[$a]);
$outc = count($out);
for($a=0;$a<$outc;$a++){
if(trim($out[$a]) != ""){
$nout[] = $out[$a];
}
}
}
}
if($found){
$pid = $nout[1];
write_log("Killing process ".$pid."... ","general");
exec("kill ".$pid);
if(!is_running()){
write_log("[OK]","general",true);
}
else{
write_log("[FAILED]","error",true);
}
}
else{
write_log("[PROCESS NOT FOUND][FAILED]","error",true);
}
}
}
function restart(){
stop();
start();
}
function check(){
write_log("Checking if running... ","general");
if(is_running()){
write_log("Process is running [OK]","general",true);
}
else{
write_log("Process is not running [FAILED]","error",true);
restart();
}
}
if($command == ""){$command = "check";}
write_log("Command: ".$command);
if($command == "start"){
start();
}
if($command == "stop"){
stop();
}
if($command == "restart"){
restart();
}
if($command == "check"){
check();
}
?>
用于自动重启php-fpm:的bash脚本
#!/bin/bash
is_running=`service php7.4-fpm status | grep running`
if [[ ! $is_running ]]
then
echo 'php7.4-fpm is running'
else
echo 'php7.4-fpm is not running';
fi
每5分钟检查一次的Cron配置(/root/check_php7.4_status.sh
-bash脚本的路径):
*/5 * * * * /root/check_php7.4_status.sh 2>&1 >> '/root/check_php7.4_status.log'
这是我写的一个琐碎但我认为很漂亮的脚本,它可以从CRON运行,并将检查服务器上安装的php-fpm的所有版本是否都在运行。这是为Ubuntu 22.04写的,所以YMMV。(这些信息部分是从这个页面上的信息中收集的,但奇怪的是,没有人采取额外的步骤来使用运行"php-fpm status"时返回的状态
其想法是对/etc/init.d中找到的每个php-fpm版本进行状态检查,然后检查返回代码。如果返回代码不为null,则表示出现了问题,我们会发出通知并尝试重新启动。
#!/bin/bash
NOTIFY=me@my.address
for each in /etc/init.d/php*fpm
do
$each status > /dev/null
if [ $? -ne 0 ]
then
logger "$each was not running on $( hostname ) "
mail -s "$each was not running on $( hostname ) " $NOTIFY < /dev/null
$each restart
fi
done