SeasLog 正在参加 2020 年度 OSC 中国开源项目评选,请投票支持!
SeasLog 在 2020 年度 OSC 中国开源项目评选 中已获得 {{ projectVoteCount }} 票,请投票支持!
投票让它出道
已投票
授权协议: Apache 2.0
开发语言: C/C++ PHP 查看源码 »
操作系统: 跨平台
收录时间: 2014-02-07
提 交 者: Neeke

SeasLog是一个轻量,高效,便捷,规范的PHP日志扩展,精准的定位、精巧的设计,使它成为一个非常优秀的日志工具。

SeasLog地址:

PECL: http://pecl.php.net/package/SeasLog

Github: https://github.com/SeasX/SeasLog

国内镜像:https://gitee.com/neeke/SeasLog

SeasLogger(composer包项目)地址:

Github: https://github.com/SeasX/seas-logger

国内镜像:https://gitee.com/neeke/seas-logger

composer包地址:https://packagist.org/packages/seasx/seas-logger

为什么使用SeasLog

log日志,通常是系统或软件、应用的运行记录。通过log的分析,可以方便用户了解系统或软件、应用的运行情况;如果你的应用log足够丰富,也可以分析以往用户的操作行为、类型喜好、地域分布或其他更多信息;如果一个应用的log同时也分了多个级别,那么可以很轻易地分析得到该应用的健康状况,及时发现问题并快速定位、解决问题,补救损失。

php内置error_log、syslog函数功能强大且性能极好,但由于各种缺陷(error_log无错误级别、无固定格式,syslog不分模块、与系统日志混合),灵活度降低了很多,不能满足应用需求。

好消息是,有不少第三方的log类库弥补了上述缺陷,如log4php、plog、Analog等(当然也有很多应用在项目中自己开发的log类)。其中以log4php最为著名,设计精良、格式完美、文档完善、功能强大。推荐。

不过log4php在性能方面表现非常差,下图是SeasLog与log4php的ab并发性能测试( 测试环境:Ubuntu12.04单机,CPU I3,内存 16G,硬盘 SATA 7200): 

那么有没有一种log类库满足以下需求呢:

  • 分模块、分级别

  • 配置简单(最好是勿须配置)

  • 日志格式清晰易读

  • 应用简单、性能很棒

    SeasLog 正是应此需求而生。

目前提供了什么

  • 在PHP项目中便捷、规范地记录log

  • 可配置的默认log目录与模块

  • 指定log目录与获取当前配置

  • 初步的分析预警框架

  • 高效的日志缓冲、便捷的缓冲debug

  • 遵循 PSR-3 日志接口规范

  • 连接TCP端口,以RFC5424格式发送日志

  • 连接UDP端口,以RFC5424格式发送日志

  • 支持RequestId区分请求

  • 支持日志模板自定义

  • 自动记录错误和异常日志

  • 支持自动记录性能日志(慢方法、支持层级和执行时间阈值)

SeasLog的性能究竟怎么样

当SeasLog不开启buffer时,SeasLog是:

  • syslog()函数的8.6

  • file_put_contents()函数的240

  • fwrite()单例情况下的36

  • fwrite()非单例情况下的211

  • monolog不开启buffer时的41

当SeasLog开启buffer且buffer_size为100时,SeasLog是:

  • syslog()函数的250

  • file_put_contents()函数的6962

  • fwrite()单例情况下的1052

  • fwrite()非单例情况下的6127

  • monolog开启buffer且buffer size为100时的118

测试脚本参考:https://github.com/SeasX/SeasLog/blob/bug_fix/tests/bench_mark.php

目标是怎样的

  • 便捷、规范的log记录

  • 高效的海量log分析

  • 可配置、多途径的log预警

安装

编译安装 SeasLog

$ /path/to/phpize
$ ./configure --with-php-config=/path/to/php-config
$ make && make install

PECL安装SeasLog

$ pecl install seaslog

Windows环境中使用SeasLog

到PECL/SeasLog主页找到对应的dll进行安装 PECL/SeasLog Windows Dll

seaslog.ini的配置

[SeasLog]
;configuration for php SeasLog module
extension = seaslog.so

;默认log根目录
seaslog.default_basepath = "/var/log/www"

;默认logger目录
seaslog.default_logger = "default"

;日期格式配置 默认"Y-m-d H:i:s"
seaslog.default_datetime_format = "Y-m-d H:i:s"

;日志格式模板 默认"%T | %L | %P | %Q | %t | %M"
seaslog.default_template = "%T | %L | %P | %Q | %t | %M"

