1: <?php
2: /**
3: * CakePHP(tm) : Rapid Development Framework (https://cakephp.org)
4: * Copyright (c) Cake Software Foundation, Inc. (https://cakefoundation.org)
5: *
6: * Licensed under The MIT License
7: * For full copyright and license information, please see the LICENSE.txt
8: * Redistributions of files must retain the above copyright notice.
9: *
10: * @copyright Copyright (c) Cake Software Foundation, Inc. (https://cakefoundation.org)
11: * @link https://cakefoundation.org CakePHP(tm) Project
12: * @since 2.4.0
13: * @license https://opensource.org/licenses/mit-license.php MIT License
14: */
15: namespace Cake\Log\Engine;
16:
17: /**
18: * Syslog stream for Logging. Writes logs to the system logger
19: */
20: class SyslogLog extends BaseLog
21: {
22: /**
23: * Default config for this class
24: *
25: * By default messages are formatted as:
26: * level: message
27: *
28: * To override the log format (e.g. to add your own info) define the format key when configuring
29: * this logger
30: *
31: * If you wish to include a prefix to all messages, for instance to identify the
32: * application or the web server, then use the prefix option. Please keep in mind
33: * the prefix is shared by all streams using syslog, as it is dependent of
34: * the running process. For a local prefix, to be used only by one stream, you
35: * can use the format key.
36: *
37: * ### Example:
38: *
39: * ```
40: * Log::config('error', ]
41: * 'engine' => 'Syslog',
42: * 'levels' => ['emergency', 'alert', 'critical', 'error'],
43: * 'format' => "%s: My-App - %s",
44: * 'prefix' => 'Web Server 01'
45: * ]);
46: * ```
47: *
48: * @var array
49: */
50: protected $_defaultConfig = [
51: 'levels' => [],
52: 'scopes' => [],
53: 'format' => '%s: %s',
54: 'flag' => LOG_ODELAY,
55: 'prefix' => '',
56: 'facility' => LOG_USER
57: ];
58:
59: /**
60: * Used to map the string names back to their LOG_* constants
61: *
62: * @var int[]
63: */
64: protected $_levelMap = [
65: 'emergency' => LOG_EMERG,
66: 'alert' => LOG_ALERT,
67: 'critical' => LOG_CRIT,
68: 'error' => LOG_ERR,
69: 'warning' => LOG_WARNING,
70: 'notice' => LOG_NOTICE,
71: 'info' => LOG_INFO,
72: 'debug' => LOG_DEBUG
73: ];
74:
75: /**
76: * Whether the logger connection is open or not
77: *
78: * @var bool
79: */
80: protected $_open = false;
81:
82: /**
83: * Writes a message to syslog
84: *
85: * Map the $level back to a LOG_ constant value, split multi-line messages into multiple
86: * log messages, pass all messages through the format defined in the configuration
87: *
88: * @param string $level The severity level of log you are making.
89: * @param string $message The message you want to log.
90: * @param array $context Additional information about the logged message
91: * @return bool success of write.
92: */
93: public function log($level, $message, array $context = [])
94: {
95: if (!$this->_open) {
96: $config = $this->_config;
97: $this->_open($config['prefix'], $config['flag'], $config['facility']);
98: $this->_open = true;
99: }
100:
101: $priority = LOG_DEBUG;
102: if (isset($this->_levelMap[$level])) {
103: $priority = $this->_levelMap[$level];
104: }
105:
106: $messages = explode("\n", $this->_format($message, $context));
107: foreach ($messages as $message) {
108: $message = sprintf($this->_config['format'], $level, $message);
109: $this->_write($priority, $message);
110: }
111:
112: return true;
113: }
114:
115: /**
116: * Extracts the call to openlog() in order to run unit tests on it. This function
117: * will initialize the connection to the system logger
118: *
119: * @param string $ident the prefix to add to all messages logged
120: * @param int $options the options flags to be used for logged messages
121: * @param int $facility the stream or facility to log to
122: * @return void
123: */
124: protected function _open($ident, $options, $facility)
125: {
126: openlog($ident, $options, $facility);
127: }
128:
129: /**
130: * Extracts the call to syslog() in order to run unit tests on it. This function
131: * will perform the actual write in the system logger
132: *
133: * @param int $priority Message priority.
134: * @param string $message Message to log.
135: * @return bool
136: */
137: protected function _write($priority, $message)
138: {
139: return syslog($priority, $message);
140: }
141:
142: /**
143: * Closes the logger connection
144: */
145: public function __destruct()
146: {
147: closelog();
148: }
149: }
150: