账号密码登录
微信安全登录
微信扫描二维码登录

登录后绑定QQ、微信即可实现信息互通

手机验证码登录
找回密码返回
邮箱找回 手机找回
注册账号返回
其他登录方式
分享
  • 收藏
    X
    linux上的PHP脚本为什么挂掉了进程还在?
    59
    0

    本人之前在linux上写的一段PHP代码(逻辑是用PHP实现对数据库中日志文件的转移,运行是shell脚本运行),为什么挂掉后(不能正常转移数据库中的数据),进程却还在,根本就看不出来他挂掉。具体的PHP代码如下:

    /**
     * 测试
     */
    class PaizuTableHandler extends ScriptBase
    {
        public static $mysql = null;
        const LOG_PAIZU_TABLE = 'log_user_paiju';
        public function logic()
        {
            if(empty(self::$mysql)){
                self::$mysql = $this->mysql('logs');
            }
            set_time_limit(0);
            while (true)
            {
                $date = date("Y-m-d");
                $dataTime =  strtotime($date);
                $timestampStart = $dataTime - 3600*24; //昨天
                $timestampEnd = mktime(0,0,0,date("m"),1,date("Y"));//本月月初 例如:2017-07-01 00:00:00
                $timestampEnd_lastmoth = mktime(0, 0 , 0,date("m")-1,1,date("Y"));//上月月初 例如:2017-06-01 00:00:00
    
                if($timestampStart < $timestampEnd){
                    sleep(60);
                    continue;
                }
    
                $table = self::LOG_PAIZU_TABLE.'_'.date("Ym");//本月的表
                $lastMothTable = self::LOG_PAIZU_TABLE.'_'.date("Ym",mktime(0, 0 , 0,date("m")-1,1,date("Y")));//上个月的表
    
                $hasTable = self::$mysql->tableExists($table);  //判断是否有本月的表
                $hasTableLast = self::$mysql->tableExists($lastMothTable);  //判断是否有上个月的表
    
                $createFlag = $hasTable ? true : false; //本月的表是否存在
                $createFlagLast = $hasTableLast ? true : false; //上个月的表是否存在
    
                if( empty( $createFlag ) ){
                    //创建表
                    $createSql = "CREATE TABLE {$table} LIKE log_user_paiju";
                    $createFlag = self::$mysql->query($createSql);
                }
                if( $createFlag ){
    
                    //查询本月当天应清空数据有没有清空
                    $sql = "select * from log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd} and {$timestampStart} order by `time` desc limit 100";
                    $result = self::$mysql->query($sql);
                    $rs = self::$mysql -> fetch_row($result);
                    if( !$result ){
                        break;
                        exit(0);
                    }
    
                    $date = date("Y-m-d");
                    $current_time =  strtotime($date); //当前时间戳
                    $current_time2 = mktime(0,0,0,date("m"),6,date("Y")); //月初第6天
                    $last_rs = array(); //添加于2017.10.25
                    if($current_time == $current_time2 && !empty( $createFlagLast ) && empty($rs)){
                        //本月第6天把 上个月的数据全部放到上个月的表中(要放最少2天前)
                        $last_sql = "select * from log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd_lastmoth} and {$timestampEnd} order by `time` desc limit 100";
                        $last_sql1 = "INSERT INTO {$lastMothTable}(uid,paiju_score,paizu_score,`time`,paizu_id,seq,room_id,server_id,creator,`status`,mahjongType) SELECT uid,paiju_score,paizu_score,`time`,paizu_id,seq,room_id,server_id,creator,`status`,mahjongType FROM log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd_lastmoth} and {$timestampEnd} order by `time` desc limit 100";
                        $last_sql2 = "delete from log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd_lastmoth} and {$timestampEnd} order by `time` desc limit 100";
    
                        $result1 = self::$mysql->query($last_sql);
                        $last_rs = self::$mysql -> fetch_row($result1);
                        if($last_rs){
                            if($r = self::$mysql->query($last_sql1)){
                                self::$mysql->query($last_sql2);
                            }
                        }
    
    
                    }
    
                    $sql1 = "INSERT INTO {$table}(uid,paiju_score,paizu_score,`time`,paizu_id,seq,room_id,server_id,creator,`status`,mahjongType) SELECT uid,paiju_score,paizu_score,`time`,paizu_id,seq,room_id,server_id,creator,`status`,mahjongType FROM log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd} and {$timestampStart} order by `time` desc limit 100";
                    $sql2 = "delete from log_user_paiju where UNIX_TIMESTAMP(`time`) between {$timestampEnd} and {$timestampStart} order by `time` desc limit 100";
    
                    if(empty($rs) && empty($last_rs)){
                        sleep(60);
                    }
                    if($rs){
                        if($r1=self::$mysql->query($sql1)){
                            !self::$mysql->query($sql2);
                        }
                    }
                }
                usleep(3000);
            }
        }
    
    }

    ====================================分割线================================

    shell脚本如下:

    #!/bin/sh
    # scripts daemon, add to /etc/crontab
    # */1 *   *   *   *   root    PATH/script.sh --daemon
    
    # run on root
    if [ "$(uname -s|grep -F 'CYGWIN')" = "" ] && [ $UID -ne 0 ]; then
        echo "superuser privileges are required to run this script."
        exit 1
    fi
    
    # settings
    PHP_CLI="/usr/bin/php -c /etc/php.ini"
    SCRIPTS="PaizuTableHandler"
    
    # paths
    BASE_PATH=$(cd $(dirname $0) && pwd)
    BASE_SCRIPT="$BASE_PATH/script.php"
    LOGS_PATH="$BASE_PATH/data/logs/bash.log"
    
    USAGE="Usage: $(basename $0) [-d|-a|-k SCRIPT]\n\
      -d, --daemon\t\tthe daemon mode, runing checking\n\
      -a, --killall\t\tkill the all scripts\n\
      -k, --kill SCRIPT\tkill the SCRIPT\n\
      -h, --help\t\tthis help text"
    
    function get_pid()
    {
      echo $(ps -ef|grep -F "$1"|grep -v "grep"|awk '{print $2}')
    }
    
    function kill_script()
    {
      PID=$(get_pid "$1")
      if [ "$PID" = "" ]; then
        echo "$1 not found"
      else
        kill -9 $PID
        echo "$1 has been killed, pid: $PID"
      fi
    }
    
    case $1 in
      -k|--kill)
        if [ "$2" = "" ]; then
          echo -e $USAGE
          exit 0
        fi
        kill_script "$BASE_SCRIPT request/$2"
        ;;
      -a|--killall)
        for SCRIPT in $SCRIPTS; do
          kill_script "$BASE_SCRIPT request/$SCRIPT"
        done
        ;;
      -d|--daemon)
        for SCRIPT in $SCRIPTS; do
          SCRIPT="$BASE_SCRIPT request/$SCRIPT"
          PID=$(get_pid "$SCRIPT")
          if [ "$PID" = "" ]; then
            eval "$PHP_CLI $SCRIPT >/dev/null 2>&1 &"
            PID=$(get_pid "$SCRIPT")
            echo "[$(date +%Y-%m-%d\ %H:%M:%S)] $SCRIPT has been down, restarted: $PID" >> $LOGS_PATH
          fi
        done
        ;;
      *)
        echo -e $USAGE
        ;;
    esac
    1
    打赏
    收藏
    点击回答
        全部回答
    • 共 0 条
    • 我就是学渣啊 普通会员 1楼

      在Linux上,PHP脚本挂掉进程但仍在运行,可能有以下几种原因:

      1. 程序在内存中占用过多资源:如果你的PHP脚本运行在一个大型的内存分配中,可能会导致它挂掉。你可以尝试关闭内存分配,或者减少脚本的内存使用。

      2. 程序在进程之间通信问题:PHP脚本可能与另一个PHP脚本或进程之间的通信出现问题。你可以在脚本之间添加错误处理代码,或者使用更安全的通信协议。

      3. 程序在进程间通信问题:PHP脚本可能与另一个PHP脚本或进程之间的通信出现问题。你可以在脚本之间添加错误处理代码,或者使用更安全的通信协议。

      4. 程序在进程间通信问题:PHP脚本可能与另一个PHP脚本或进程之间的通信出现问题。你可以在脚本之间添加错误处理代码,或者使用更安全的通信协议。

      5. 程序在进程间通信问题:PHP脚本可能与另一个PHP脚本或进程之间的通信出现问题。你可以在脚本之间添加错误处理代码,或者使用更安全的通信协议。

      以上都是一些常见的原因,但具体原因可能因你的PHP脚本和Linux环境的不同而有所不同。如果你不确定是什么原因导致的挂掉进程但仍在运行,建议你查看错误日志,或者寻求专业的帮助。

    更多回答
    扫一扫访问手机版
    • 回到顶部
    • 回到顶部