;是否以目录区分Logger 1是(默认) 0否
seaslog.disting_folder = 1

;是否以type分文件 1是 0否(默认)
seaslog.disting_type = 0

;是否每小时划分一个文件 1是 0否(默认)
seaslog.disting_by_hour = 0

;是否启用buffer 1是 0否(默认)
seaslog.use_buffer = 0

;buffer中缓冲数量 默认0(不使用buffer_size)
seaslog.buffer_size = 100

;cli运行时关闭buffer
;1是 0否(默认)
seaslog.buffer_disabled_in_cli = 0

;记录日志级别,数字越大,根据级别记的日志越多。
;0-EMERGENCY 1-ALERT 2-CRITICAL 3-ERROR 4-WARNING 5-NOTICE 6-INFO 7-DEBUG 8-ALL
;默认8(所有日志)
;
;   注意, 该配置项自1.7.0版本开始有变动。
;   在1.7.0版本之前, 该值数字越小,根据级别记的日志越多: 
;   0-all 1-debug 2-info 3-notice 4-warning 5-error 6-critical 7-alert 8-emergency
;   1.7.0 之前的版本,该值默认为0(所有日志);
seaslog.level = 8

;日志函数调用回溯层级
;影响预定义变量 %F 中的行数
;默认0
seaslog.recall_depth = 0

;自动记录notice 默认0(关闭)
seaslog.trace_notice = 0

;自动记录warning 默认0(开启)
seaslog.trace_warning = 0

;自动记录错误 默认1(开启)
seaslog.trace_error = 1

;自动记录异常信息 默认0(关闭)
seaslog.trace_exception = 0

;日志存储介质 1File 2TCP 3UDP (默认为1)
seaslog.appender = 1

;写入重试次数
;默认0(不重试)
seaslog.appender_retry = 0

;接收ip 默认127.0.0.1 (当使用TCP或UDP时必填)
seaslog.remote_host = "127.0.0.1"

;接收端口 默认514 (当使用TCP或UDP时必填)
seaslog.remote_port = 514

;接收端口的超时时间 默认1秒
seaslog.remote_timeout = 1

;过滤日志中的回车和换行符 (默认为0)
seaslog.trim_wrap = 0

;是否开启抛出SeasLog自身异常  1开启(默认) 0否
seaslog.throw_exception = 1

;是否开启忽略SeasLog自身warning  1开启(默认) 0否
seaslog.ignore_warning = 1

;是否开启性能追踪 1开启 0关闭(默认)
seaslog.trace_performance = 0

;性能追踪时的千分比采样率
;默认10,即百分之一
seaslog.trace_performance_sample_rate = 10

;性能追踪时的开始层级 默认从第1层开始
seaslog.trace_performance_start_depth = 1

;性能追踪时深度层级 默认5层
seaslog.trace_performance_max_depth = 5

;性能追踪时每层的函数最大数 按wall_time降序排列top 默认top5
seaslog.trace_performance_max_functions_per_depth = 5

;性能追踪时当前请求执行时间的记录阈值 只有当请求执行时间大于该值时,才记录性能日志 默认1000ms
seaslog.trace_performance_min_wall_time = 1000

;性能追踪时每个方法执行时间的记录阈值 只有当方法执行时间大于该值时,才参与计算 默认10ms
seaslog.trace_performance_min_function_wall_time = 10

seaslog.disting_folder = 1 开启以目录分文件,即logger以目录区分。当关闭时,logger以下划线拼接时间, 如default_20180211.log。

seaslog.disting_type = 1 开启以type分文件,即log文件区分info\warn\erro

seaslog.disting_by_hour = 1 开启每小时划分一个文件

seaslog.use_buffer = 1 开启buffer。默认关闭。当开启此项时,日志预存于内存,当请求结束时(或异常退出时)一次写入文件。

seaslog.buffer_size = 100 设置缓冲数量为100. 默认为0,即无缓冲数量限制.当buffer_size大于0时,缓冲量达到该值则写一次文件.

seaslog.buffer_disabled_in_cli = 1 开启CLI运行时禁用缓存。默认关闭。当开启此项时,CLI运行时将忽略seaslog.use_buffer设定,日志写入文件。

seaslog.level = 8 记录的日志级别.默认为8,即所有日志均记录。

seaslog.level = 0 记录EMERGENCY。

seaslog.level = 1 记录EMERGENCY、ALERT。

seaslog.level = 2 记录EMERGENCY、ALERT、CRITICAL。

seaslog.level = 3 记录EMERGENCY、ALERT、CRITICAL、ERROR。

