scratch – Blame information for rev 115
?pathlinks?
Rev | Author | Line No. | Line |
---|---|---|---|
115 | office | 1 | <?php |
2 | |||
3 | /* |
||
4 | * This file is part of the Monolog package. |
||
5 | * |
||
6 | * (c) Jordi Boggiano <j.boggiano@seld.be> |
||
7 | * |
||
8 | * For the full copyright and license information, please view the LICENSE |
||
9 | * file that was distributed with this source code. |
||
10 | */ |
||
11 | |||
12 | namespace Monolog\Formatter; |
||
13 | |||
14 | use Monolog\Logger; |
||
15 | use Gelf\Message; |
||
16 | |||
17 | /** |
||
18 | * Serializes a log message to GELF |
||
19 | * @see http://www.graylog2.org/about/gelf |
||
20 | * |
||
21 | * @author Matt Lehner <mlehner@gmail.com> |
||
22 | */ |
||
23 | class GelfMessageFormatter extends NormalizerFormatter |
||
24 | { |
||
25 | const DEFAULT_MAX_LENGTH = 32766; |
||
26 | |||
27 | /** |
||
28 | * @var string the name of the system for the Gelf log message |
||
29 | */ |
||
30 | protected $systemName; |
||
31 | |||
32 | /** |
||
33 | * @var string a prefix for 'extra' fields from the Monolog record (optional) |
||
34 | */ |
||
35 | protected $extraPrefix; |
||
36 | |||
37 | /** |
||
38 | * @var string a prefix for 'context' fields from the Monolog record (optional) |
||
39 | */ |
||
40 | protected $contextPrefix; |
||
41 | |||
42 | /** |
||
43 | * @var int max length per field |
||
44 | */ |
||
45 | protected $maxLength; |
||
46 | |||
47 | /** |
||
48 | * Translates Monolog log levels to Graylog2 log priorities. |
||
49 | */ |
||
50 | private $logLevels = array( |
||
51 | Logger::DEBUG => 7, |
||
52 | Logger::INFO => 6, |
||
53 | Logger::NOTICE => 5, |
||
54 | Logger::WARNING => 4, |
||
55 | Logger::ERROR => 3, |
||
56 | Logger::CRITICAL => 2, |
||
57 | Logger::ALERT => 1, |
||
58 | Logger::EMERGENCY => 0, |
||
59 | ); |
||
60 | |||
61 | public function __construct($systemName = null, $extraPrefix = null, $contextPrefix = 'ctxt_', $maxLength = null) |
||
62 | { |
||
63 | parent::__construct('U.u'); |
||
64 | |||
65 | $this->systemName = $systemName ?: gethostname(); |
||
66 | |||
67 | $this->extraPrefix = $extraPrefix; |
||
68 | $this->contextPrefix = $contextPrefix; |
||
69 | $this->maxLength = is_null($maxLength) ? self::DEFAULT_MAX_LENGTH : $maxLength; |
||
70 | } |
||
71 | |||
72 | /** |
||
73 | * {@inheritdoc} |
||
74 | */ |
||
75 | public function format(array $record) |
||
76 | { |
||
77 | $record = parent::format($record); |
||
78 | |||
79 | if (!isset($record['datetime'], $record['message'], $record['level'])) { |
||
80 | throw new \InvalidArgumentException('The record should at least contain datetime, message and level keys, '.var_export($record, true).' given'); |
||
81 | } |
||
82 | |||
83 | $message = new Message(); |
||
84 | $message |
||
85 | ->setTimestamp($record['datetime']) |
||
86 | ->setShortMessage((string) $record['message']) |
||
87 | ->setHost($this->systemName) |
||
88 | ->setLevel($this->logLevels[$record['level']]); |
||
89 | |||
90 | // message length + system name length + 200 for padding / metadata |
||
91 | $len = 200 + strlen((string) $record['message']) + strlen($this->systemName); |
||
92 | |||
93 | if ($len > $this->maxLength) { |
||
94 | $message->setShortMessage(substr($record['message'], 0, $this->maxLength)); |
||
95 | } |
||
96 | |||
97 | if (isset($record['channel'])) { |
||
98 | $message->setFacility($record['channel']); |
||
99 | } |
||
100 | if (isset($record['extra']['line'])) { |
||
101 | $message->setLine($record['extra']['line']); |
||
102 | unset($record['extra']['line']); |
||
103 | } |
||
104 | if (isset($record['extra']['file'])) { |
||
105 | $message->setFile($record['extra']['file']); |
||
106 | unset($record['extra']['file']); |
||
107 | } |
||
108 | |||
109 | foreach ($record['extra'] as $key => $val) { |
||
110 | $val = is_scalar($val) || null === $val ? $val : $this->toJson($val); |
||
111 | $len = strlen($this->extraPrefix . $key . $val); |
||
112 | if ($len > $this->maxLength) { |
||
113 | $message->setAdditional($this->extraPrefix . $key, substr($val, 0, $this->maxLength)); |
||
114 | break; |
||
115 | } |
||
116 | $message->setAdditional($this->extraPrefix . $key, $val); |
||
117 | } |
||
118 | |||
119 | foreach ($record['context'] as $key => $val) { |
||
120 | $val = is_scalar($val) || null === $val ? $val : $this->toJson($val); |
||
121 | $len = strlen($this->contextPrefix . $key . $val); |
||
122 | if ($len > $this->maxLength) { |
||
123 | $message->setAdditional($this->contextPrefix . $key, substr($val, 0, $this->maxLength)); |
||
124 | break; |
||
125 | } |
||
126 | $message->setAdditional($this->contextPrefix . $key, $val); |
||
127 | } |
||
128 | |||
129 | if (null === $message->getFile() && isset($record['context']['exception']['file'])) { |
||
130 | if (preg_match("/^(.+):([0-9]+)$/", $record['context']['exception']['file'], $matches)) { |
||
131 | $message->setFile($matches[1]); |
||
132 | $message->setLine($matches[2]); |
||
133 | } |
||
134 | } |
||
135 | |||
136 | return $message; |
||
137 | } |
||
138 | } |