PageRenderTime 47ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/accepted/PSR-3-logger-interface.md

https://bitbucket.org/tofiradi/fig-standards
Markdown | 304 lines | 248 code | 56 blank | 0 comment | 0 complexity | c1ae34f5d56b33ce8b7e7d9a7ac25ab2 MD5 | raw file
Possible License(s): CC-BY-3.0
  1. Logger Interface
  2. ================
  3. This document describes a common interface for logging libraries.
  4. The main goal is to allow libraries to receive a `Psr\Log\LoggerInterface`
  5. object and write logs to it in a simple and universal way. Frameworks
  6. and CMSs that have custom needs MAY extend the interface for their own
  7. purpose, but SHOULD remain compatible with this document. This ensures
  8. that the third-party libraries an application uses can write to the
  9. centralized application logs.
  10. The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD",
  11. "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be
  12. interpreted as described in [RFC 2119][].
  13. The word `implementor` in this document is to be interpreted as someone
  14. implementing the `LoggerInterface` in a log-related library or framework.
  15. Users of loggers are referred to as `user`.
  16. [RFC 2119]: http://tools.ietf.org/html/rfc2119
  17. ## 1. Specification
  18. ### 1.1 Basics
  19. - The `LoggerInterface` exposes eight methods to write logs to the eight
  20. [RFC 5424][] levels (debug, info, notice, warning, error, critical, alert,
  21. emergency).
  22. - A ninth method, `log`, accepts a log level as the first argument. Calling this
  23. method with one of the log level constants MUST have the same result as
  24. calling the level-specific method. Calling this method with a level not
  25. defined by this specification MUST throw a `Psr\Log\InvalidArgumentException`
  26. if the implementation does not know about the level. Users SHOULD NOT use a
  27. custom level without knowing for sure the current implementation supports it.
  28. [RFC 5424]: http://tools.ietf.org/html/rfc5424
  29. ### 1.2 Message
  30. - Every method accepts a string as the message, or an object with a
  31. `__toString()` method. Implementors MAY have special handling for the passed
  32. objects. If that is not the case, implementors MUST cast it to a string.
  33. - The message MAY contain placeholders which implementors MAY replace with
  34. values from the context array.
  35. Placeholder names MUST correspond to keys in the context array.
  36. Placeholder names MUST be delimited with a single opening brace `{` and
  37. a single closing brace `}`. There MUST NOT be any whitespace between the
  38. delimiters and the placeholder name.
  39. Placeholder names SHOULD be composed only of the characters `A-Z`, `a-z`,
  40. `0-9`, underscore `_`, and period `.`. The use of other characters is
  41. reserved for future modifications of the placeholders specification.
  42. Implementors MAY use placeholders to implement various escaping strategies
  43. and translate logs for display. Users SHOULD NOT pre-escape placeholder
  44. values since they can not know in which context the data will be displayed.
  45. The following is an example implementation of placeholder interpolation
  46. provided for reference purposes only:
  47. ~~~php
  48. <?php
  49. /**
  50. * Interpolates context values into the message placeholders.
  51. */
  52. function interpolate($message, array $context = array())
  53. {
  54. // build a replacement array with braces around the context keys
  55. $replace = array();
  56. foreach ($context as $key => $val) {
  57. // check that the value can be casted to string
  58. if (!is_array($val) && (!is_object($val) || method_exists($val, '__toString'))) {
  59. $replace['{' . $key . '}'] = $val;
  60. }
  61. }
  62. // interpolate replacement values into the message and return
  63. return strtr($message, $replace);
  64. }
  65. // a message with brace-delimited placeholder names
  66. $message = "User {username} created";
  67. // a context array of placeholder names => replacement values
  68. $context = array('username' => 'bolivar');
  69. // echoes "User bolivar created"
  70. echo interpolate($message, $context);
  71. ~~~
  72. ### 1.3 Context
  73. - Every method accepts an array as context data. This is meant to hold any
  74. extraneous information that does not fit well in a string. The array can
  75. contain anything. Implementors MUST ensure they treat context data with
  76. as much lenience as possible. A given value in the context MUST NOT throw
  77. an exception nor raise any php error, warning or notice.
  78. - If an `Exception` object is passed in the context data, it MUST be in the
  79. `'exception'` key. Logging exceptions is a common pattern and this allows
  80. implementors to extract a stack trace from the exception when the log
  81. backend supports it. Implementors MUST still verify that the `'exception'`
  82. key is actually an `Exception` before using it as such, as it MAY contain
  83. anything.
  84. ### 1.4 Helper classes and interfaces
  85. - The `Psr\Log\AbstractLogger` class lets you implement the `LoggerInterface`
  86. very easily by extending it and implementing the generic `log` method.
  87. The other eight methods are forwarding the message and context to it.
  88. - Similarly, using the `Psr\Log\LoggerTrait` only requires you to
  89. implement the generic `log` method. Note that since traits can not implement
  90. interfaces, in this case you still have to implement `LoggerInterface`.
  91. - The `Psr\Log\NullLogger` is provided together with the interface. It MAY be
  92. used by users of the interface to provide a fall-back "black hole"
  93. implementation if no logger is given to them. However, conditional logging
  94. may be a better approach if context data creation is expensive.
  95. - The `Psr\Log\LoggerAwareInterface` only contains a
  96. `setLogger(LoggerInterface $logger)` method and can be used by frameworks to
  97. auto-wire arbitrary instances with a logger.
  98. - The `Psr\Log\LoggerAwareTrait` trait can be used to implement the equivalent
  99. interface easily in any class. It gives you access to `$this->logger`.
  100. - The `Psr\Log\LogLevel` class holds constants for the eight log levels.
  101. ## 2. Package
  102. The interfaces and classes described as well as relevant exception classes
  103. and a test suite to verify your implementation are provided as part of the
  104. [psr/log](https://packagist.org/packages/psr/log) package.
  105. ## 3. `Psr\Log\LoggerInterface`
  106. ~~~php
  107. <?php
  108. namespace Psr\Log;
  109. /**
  110. * Describes a logger instance
  111. *
  112. * The message MUST be a string or object implementing __toString().
  113. *
  114. * The message MAY contain placeholders in the form: {foo} where foo
  115. * will be replaced by the context data in key "foo".
  116. *
  117. * The context array can contain arbitrary data, the only assumption that
  118. * can be made by implementors is that if an Exception instance is given
  119. * to produce a stack trace, it MUST be in a key named "exception".
  120. *
  121. * See https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-3-logger-interface.md
  122. * for the full interface specification.
  123. */
  124. interface LoggerInterface
  125. {
  126. /**
  127. * System is unusable.
  128. *
  129. * @param string $message
  130. * @param array $context
  131. * @return void
  132. */
  133. public function emergency($message, array $context = array());
  134. /**
  135. * Action must be taken immediately.
  136. *
  137. * Example: Entire website down, database unavailable, etc. This should
  138. * trigger the SMS alerts and wake you up.
  139. *
  140. * @param string $message
  141. * @param array $context
  142. * @return void
  143. */
  144. public function alert($message, array $context = array());
  145. /**
  146. * Critical conditions.
  147. *
  148. * Example: Application component unavailable, unexpected exception.
  149. *
  150. * @param string $message
  151. * @param array $context
  152. * @return void
  153. */
  154. public function critical($message, array $context = array());
  155. /**
  156. * Runtime errors that do not require immediate action but should typically
  157. * be logged and monitored.
  158. *
  159. * @param string $message
  160. * @param array $context
  161. * @return void
  162. */
  163. public function error($message, array $context = array());
  164. /**
  165. * Exceptional occurrences that are not errors.
  166. *
  167. * Example: Use of deprecated APIs, poor use of an API, undesirable things
  168. * that are not necessarily wrong.
  169. *
  170. * @param string $message
  171. * @param array $context
  172. * @return void
  173. */
  174. public function warning($message, array $context = array());
  175. /**
  176. * Normal but significant events.
  177. *
  178. * @param string $message
  179. * @param array $context
  180. * @return void
  181. */
  182. public function notice($message, array $context = array());
  183. /**
  184. * Interesting events.
  185. *
  186. * Example: User logs in, SQL logs.
  187. *
  188. * @param string $message
  189. * @param array $context
  190. * @return void
  191. */
  192. public function info($message, array $context = array());
  193. /**
  194. * Detailed debug information.
  195. *
  196. * @param string $message
  197. * @param array $context
  198. * @return void
  199. */
  200. public function debug($message, array $context = array());
  201. /**
  202. * Logs with an arbitrary level.
  203. *
  204. * @param mixed $level
  205. * @param string $message
  206. * @param array $context
  207. * @return void
  208. */
  209. public function log($level, $message, array $context = array());
  210. }
  211. ~~~
  212. ## 4. `Psr\Log\LoggerAwareInterface`
  213. ~~~php
  214. <?php
  215. namespace Psr\Log;
  216. /**
  217. * Describes a logger-aware instance
  218. */
  219. interface LoggerAwareInterface
  220. {
  221. /**
  222. * Sets a logger instance on the object
  223. *
  224. * @param LoggerInterface $logger
  225. * @return void
  226. */
  227. public function setLogger(LoggerInterface $logger);
  228. }
  229. ~~~
  230. ## 5. `Psr\Log\LogLevel`
  231. ~~~php
  232. <?php
  233. namespace Psr\Log;
  234. /**
  235. * Describes log levels
  236. */
  237. class LogLevel
  238. {
  239. const EMERGENCY = 'emergency';
  240. const ALERT = 'alert';
  241. const CRITICAL = 'critical';
  242. const ERROR = 'error';
  243. const WARNING = 'warning';
  244. const NOTICE = 'notice';
  245. const INFO = 'info';
  246. const DEBUG = 'debug';
  247. }
  248. ~~~