seaslog.level = 4 记录EMERGENCY、ALERT、CRITICAL、ERROR、WARNING。

seaslog.level = 5 记录EMERGENCY、ALERT、CRITICAL、ERROR、WARNING、NOTICE。

seaslog.level = 6 记录EMERGENCY、ALERT、CRITICAL、ERROR、WARNING、NOTICE、INFO。

seaslog.level = 7 记录EMERGENCY、ALERT、CRITICAL、ERROR、WARNING、NOTICE、INFO、DEBUG。

seaslog.throw_exception = 1 开启抛出SeasLog抛出自身的异常。当出现录权限或接收服务器端口不通等情况时,抛出异常;关闭时不抛出异常。

seaslog.ignore_warning = 1 开启忽略SeasLog自身的警告。当出现目录权限或接收服务器端口不通等情况时,将进行忽略;关闭时,将抛出警告。

seaslog.trace_performance = 1 开启性能追踪功能。性能日志如:

2019-01-30 11:46:53 | INFO | 91390 | 5c518ea46e010 | 1548848813.299 | {"main()":{"wt":8848,"mu":20712},"1":[{"cm":"Class0::Method0","ct":2,"wt":2007,"mu":192},{"cm":"Class1::Method1","ct":1,"wt":1002,"mu":192},{"cm":"Class2::Method2","ct":1,"wt":1001,"mu":192},{"cm":"Class3::Method3","ct":1,"wt":1000,"mu":192},{"cm":"Class4::Method4","ct":1,"wt":1000,"mu":192}],"2":[{"cm":"Class5::Method5","ct":1,"wt":1000,"mu":192}],"3":[{"cm":"Class5::Recursion","ct":1,"wt":1000,"mu":3248}],"4":[{"cm":"Class5::Recursion","ct":1,"wt":1000,"mu":2952}],"5":[{"cm":"Class5::Recursion","ct":1,"wt":1000,"mu":2656}]}

cm => function_name (类名::方法名)
wt => wall_time (ms)
mu => memory_usage (byte)
ct => call_times (方法调用计数)

自定义日志模板

很多朋友在使用过程中提到自定义日志模板的需求,于是SeasLog自1.7.2版本开始,拥有了这个能力,允许用户自定义日志的模板, 同时在模板中可以使用SeasLog预置的诸多预设变量,参照预设变量表

日志模板说明

  • 模板默认为:seaslog.default_template = "%T | %L | %P | %Q | %t | %M"

  • 意味着,默认的格式为{dateTime} | {level} | {pid} | {uniqid} | {timeStamp} | {logInfo}

  • 如果自定义的格式为:seaslog.default_template = "[%T]:%L %P %Q %t %M"

  • 那么,日志格式将被自定义为:[{dateTime}]:{level} {pid} {uniqid} {timeStamp} {logInfo}

预设变量表

SeasLog提供了下列预设变量,可以直接使用在日志模板中,将在日志最终生成时替换成对应值。

  • %L - Level 日志级别。

  • %M - Message 日志信息。

  • %T - DateTime 如2017-08-16 19:15:02,受seaslog.default_datetime_format影响。

  • %t - Timestamp 如1502882102.862,精确到毫秒数。

  • %Q - RequestId 区分单次请求,如没有调用SeasLog::setRequestId($string)方法,则在初始化请求时,采用内置的static char *get_uniqid()方法生成的惟一值。

  • %H - HostName 主机名。

  • %P - ProcessId 进程ID。

  • %D - Domain:Port 域名:口号,如www.cloudwise.com:8080; Cli模式下为cli

  • %R - Request URI 请求URI,如/app/user/signin; Cli模式下为入口文件,如CliIndex.php

  • %m - Request Method 请求类型,如GET; Cli模式下为执行命令,如/bin/bash

  • %I - Client IP 来源客户端IP; Cli模式下为local。取值优先级为:HTTP_X_REAL_IP > HTTP_X_FORWARDED_FOR > REMOTE_ADDR

  • %F - FileName:LineNo 文件名:行号,如UserService.php:118

  • %U - MemoryUsage 当前内容使用量,单位byte。调用zend_memory_usage

  • %u - PeakMemoryUsage 当前内容使用峰值量,单位byte。调用zend_memory_peak_usage

  • %C - Class::Action 类名::方法名,如UserService::getUserInfo。不在类中使用时,记录函数名

使用

常量与函数

常量列表

SeasLog 共将日志分成8个级别

SEASLOG_DEBUG

  • "DEBUG" - debug信息、细粒度信息事件

