最近開發一個新的PHP項目,終於脫離了某框架的魔爪(之前被折磨的不輕),選用了江湖中如雷貫耳的Yii2框架。每個項目代碼的運行,日志是必不可少的,在開發中踩了一遍Yii2日志管理的坑,看過很多網上對Yii2日志的配置介紹,今天總結一下Yii2對日志的處理分享給大家。
1.首先看一下log配置:
1 return [ 2 'traceLevel' => YII_DEBUG ? 3 : 0, 3 'targets' => [ //可以配置多個log 4 [ 5 'class' => 'yii\log\FileTarget', //Yii2處理日志的類 6 'levels' => ['error', 'warning', 'info'], //設置日志記錄的級別 7 'categories' => ['user'], //自定義日志分類 8 'maxFileSize' => 1024 * 20, //設置文件大小,以k為單位 9 'logFile' => '@runtime/../logs/user'.date('Ymd'), //自定義文件路徑 (一般項目的日志會打到服務器的其他路徑,需要修改相應目錄的權限哦~) 10 'logVars' => ['_POST'], //捕獲請求參數 11 'fileMode' => 0775, //設置日志文件權限 12 'maxLogFiles' => 100, //同個文件名最大數量 13 'rotateByCopy' => false, //是否以復制的方式rotate 14 'prefix' => function() { //日志格式自定義 回調方法 15 if (Yii::$app === null) { 16 return ''; 17 } 18 $request = Yii::$app->getRequest(); 19 $ip = $request instanceof Request ? $request->getUserIP() : '-'; 20 $controller = Yii::$app->controller->id; 21 $action = Yii::$app->controller->action->id; 22 return "[$ip][$controller-$action]"; 23 }, 24 ], 25 ];
2.日志記錄
Yii::trace():記錄一條消息去跟蹤一段代碼是怎樣運行的。這主要在開發的時候使用。
Yii::info():記錄一條消息來傳達一些有用的信息。
Yii::warning():記錄一個警告消息用來指示一些已經發生的意外。
Yii::error():記錄一個致命的錯誤,這個錯誤應該盡快被檢查。
eg: Yii::info('the log content', 'user');
第二個參數可以是自定義的日志分類,對應配置文件中categories字段。
3.日志組件調用
log配置通過web.php(基礎模板web.php 高級模板main.php)以component方式加載到應用對象Yii::$app中。
4.日志切分
./vendor/yiisoft/yii2/log/FileTarget.php
1 class FileTarget extends Target 2 { 3 public $logFile; 4 //rotation開關 如果開啟,當日志文件大於maxFileSize設定的文件大小之后,就會自動切分日志 5 public $enableRotation = true; 6 public $maxFileSize = 10240; // in KB 7 //同一個文件名可以切分多少個文件 8 public $maxLogFiles = 5; 9 public $fileMode; //日志文件權限 10 public $dirMode = 0775; 11 /** 12 * @var bool Whether to rotate log files by copy and truncate in contrast to rotation by 13 * renaming files. Defaults to `true` to be more compatible with log tailers and is windows 14 * systems which do not play well with rename on open files. Rotation by renaming however is 15 * a bit faster. 16 * 17 * The problem with windows systems where the [rename()](http://www.php.net/manual/en/function.rename.php) 18 * function does not work with files that are opened by some process is described in a 19 * [comment by Martin Pelletier](http://www.php.net/manual/en/function.rename.php#102274) in 20 * the PHP documentation. By setting rotateByCopy to `true` you can work 21 * around this problem. 22 */ 23 public $rotateByCopy = true; 24 25 /** 26 * Rotates log files. 27 */ 28 protected function rotateFiles() 29 { 30 $file = $this->logFile; 31 for ($i = $this->maxLogFiles; $i >= 0; --$i) { 32 // $i == 0 is the original log file 33 $rotateFile = $file . ($i === 0 ? '' : '.' . $i); 34 if (is_file($rotateFile)) { 35 // suppress errors because it's possible multiple processes enter into this section 36 if ($i === $this->maxLogFiles) { 37 @unlink($rotateFile); 38 } else { 39 if ($this->rotateByCopy) { 40 @copy($rotateFile, $file . '.' . ($i + 1)); 41 if ($fp = @fopen($rotateFile, 'a')) { 42 @ftruncate($fp, 0); 43 @fclose($fp); 44 } 45 if ($this->fileMode !== null) { 46 @chmod($file . '.' . ($i + 1), $this->fileMode); 47 } 48 } else { 49 // linux下用rename方式 50 @rename($rotateFile, $file . '.' . ($i + 1)); 51 } 52 } 53 } 54 } 55 } 56 }
5.日志前綴
prefix:如果沒有配置,默認調用./vendor/yiisoft/yii2/log/Target.php
1 public function getMessagePrefix($message) 2 { 3 if ($this->prefix !== null) { 4 return call_user_func($this->prefix, $message); 5 } 6 7 if (Yii::$app === null) { 8 return ''; 9 } 10 11 $request = Yii::$app->getRequest(); 12 $ip = $request instanceof Request ? $request->getUserIP() : '-'; 13 14 /* @var $user \yii\web\User */ 15 $user = Yii::$app->has('user', true) ? Yii::$app->get('user') : null; 16 if ($user && ($identity = $user->getIdentity(false))) { 17 $userID = $identity->getId(); 18 } else { 19 $userID = '-'; 20 } 21 22 /* @var $session \yii\web\Session */ 23 $session = Yii::$app->has('session', true) ? Yii::$app->get('session') : null; 24 $sessionID = $session && $session->getIsActive() ? $session->getId() : '-'; 25 26 return "[$ip][$userID][$sessionID]"; 27 }
如果想要自定義日志格式前綴,可以配置回調函數(note:如果在回調中使用了特定的類需要在文件開頭用“use”關鍵詞 引入該類)