Yii2 Log初探

关于Yii2的log组件我想理清如下几个问题:

(1)我们在配置文件(commonconfigmain.php或appconfigmain.php)中定义的log组件配置如何发挥作用,怎样记录到文件,怎样发送到邮箱;

(2)我们把log组件添加到配置文件的bootstrap[]中有什么作用;

(3)我们通过Yii::error(),Yii::info(),Yii::trace()等方法记日志时与log组件发生了怎样的关联。

1.Yii2 Log相关类结构

(1)BaseYii

    1)类中定义了一个私有成员变量$_logger,类型为yiilogLogger,并提供了对应的属性读写方法;

    2)定义了我们经常用到的Yii::trace()等记录不同等级log的快捷方法,省去通过Yii::getLogger()获取logger,再手动设置log级别的过程;

(2)yiilogLogger

    1)这里有几个关键属性需要理解:一个是存储log信息的$messages数组,一个是flush掉$messages的数量阈值$flushIntervalInteger,还有一个用于分发$messages到不同存储目标的$dispatcher,而这个分发者的类型是yiilogDispatcher;

    2)log()是被Yii::error()等便捷方法直接调用的方法,功能是将不同级别的日志消息整理并记录到$messages中,包含每条消息的内容,级别,所属category等;

    3)flush()方法会使用$dispatcher的diapatch()方法将$messages消息分发出去,执行分发的一个前提条件是消息数量达到阈值$flushIntervalInteger。

(3)yiiaseApplication

    1)coreComponents()方法定义了应用的核心组件,其中包括log组件,关联的类正是yiilogDispatcher;

    2)$bootstrap中存放我们在配置文件中指定的bootstrap内容,这里的内容会在Application的构造方法里被实例化,所以我们把核心组件log额外加到$bootstrap中是为了在应用实例化时就拿到实例化的log组件以便后续应用;

    3)构造方法中会通过基类的构造方法调用init(),而init()方法会调用bootstrap()方法,在bootstrap()里对$bootstrap的内容进行了实例化。

(4)yiilogDispatcher

    1)$targets接收我们在配置文件中为log组件指定的日志目标信息,日志目标均是yiilogTarget的子类,各自按照各自的方式处理指定levels与指定categories的日志消息;

    2)$_logger属性实际存储的是BaseYii::getLogger()的内容,在yiilogDispatcher::__constract()中做了一个关联处理,即将Dispatcher对象自身赋值给了BaseYii中$_logger的$dispatcher属性,此时BaseYii的$_logger与Application的log组件才算真正发生了关联;

    3)dispatch()方法将yiilogLogger::flush()传送过来的$messages进行分发,具体方式是调用$targets中所有Target的collect()方法,将消息的处理下放到Target层。

(5)yiilogTarget

    1)这里的几个关键属性与我们在配置文件中对log组件的配置方式直接相关,例如我们可以指定某种日志目标有权处理的日志级别($_levels),日志所属category($categories),以及日志内容需要追加的变量信息($logVars)等;

    2)collect()方法被yiilogDispatcher直接调用,对分发过来的日志消息进行过滤整理,找出符合指定日志级别与categories的部分,然后调用交由子类具体实现的export()方法将日志内容导出到具体目标,如EmailTarget会使用配置的$mailer发送到指定邮箱,FileTarget会存储到指定目录的日志文件等。

2.Yii2 Log组件初始化与一次error日志记录过程

结合上图与第一部分的解释可以更加清晰地理解如下问题:

(1)log组件是在应用实例化的时候被实例化的;

(2)BaseYii的$_logger是在log组件实例化的时候就与log组件产生关联的,所以我们在使用Yii::error()等方法时会使用我们配置的log组件(实际是一个日志分发器)实现日志的分发处理;

(2)我们对log组件的主要配置其实作用在其$targets属性,也就是具体的日志目标的属性配置,这些具体的Target才是真正处理日志去向的地方。

原文地址:https://www.cnblogs.com/ling-diary/p/9206466.html