SEASLOG_INFO

  • "INFO" - 重要事件、强调应用程序的运行过程

SEASLOG_NOTICE

  • "NOTICE" - 一般重要性事件、执行过程中较INFO级别更为重要的信息

SEASLOG_WARNING

  • "WARNING" - 出现了非错误性的异常信息、潜在异常信息、需要关注并且需要修复

SEASLOG_ERROR

  • "ERROR" - 运行时出现的错误、不必要立即进行修复、不影响整个逻辑的运行、需要记录并做检测

SEASLOG_CRITICAL

  • "CRITICAL" - 紧急情况、需要立刻进行修复、程序组件不可用

SEASLOG_ALERT

  • "ALERT" - 必须立即采取行动的紧急事件、需要立即通知相关人员紧急修复

SEASLOG_EMERGENCY

  • "EMERGENCY" - 系统不可用

var_dump(SEASLOG_DEBUG,SEASLOG_INFO,SEASLOG_NOTICE);
/*
string('DEBUG') debug级别
string('INFO')  info级别
string('NOTICE') notice级别
*/

函数列表

SeasLog 提供了这样一组函数,可以方便地获取与设置根目录、模块目录、快速写入与统计log。 相信从下述伪代码的注释中,您可以快速获取函数信息,具体使用将紧接其后:

<?php
/**
 * @author neeke@php.net
 * Date: 14-1-27 下午4:47
 */
define('SEASLOG_ALL', 'ALL');
define('SEASLOG_DEBUG', 'DEBUG');
define('SEASLOG_INFO', 'INFO');
define('SEASLOG_NOTICE', 'NOTICE');
define('SEASLOG_WARNING', 'WARNING');
define('SEASLOG_ERROR', 'ERROR');
define('SEASLOG_CRITICAL', 'CRITICAL');
define('SEASLOG_ALERT', 'ALERT');
define('SEASLOG_EMERGENCY', 'EMERGENCY');
define('SEASLOG_DETAIL_ORDER_ASC', 1);
define('SEASLOG_DETAIL_ORDER_DESC', 2);
define('SEASLOG_CLOSE_LOGGER_STREAM_MOD_ALL', 1);
define('SEASLOG_CLOSE_LOGGER_STREAM_MOD_ASSIGN', 2);
define('SEASLOG_REQUEST_VARIABLE_DOMAIN_PORT', 1);
define('SEASLOG_REQUEST_VARIABLE_REQUEST_URI', 2);
define('SEASLOG_REQUEST_VARIABLE_REQUEST_METHOD', 3);
define('SEASLOG_REQUEST_VARIABLE_CLIENT_IP', 4);

class SeasLog
{
    public function __construct()
    {
        #SeasLog init
    }

    public function __destruct()
    {
        #SeasLog distroy
    }

    /**
     * 设置basePath
     *
     * @param $basePath
     *
     * @return bool
     */
    static public function setBasePath($basePath)
    {
        return true;
    }

    /**
     * 获取basePath
     *
     * @return string
     */
    static public function getBasePath()
    {
        return 'the base_path';
    }

    /**
     * 设置本次请求标识
     *
     * @param string
     *
     * @return bool
     */
    static public function setRequestID($request_id)
    {
        return true;
    }

    /**
     * 获取本次请求标识
     * @return string
     */
    static public function getRequestID()
    {
        return uniqid();
    }

    /**
     * 设置模块目录
     *
     * @param $module
     *
     * @return bool
     */
    static public function setLogger($module)
    {
        return true;
    }

    /**
     * 手动清除logger的stream流
     *
     * @param $model
     * @param $logger
     *
     * @return bool
     */
    static public function closeLoggerStream($model = SEASLOG_CLOSE_LOGGER_STREAM_MOD_ALL, $logger)
    {
        return true;
    }

    /**
     * 获取最后一次设置的模块目录
     * @return string
     */
    static public function getLastLogger()
    {
        return 'the lastLogger';
    }

    /**
     * 设置DatetimeFormat配置
     *
     * @param $format
     *
     * @return bool
     */
    static public function setDatetimeFormat($format)
    {
        return true;
    }

    /**
     * 返回当前DatetimeFormat配置格式
     * @return string
     */
    static public function getDatetimeFormat()
    {
        return 'the datetimeFormat';
    }

    /**
     * 设置请求变量
     *
     * @param $key
     * @param $value
     *
     * @return bool
     */
    static public function setRequestVariable($key, $value)
    {
        return true;
    }

    /**
     * 获取请求变量
     *
     * @param $key
     *
     * @return string
     */
    static public function getRequestVariable($key)
    {
        return '';
    }

    /**
     * 统计所有类型(或单个类型)行数
     *
     * @param string $level
     * @param string $log_path
     * @param null   $key_word
     *
     * @return array | long
     */
    static public function analyzerCount($level = 'all', $log_path = '*', $key_word = null)
    {
        return array();
    }

    /**
     * 以数组形式,快速取出某类型log的各行详情
     *
     * @param        $level
     * @param string $log_path
     * @param null   $key_word
     * @param int    $start
     * @param int    $limit
     * @param        $order
     *
     * @return array
     */
    static public function analyzerDetail($level = SEASLOG_INFO, $log_path = '*', $key_word = null, $start = 1, $limit = 20, $order = SEASLOG_DETAIL_ORDER_ASC)
    {
        return array();
    }

    /**
     * 获得当前日志buffer中的内容
     *
     * @return array
     */
    static public function getBuffer()
    {
        return array();
    }

    /**
     * 将buffer中的日志立刻刷到硬盘
     *
     * @return bool
     */
    static public function flushBuffer()
    {
        return true;
    }

    /**
     * 记录debug日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function debug($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_DEBUG
    }

    /**
     * 记录info日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function info($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_INFO
    }

    /**
     * 记录notice日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function notice($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_NOTICE
    }

    /**
     * 记录warning日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function warning($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_WARNING
    }

    /**
     * 记录error日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function error($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_ERROR
    }

    /**
     * 记录critical日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function critical($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_CRITICAL
    }

    /**
     * 记录alert日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function alert($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_ALERT
    }

    /**
     * 记录emergency日志
     *
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function emergency($message, array $context = array(), $module = '')
    {
        #$level = SEASLOG_EMERGENCY
    }

    /**
     * 通用日志方法
     *
     * @param              $level
     * @param string|array $message
     * @param array        $context
     * @param string       $module
     */
    static public function log($level, $message, array $context = array(), $module = '')
    {

    }
}

PHP Re 结果

SeasLog_PHP_Re_Result

SeasLog Logger的使用

获取与设置basePath

$basePath_1 = SeasLog::getBasePath();

SeasLog::setBasePath('/log/base_test');
$basePath_2 = SeasLog::getBasePath();

var_dump($basePath_1,$basePath_2);

/*
string(19) "/log/seaslog-ciogao"
string(14) "/log/base_test"
*/

直接使用 SeasLog::getBasePath(),将获取php.ini(seaslog.ini)中设置的 seaslog.default_basepath 的值。

使用 SeasLog::setBasePath() 函数,将改变 SeasLog::getBasePath() 的取值。

设置logger与获取lastLogger

$lastLogger_1 = SeasLog::getLastLogger();

SeasLog::setLogger('testModule/app1');
$lastLogger_2 = SeasLog::getLastLogger();

var_dump($lastLogger_1,$lastLogger_2);
/*
string(7) "default"
string(15) "testModule/app1"
*/

与basePath相类似的,

直接使用 SeasLog::getLastLogger(),将获取php.ini(seaslog.ini)中设置的 seaslog.default_logger 的值。

使用 SeasLog::setLogger() 函数,将改变 SeasLog::getLastLogger() 的取值。

快速写入log

上面已经设置过了basePath与logger,于是log记录的目录已经产生了,

log记录目录 = basePath / logger / {fileName}.log log文件名,以 年月日 分文件,如今天是2014年02月18日期,那么 {fileName} = 20140218;

还记得 php.ini 中设置的 seaslog.disting_type 吗?

默认的 seaslog.disting_type = 0,如果今天我使用了 SeasLog ,那么将产生最终的log文件:

  • LogFile = basePath / logger / 20140218.log

如果 seaslog.disting_type = 1,则最终的log文件将是这样的三个文件

  • infoLogFile = basePath / logger / 20140218.INFO.log

  • warnLogFile = basePath / logger / 20140218.WARNING.log

  • erroLogFile = basePath / logger / 20140218.ERROR.log

用于记录日志的函数原型有两个:

  • SeasLog::log($level, $messages[, $context, $logger])

  • SeasLog::$level($messages[, $context, $logger])

$level - 参见上文所列的8个级别

$messages - 可以使用stringarray两种类型, array仅接受一维数组

$context - 仅接受一维数组,用于替换$messages中log的占位符

$logger - 可以临时为当前操作指定一个logger,而不改变getLastLogger方法的取值

SeasLog::log(SEASLOG_ERROR,'this is a error test by ::log');

SeasLog::debug('this is a {userName} debug',array('{userName}' => 'neeke'));

SeasLog::info('this is a info log');

SeasLog::notice('this is a notice log');

SeasLog::warning('your {website} was down,please {action} it ASAP!',array('{website}' => 'github.com','{action}' => 'rboot'));

SeasLog::error('a error log');

SeasLog::critical('some thing was critical');

SeasLog::alert('yes this is a {messageName}',array('{messageName}' => 'alertMSG'));

SeasLog::emergency('Just now, the house next door was completely burnt out! {note}',array('{note}' => 'it`s a joke'));

$aMessages = array('test log from array abc {website}','test log from array def {action}');
$aContent = array('website' => 'github.com','action' => 'rboot'));
SeasLog::debug($aMessages,$aContent);
/*
这些函数同时也接受第3个参数为logger的设置项
注意,当last_logger == 'default'时等同于:
SeasLog::setLogger('test/new/path');
SeasLog::error('test error 3');
如果已经在前文使用过SeasLog::setLogger()函数,第3个参数的log只在此处临时使用,不影响下文。
*/

log格式受seaslog.default_template影响。 seaslog.default_template默认模板为 seaslog.default_template = "%T | %L | %P | %Q | %t | %M" 那么在默认情况下,日志格式为: {dateTime} | {level} | {pid} | {uniqid} | {timeStamp} | {logInfo} 关于自定义模板,及SeasLog中的预置值,可参阅 自定义日志模板

2014-07-27 08:53:52 | ERROR | 23625 | 599159975a9ff | 1406422432.786 | this is a error test by log
2014-07-27 08:53:52 | DEBUG | 23625 | 599159975a9ff | 1406422432.786 | this is a neeke debug
2014-07-27 08:53:52 | INFO | 23625 | 599159975a9ff | 1406422432.787 | this is a info log
2014-07-27 08:53:52 | NOTICE | 23625 | 599159975a9ff | 1406422432.787 | this is a notice log
2014-07-27 08:53:52 | WARNING | 23625 | 599159975a9ff | 1406422432.787 | your github.com was down,please rboot it ASAP!
2014-07-27 08:53:52 | ERROR | 23625 | 599159975a9ff | 1406422432.787 | a error log
2014-07-27 08:53:52 | CRITICAL | 23625 | 599159975a9ff | 1406422432.787 | some thing was critical
2014-07-27 08:53:52 | EMERGENCY | 23625 | 599159975a9ff | 1406422432.787 | Just now, the house next door was completely burnt out! it is a joke
2014-07-27 08:53:52 | DEBUG | 23625 | 599159975a9ff | 1406422432.787 | test log from array abc github.com
2014-07-27 08:53:52 | DEBUG | 23625 | 599159975a9ff | 1406422432.787 | test log from array def rboot

使用TCP或UDP发送时的数据格式

seaslog.appender配置为 2(TCP) 或 3(UDP) 时,日志将推送至remote_host:remote_port的TCP或UDP端口

SeasLog发送至远端时,遵循规范RFC5424 log格式统一为:<PRI>1 {timeStampWithRFC3339} {HostName} {loggerName}[{pid}]: {logInfo} 上述{logInfo} 受配置 seaslog.default_template影响。

发送出去的格式如:
<15>1 2017-08-27T01:24:59+08:00 vagrant-ubuntu-trusty test/logger[27171]: 2016-06-25 00:59:43 | DEBUG | 21423 | 599157af4e937 | 1466787583.322 | this is a neeke debug
<14>1 2017-08-27T01:24:59+08:00 vagrant-ubuntu-trusty test/logger[27171]: 2016-06-25 00:59:43 | INFO | 21423 | 599157af4e937 | 1466787583.323 | this is a info log
<13>1 2017-08-27T01:24:59+08:00 vagrant-ubuntu-trusty test/logger[27171]: 2016-06-25 00:59:43 | NOTICE | 21423 | 599157af4e937 | 1466787583.324 | this is a notice log

手动清除LoggerStream缓存

SeasLog会将日志Logger开启的Stream句柄进行缓存,以节省创建流时引起的开销。句柄将在请求结束时自动释放。 如果在CLI模式下,进程退出时也会自动释放。或者你可以使用下面的函数进行手动释放(手动释放函数需要更新SeasLog 1.8.6或更新版本)。

手动关闭所有的Logger Stream句柄:

SeasLog::closeLoggerStream();

或

SeasLog::closeLoggerStream(SEASLOG_CLOSE_LOGGER_STREAM_MOD_ALL);

手动关闭指定的Logger Stream句柄:

SeasLog::closeLoggerStream(SEASLOG_CLOSE_LOGGER_STREAM_MOD_ASSIGN, 'logger_name');

SeasLog Analyzer的使用

快速统计某类型log的count值

SeasLog在扩展中使用管道调用shell命令 grep -wc快速地取得count值,并返回值(array || int)给PHP。

$countResult_1 = SeasLog::analyzerCount();
$countResult_2 = SeasLog::analyzerCount(SEASLOG_WARNING);
$countResult_3 = SeasLog::analyzerCount(SEASLOG_ERROR,date('Ymd',time()));

var_dump($countResult_1,$countResult_2,$countResult_3);
/*
array(8) {
  ["DEBUG"]=>
  int(3)
  ["INFO"]=>
  int(3)
  ["NOTICE"]=>
  int(3)
  ["WARNING"]=>
  int(3)
  ["ERROR"]=>
  int(6)
  ["CRITICAL"]=>
  int(3)
  ["ALERT"]=>
  int(3)
  ["EMERGENCY"]=>
  int(3)
}


int(7)

int(1)

*/

获取某类型log列表

SeasLog在扩展中使用管道调用shell命令 grep -w快速地取得列表,并返回array给PHP。

$detailErrorArray_inAll   = SeasLog::analyzerDetail(SEASLOG_ERROR);
$detailErrorArray_today   = SeasLog::analyzerDetail(SEASLOG_ERROR,date('Ymd',time()));

var_dump($detailErrorArray_inAll,$detailErrorArray_today);

/*
SeasLog::analyzerDetail(SEASLOG_ERROR) == SeasLog::analyzerDetail(SEASLOG_ERROR,'*');
取当前模块下所有level为 SEASLOG_ERROR 的信息列表:
array(6) {
 [0] =>
  string(66) "2014-02-24 00:14:02 | ERROR | 8568 | 599157af4e937 | 1393172042.717 | test error 3 "
  [1] =>
  string(66) "2014-02-24 00:14:04 | ERROR | 8594 | 5991576584446 | 1393172044.104 | test error 3 "
  [2] =>
  string(66) "2014-02-24 00:14:04 | ERROR | 8620 | 1502697015147 | 1393172044.862 | test error 3 "
  [3] =>
  string(66) "2014-02-24 00:14:05 | ERROR | 8646 | 599159975a9ff | 1393172045.989 | test error 3 "
  [4] =>
  string(66) "2014-02-24 00:14:07 | ERROR | 8672 | 599159986ec28 | 1393172047.882 | test error 3 "
  [5] =>
  string(66) "2014-02-24 00:14:08 | ERROR | 8698 | 5991599981cec | 1393172048.736 | test error 3 "
}

SeasLog::analyzerDetail(SEASLOG_ERROR,date('Ymd',time()));
只取得当前模块下,当前一天内,level为SEASLOG_ERROR 的信息列表:
array(2) {
  [0] =>
  string(66) "2014-02-24 00:14:02 | ERROR | 8568 | 599157af4e937 | 1393172042.717 | test error 3 "
  [1] =>
  string(66) "2014-02-24 00:14:04 | ERROR | 8594 | 5991576584446 | 1393172044.104 | test error 3 "
}

同理,取当月
$detailErrorArray_mouth = SeasLog::analyzerDetail(SEASLOG_ERROR,date('Ym',time()));

*/

使用SeasLog进行健康预警

预警的配置

[base]
wait_analyz_log_path = /log/base_test

[fork]
;是否开启多线程 1开启 0关闭
fork_open = 1

;线程个数
fork_count = 3

[warning]
email[smtp_host] = smtp.163.com
email[smtp_port] = 25
; 是否开启加密协议 tsl ssl, 留空为不开启
email[smtp_secure] =
; 邮件发送类型 smtp, sendmail, mail
; smtp: PHP实现的smtp协议
; sendmail: 需配置php.ini中sendmail_path
; mail: 使用PHP内置mail()函数
email[smtp_mailer] = smtp
email[subject_pre] = 预警邮件 -
email[smtp_user] = seaslogdemo@163.com
email[smtp_pwd] = seaslog#demo
email[mail_from] = seaslogdemo@163.com
email[mail_to] = gaochitao@weiboyi.com
email[mail_cc] = ciogao@gmail.com
email[mail_bcc] =

[analyz]
; enum
; SEASLOG_DEBUG      "DEBUG"
; SEASLOG_INFO       "INFO"
; SEASLOG_NOTICE     "NOTICE"
; SEASLOG_WARNING    "WARNING"
; SEASLOG_ERROR      "ERROR"
; SEASLOG_CRITICAL   "CRITICAL"
; SEASLOG_ALERT      "ALERT"
; SEASLOG_EMERGENCY  "EMERGENCY"

; 可以实现分别监控不同模块下特定级别的日志发送给不同的邮箱
; test1 监控任务表示
; 统计test模块SEASLOG_ERROR等级的日志数量,如果数量大于3则发送报警邮件到gaochitao@weiboyi.com

test1[module] = test
test1[level] = SEASLOG_ERROR
test1[bar] = 3
test1[mail_to] = neeke@php.net

test2[module] = 222
test2[level] = SEASLOG_WARNING
test2[mail_to] = neeke@php.net,ciogao@gmail.com

test3[module] = 333
test3[level] = SEASLOG_CRITICAL

test4[module] = 444
test4[level] = SEASLOG_EMERGENCY

test5[module] = 555
test5[level] = SEASLOG_DEBUG

crontab配置

;每天凌晨3点执行
0 3 * * * /path/to/php /path/to/SeasLog/Analyzer/SeasLogAnalyzer.php
展开阅读全文

代码

的 Gitee 指数为
超过 的项目

SeasLog 的相关博客

seaslog学习笔记

安装 官网:http://pecl.php.net/package/SeasLog 下载链接:http://pecl.php.net/get/SeasLog-1.8.4.tgz 安装命令 cd /home...

SeasLog学习笔记

为什么使用SeasLog

SeasLog高性能php日志系统

日志是php开发过程中不可缺少的部分,尤其是一些系统核心业务更加需要配置健壮、高可用的日志系统,比如订单、支付等业务必须...

php 日志处理工具 SeasLog 的使用

首先附上seaslog github地址:   https://github.com/Neeke/SeasLog/blob/master/README_zh.md php官方文档地址:   https...

PHP日志系统SeasLog入门到封装

目录 1. 前言 2.安装配置seaslog 2.1下载地址 2.2编译安装 2.2.1linux下安装 2.2.2window下安装 2.3配置php.ini 2.4自定义日志...

高性能的PHP日志系统 SeasLog 使用

这篇主要是介绍和使用 安装请参考我另一篇 docker php容器中添加seaslog拓展 简介 使用SeasLog好处 log日志,通常是系统或软件...

docker php容器中添加seaslog拓展

需要用到seaslog 安转步骤如下 1、开启PHP容器 docker start phps 2、进入容器 docker exec -it phps bash 3、跳到临时目录(...

docker php容器中简单添加seaslog拓展

最近有个项目用到了seaslog,因为之前调试php的容器已经搭好了,不想再通过dockerfile重新搭建了,搜了半天没有东西可以装,就...

windows安装 Seaslog

SeasLog是一个C语言编写的PHP扩展,提供一组规范标准的功能函数,在PHP项目中方便、规范、高效地写日志,以及快速地读取和查询...

日志记录工具

日志是每个项目中必不可少的,通过日志的分析,可以方便用户了解系统或软件、应用的运行情况,从而帮助我们完善系统。 目前功...

评论 (10)

加载中
这个和fpm自带的的slow log有什么区别呢?
2019/02/13 17:26
回复
举报
Neeke软件作者
打分: 力荐
@LeeZard 如果使用namespace,使用时需要加反斜线,如 \SeasLog::info('msg')
2017/05/13 17:30
回复
举报
Class 'SeasLog' not found 这种问题怎么解决
2017/04/11 17:12
回复
举报
好东西啊 SeasLog
2014/07/29 11:49
回复
举报
这货是版本帝啊…… SeasLog
2014/08/21 11:40
回复
举报
Neeke软件作者
目前最稳定版本1.4.4 可自动记录error与exception 可帮助开发者快速定位错误与异常 #SeasLog#
2015/09/27 12:54
回复
举报
Neeke软件作者
1.5.0 已发布,支持PHP7 #SeasLog#
2015/12/07 09:46
回复
举报
seaslog类封装中应该注意的地方,http://wp.iyouths.org/283.html#SeasLog#
2016/04/11 10:51
回复
举报
支持一下,感谢分享,希望作者能够一直坚持下去,加油! #SeasLog#
2016/04/29 16:54
回复
举报
很厉害,很实用 #SeasLog#
2016/12/01 15:09
回复
举报
更多评论
10 评论
197 收藏
分享
返回顶部
顶部