1<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
2  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3
4<html xmlns="http://www.w3.org/1999/xhtml">
5  <head>
6    <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
7    <title>SLF4J Manual</title>
8    <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
9    <link rel="stylesheet" type="text/css" href="css/prettify.css" />
10  </head>
11  <body onload="prettyPrint(); decorate();">
12    <script type="text/javascript">prefix='';</script>
13    <script type="text/javascript" src="js/prettify.js"></script>
14    <script type="text/javascript" src="js/jquery-min.js"></script>
15    <script type="text/javascript" src="js/decorator.js"></script>
16    <script type="text/javascript" src="templates/header.js"></script>
17    <div id="left">
18      <script type="text/javascript" src="templates/left.js"></script>
19    </div>
20    <div id="content">
21
22
23    <h2>SLF4J user manual</h2>
24
25    <p>The Simple Logging Facade for Java (SLF4J) serves as a simple
26    facade or abstraction for various logging frameworks, such as
27    java.util.logging, logback and log4j. SLF4J allows the end-user to
28    plug in the desired logging framework at <em>deployment</em> time.
29    Note that SLF4J-enabling your library/application implies the
30    addition of only a single mandatory dependency, namely
31    <em>slf4j-api-${project.version}.jar</em>.</p>
32
33    <p><span class="label">since 1.6.0</span> If no binding is found on the
34    class path, then SLF4J will default to a no-operation
35    implementation.
36    </p>
37
38    <p><span class="label">since 1.7.0</span> Printing methods in the
39    <a href="apidocs/org/slf4j/Logger.html"><code>Logger</code></a>
40    interface now offer variants accepting <a
41    href="http://docs.oracle.com/javase/1.5.0/docs/guide/language/varargs.html">varargs</a>
42    instead of <code>Object[]</code>. This change implies that SLF4J
43    requires JDK 1.5 or later.  Under the hood the Java compiler
44    transforms the varargs part in methods into
45    <code>Object[]</code>. Thus, the Logger interface generated by the
46    compiler is indistinguishable in 1.7.x from its 1.6.x
47    counterpart. It follows that SLF4J version 1.7.x is totally 100%
48    no-ifs-or-buts compatible with SLF4J version 1.6.x.
49    </p>
50
51    <p><span class="label">since 1.7.5</span> Significant improvement
52    in logger retrieval times. Given the extent of the improvement,
53    users are highly encouraged to migrate to SLF4J 1.7.5 or later.
54    </p>
55
56    <p><span class="label">since 1.7.9</span> By setting the
57    <code>slf4j.detectLoggerNameMismatch</code> system property to
58    true, SLF4J can automatically <a
59    href="codes.html#loggerNameMismatch">spot incorrectly named
60    loggers</a>.
61    </p>
62
63
64    <h3 class="doAnchor" name="hello_world">Hello World</h3>
65
66    <p>As customary in programming tradition, here is an example
67    illustrating the simplest way to output "Hello world" using SLF4J.
68    It begins by getting a logger with the name "HelloWorld". This
69    logger is in turn used to log the message "Hello World".
70    </p>
71
72<pre class="prettyprint source">import org.slf4j.Logger;
73import org.slf4j.LoggerFactory;
74
75public class HelloWorld {
76  public static void main(String[] args) {
77    Logger logger = LoggerFactory.getLogger(HelloWorld.class);
78    logger.info("Hello World");
79  }
80}</pre>
81
82     <p>To run this example, you first need to <a
83     href="download.html">download the slf4j distribution</a>, and
84     then to unpack it. Once that is done, add the file
85     <em>slf4j-api-${project.version}.jar</em> to your class path.</p>
86
87     <p>Compiling and running <em>HelloWorld</em> will result in the
88     following output being printed on the console.</p>
89
90<pre>SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
91SLF4J: Defaulting to no-operation (NOP) logger implementation
92SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.</pre>
93
94     <p>This warning is printed because no slf4j binding could be
95     found on your class path.</p>
96
97     <p>The warning will disappear as soon as you add a <a
98     href="#swapping">binding</a> to your class path. Assuming you add
99     <em>slf4j-simple-${project.version}.jar</em> so that your class
100     path contains:</p>
101
102     <ul>
103       <li>slf4j-api-${project.version}.jar</li>
104       <li>slf4j-simple-${project.version}.jar</li>
105     </ul>
106
107     <p>Compiling and running <em>HelloWorld</em> will now result in
108     the following output on the console.</p>
109
110     <pre class="output">0 [main] INFO HelloWorld - Hello World</pre>
111
112     <h3 class="doAnchor" name="typical_usage">Typical usage
113     pattern</h3>
114
115     <p>The sample code below illustrates the typical usage pattern
116     for SLF4J. Note the use of {}-placeholders on line 15. See the
117     question <a href="faq.html#logging_performance">"What is the
118     fastest way of logging?"</a> in the FAQ for more details.
119     </p>
120
121     <p></p>
122
123      <pre class="prettyprint source"> 1: <b>import org.slf4j.Logger;</b>
124 2: <b>import org.slf4j.LoggerFactory;</b>
125 3:
126 4: public class Wombat {
127 5:
128 6:   <b>final Logger logger = LoggerFactory.getLogger(Wombat.class);</b>
129 7:   Integer t;
130 8:   Integer oldT;
131 9:
13210:   public void setTemperature(Integer temperature) {
13311:
13412:     oldT = t;
13513:     t = temperature;
13614:
13715:     <b>logger.debug("Temperature set to {}. Old temperature was {}.", t, oldT);</b>
13816:
13917:     if(temperature.intValue() > 50) {
14018:       <b>logger.info("Temperature has risen above 50 degrees.");</b>
14119:     }
14220:   }
14321: } </pre>
144
145
146
147      <h3 class="doAnchor" name="swapping">Binding with a logging
148      framework at deployment time</h3>
149
150      <p>As mentioned previously, SLF4J supports various logging
151      frameworks. The SLF4J distribution ships with several jar files
152      referred to as "SLF4J bindings", with each binding corresponding
153      to a supported framework.  </p>
154
155      <dl>
156
157        <dt><em>slf4j-log4j12-${project.version}.jar</em>
158        </dt>
159        <dd>Binding for <a
160        href="http://logging.apache.org/log4j/1.2/index.html">log4j
161        version 1.2</a>, a widely used logging framework. You also
162        need to place <em>log4j.jar</em> on your class path.<p/></dd>
163
164        <dt><em>slf4j-jdk14-${project.version}.jar</em> </dt>
165        <dd>Binding for java.util.logging, also referred to as JDK 1.4
166        logging <p/></dd>
167
168        <dt><em>slf4j-nop-${project.version}.jar</em></dt>
169        <dd>Binding for <a
170        href="http://www.slf4j.org/api/org/slf4j/helpers/NOPLogger.html">NOP</a>,
171        silently discarding all logging.<p/></dd>
172
173        <dt><em>slf4j-simple-${project.version}.jar</em></dt>
174        <dd>Binding for <a
175        href="http://www.slf4j.org/apidocs/org/slf4j/impl/SimpleLogger.html">Simple
176        </a> implementation, which outputs all events to
177        System.err. Only messages of level INFO and higher are
178        printed. This binding may be useful in the context of small
179        applications.<p/></dd>
180
181        <dt><em>slf4j-jcl-${project.version}.jar</em></dt>
182
183        <dd>Binding for <a
184        href="http://commons.apache.org/logging/">Jakarta Commons
185        Logging</a>. This binding will delegate all SLF4J logging to
186        JCL.<p/>
187        </dd>
188
189        <dt><em>logback-classic-${logback.version}.jar (requires logback-core-${logback.version}.jar)</em></dt>
190
191        <dd><span class="label notice">Native implementation</span> There are also
192        SLF4J bindings external to the SLF4J project, e.g. <a
193        href="http://logback.qos.ch/">logback</a> which implements
194        SLF4J natively.  Logback's
195        <a href="http://logback.qos.ch/apidocs/ch/qos/logback/classic/Logger.html">
196        <code>ch.qos.logback.classic.Logger</code></a> class is a
197        direct implementation of SLF4J's <a
198        href="http://www.slf4j.org/apidocs/org/slf4j/Logger.html">
199        <code>org.slf4j.Logger</code></a> interface. Thus, using SLF4J
200        in conjunction with logback involves strictly zero memory and
201        computational overhead.
202
203        </dd>
204      </dl>
205
206      <p>
207      </p>
208
209
210      <p>To switch logging frameworks, just replace slf4j bindings on
211      your class path. For example, to switch from java.util.logging
212      to log4j, just replace slf4j-jdk14-${project.version}.jar with
213      slf4j-log4j12-${project.version}.jar.
214      </p>
215
216      <p>SLF4J does not rely on any special class loader machinery. In
217      fact, each SLF4J binding is hardwired <em>at compile time</em>
218      to use one and only one specific logging framework.  For
219      example, the slf4j-log4j12-${project.version}.jar binding is
220      bound at compile time to use log4j.  In your code, in addition
221      to <em>slf4j-api-${project.version}.jar</em>, you simply drop
222      <b>one and only one</b> binding of your choice onto the
223      appropriate class path location. Do not place more than one
224      binding on your class path. Here is a graphical illustration of
225      the general idea.
226      </p>
227
228      <p><a href="images/concrete-bindings.png">
229      <img border="1" src="images/concrete-bindings.png" alt="click to enlarge" width="800"/>
230      </a></p>
231
232      <p>The SLF4J interfaces and their various adapters are extremely
233      simple. Most developers familiar with the Java language should
234      be able to read and fully understand the code in less than one
235      hour.  No knowledge of class loaders is necessary as SLF4J does
236      not make use nor does it directly access any class loaders. As a
237      consequence, SLF4J suffers from none of the class loader
238      problems or memory leaks observed with Jakarta Commons Logging
239      (JCL).
240      </p>
241
242      <p>Given the simplicity of the SLF4J interfaces and its
243      deployment model, developers of new logging frameworks should
244      find it very easy to write SLF4J bindings.
245      </p>
246
247      <h3 class="doAnchor" name="libraries">Libraries</h3>
248
249      <p>Authors of widely-distributed components and libraries may
250      code against the SLF4J interface in order to avoid imposing an
251      logging framework on their end-user.  Thus, the end-user may
252      choose the desired logging framework at deployment time by
253      inserting the corresponding slf4j binding on the classpath,
254      which may be changed later by replacing an existing binding with
255      another on the class path and restarting the application.  This
256      approach has proven to be simple and very robust.
257      </p>
258
259      <p><b>As of SLF4J version 1.6.0</b>, if no binding is found on
260      the class path, then slf4j-api will default to a no-operation
261      implementation discarding all log requests. Thus, instead of
262      throwing a <code>NoClassDefFoundError</code> because the
263      <code>org.slf4j.impl.StaticLoggerBinder</code> class is missing,
264      SLF4J version 1.6.0 and later will emit a single warning message
265      about the absence of a binding and proceed to discard all log
266      requests without further protest. For example, let Wombat be
267      some biology-related framework depending on SLF4J for
268      logging. In order to avoid imposing a logging framework on the
269      end-user, Wombat's distribution includes <em>slf4j-api.jar</em>
270      but no binding. Even in the absence of any SLF4J binding on the
271      class path, Wombat's distribution will still work
272      out-of-the-box, and without requiring the end-user to download a
273      binding from SLF4J's web-site. Only when the end-user decides to
274      enable logging will she need to install the SLF4J binding
275      corresponding to the logging framework chosen by her.
276      </p>
277
278      <p><span class="label">Basic rule</span> <b>Embedded components
279      such as libraries or frameworks should not declare a dependency
280      on any SLF4J binding but only depend on slf4j-api</b>. When a
281      library declares a transitive dependency on a specific binding,
282      that binding is imposed on the end-user negating the purpose of
283      SLF4J. Note that declaring a non-transitive dependency on a
284      binding, for example for testing, does not affect the
285      end-user.</p>
286
287      <p>SLF4J usage in embedded components is also discussed in the
288      FAQ in relation with <a
289      href="faq.html#configure_logging">logging configuration</a>, <a
290      href="faq.html#optional_dependency">dependency reduction</a> and
291      <a href="faq.html#optional_dependency">testing</a>.</p>
292
293      <h3 class="doAnchor" name="projectDep">Declaring project
294      dependencies for logging</h3>
295
296      <p>Given Maven's transitive dependency rules, for "regular"
297      projects (not libraries or frameworks) declaring logging
298      dependencies can be accomplished with a single dependency
299      declaration.
300      </p>
301
302      <p><span class="label notice">logback-classic</span> If you wish
303      to use logback-classic as the underlying logging framework, all
304      you need to do is to declare "ch.qos.logback:logback-classic" as
305      a dependency in your <em>pom.xml</em> file as shown below. In
306      addition to <em>logback-classic-${logback.version}.jar</em>,
307      this will pull <em>slf4j-api-${project.version}.jar</em> as well
308      as <em>logback-core-${logback.version}.jar</em> into your
309      project. Note that explicitly declaring a dependency on
310      <em>logback-core-${logback.version}</em> or
311      <em>slf4j-api-${project.version}.jar</em> is not wrong and may
312      be necessary to impose the correct version of said artifacts by
313      virtue of Maven's "nearest definition" dependency mediation
314      rule.
315      </p>
316
317<pre class="prettyprint source">&lt;dependency>
318  &lt;groupId>ch.qos.logback&lt;/groupId>
319  &lt;artifactId>logback-classic&lt;/artifactId>
320  &lt;version>${logback.version}&lt;/version>
321&lt;/dependency></pre>
322
323     <p/>
324
325      <p><span class="label notice">log4j</span> If you wish to use
326      log4j as the underlying logging framework, all you need to do is
327      to declare "org.slf4j:slf4j-log4j12" as a dependency in your
328      <em>pom.xml</em> file as shown below. In addition to
329      <em>slf4j-log4j12-${project.version}.jar</em>, this will pull
330      <em>slf4j-api-${project.version}.jar</em> as well as
331      <em>log4j-${log4j.version}.jar</em> into your project.  Note
332      that explicitly declaring a dependency on
333      <em>log4j-${log4j.version}.jar</em> or
334      <em>slf4j-api-${project.version}.jar</em> is not wrong and may
335      be necessary to impose the correct version of said artifacts by
336      virtue of Maven's "nearest definition" dependency mediation
337      rule.</p>
338
339<pre class="prettyprint source">&lt;dependency>
340  &lt;groupId>org.slf4j&lt;/groupId>
341  &lt;artifactId>slf4j-log4j12&lt;/artifactId>
342  &lt;version>${project.version}&lt;/version>
343&lt;/dependency></pre>
344
345     <p/>
346
347      <p><span class="label notice">java.util.logging</span> If you
348      wish to use java.util.logging as the underlying logging
349      framework, all you need to do is to declare
350      "org.slf4j:slf4j-jdk14" as a dependency in your <em>pom.xml</em>
351      file as shown below. In addition to
352      <em>slf4j-jdk14-${project.version}.jar</em>, this will pull
353      <em>slf4j-api-${project.version}.jar</em> into your project.
354      Note that explicitly declaring a dependency on
355      <em>slf4j-api-${project.version}.jar</em> is not wrong and may
356      be necessary to impose the correct version of said artifact by
357      virtue of Maven's "nearest definition" dependency mediation
358      rule.</p>
359
360<pre class="prettyprint source">&lt;dependency>
361  &lt;groupId>org.slf4j&lt;/groupId>
362  &lt;artifactId>slf4j-jdk14&lt;/artifactId>
363  &lt;version>${project.version}&lt;/version>
364&lt;/dependency></pre>
365
366
367
368      <h3 class="doAnchor" name="compatibility">Binary
369      compatibility</h3>
370
371      <p>An SLF4J binding designates an artifact such as
372      <em>slf4j-jdk14.jar</em> or <em>slf4j-log4j12.jar</em> used to
373      <em>bind</em> slf4j to an underlying logging framework, say,
374      java.util.logging and respectively log4j.
375      </p>
376
377      <p class="highlight">From the client's perspective all versions
378      of slf4j-api are compatible.  Client code compiled with
379      slf4j-api-N.jar will run perfectly fine with slf4j-api-M.jar for
380      any N and M. You only need to ensure that the version of your
381      binding matches that of the slf4j-api.jar. You do not have to
382      worry about the version of slf4j-api.jar used by a given
383      dependency in your project. </p>
384
385
386      <p>Mixing different versions of <em>slf4j-api.jar</em> and SLF4J
387      binding can cause problems. For example, if you are using
388      slf4j-api-${project.version}.jar, then you should also use
389      slf4j-simple-${project.version}.jar, using
390      slf4j-simple-1.5.5.jar will not work.</p>
391
392
393      <p>However, from the client's perspective all versions of
394      slf4j-api are compatible. Client code compiled with
395      <em>slf4j-api-N.jar</em> will run perfectly fine with
396      <em>slf4j-api-M.jar</em> for any N and M. You only need to
397      ensure that the version of your binding matches that of the
398      slf4j-api.jar. You do not have to worry about the version of
399      slf4j-api.jar used by a given dependency in your project. You
400      can always use any version of <em>slf4j-api.jar</em>, and as
401      long as the version of <em>slf4j-api.jar</em> and its binding
402      match, you should be fine.
403      </p>
404
405      <p>At initialization time, if SLF4J suspects that there may be
406      an slf4j-api vs. binding version mismatch problem, it will emit
407      a warning about the suspected mismatch.
408      </p>
409
410
411      <h3 class="doAnchor" name="consolidate">Consolidate logging via
412      SLF4J</h3>
413
414      <p>Often times, a given project will depend on various
415      components which rely on logging APIs other than SLF4J. It is
416      common to find projects depending on a combination of JCL,
417      java.util.logging, log4j and SLF4J. It then becomes desirable to
418      consolidate logging through a single channel. SLF4J caters for
419      this common use-case by providing bridging modules for JCL,
420      java.util.logging and log4j. For more details, please refer to
421      the page on <a href="legacy.html"><b>Bridging legacy
422      APIs</b></a>.
423      </p>
424
425      <h3 class="doAnchor" name="mdc">Mapped Diagnostic Context (MDC) support</h3>
426
427      <p>"Mapped Diagnostic Context" is essentially a map maintained
428      by the logging framework where the application code provides
429      key-value pairs which can then be inserted by the logging
430      framework in log messages. MDC data can also be highly helpful
431      in filtering messages or triggering certain actions.</p>
432
433      <p>SLF4J supports MDC, or mapped diagnostic context. If the
434      underlying logging framework offers MDC functionality, then
435      SLF4J will delegate to the underlying framework's MDC. Note that
436      at this time, only log4j and logback offer MDC functionality. If
437      the underlying framework does not offer MDC, for example
438      java.util.logging, then SLF4J will still store MDC data but the
439      information therein will need to be retrieved by custom user
440      code.</p>
441
442      <p>Thus, as a SLF4J user, you can take advantage of MDC
443      information in the presence of log4j or logback, but without
444      forcing these logging frameworks upon your users as
445      dependencies.
446      </p>
447
448      <p>For more information on MDC please see the <a
449      href="http://logback.qos.ch/manual/mdc.html">chapter on MDC</a>
450      in the logback manual.
451      </p>
452
453
454
455      <h3 class="doAnchor" name="summary">Executive summary</h3>
456
457      <table  class="bodyTable striped" cellspacing="4" cellpadding="4">
458        <tr>
459          <th align="left">Advantage</th>
460          <th align="left">Description</th>
461        </tr>
462
463        <tr>
464
465          <td>Select your logging framework at deployment time</td>
466
467          <td>The desired logging framework can be plugged in at
468          deployment time by inserting the appropriate jar file
469          (binding) on your class path.
470          </td>
471        </tr>
472
473
474        <tr>
475          <td>Fail-fast operation</td>
476
477          <td>Due to the way that classes are loaded by the JVM, the
478          framework binding will be verified automatically very early
479          on.  If SLF4J cannot find a binding on the class path it
480          will emit a single warning message and default to
481          no-operation implementation.
482          </td>
483        </tr>
484
485
486        <tr>
487          <td>Bindings for popular logging frameworks
488          </td>
489
490          <td>SLF4J supports popular logging frameworks, namely log4j,
491          java.util.logging, Simple logging and NOP. The <a
492          href="http://logback.qos.ch">logback</a> project supports
493          SLF4J natively.  </td>
494
495        </tr>
496
497        <tr>
498          <td>Bridging legacy logging APIs</td>
499
500          <td>
501            <p>The implementation of JCL over SLF4J, i.e
502            <em>jcl-over-slf4j.jar</em>, will allow your project to
503            migrate to SLF4J piecemeal, without breaking compatibility
504            with existing software using JCL. Similarly,
505            log4j-over-slf4j.jar and jul-to-slf4j modules will allow
506            you to redirect log4j and respectively java.util.logging
507            calls to SLF4J. See the page on <a
508            href="legacy.html">Bridging legacy APIs</a> for more
509            details.
510            </p>
511          </td>
512        </tr>
513
514        <tr>
515          <td>Migrate your source code</td>
516          <td>The <a href="migrator.html">slf4j-migrator</a> utility
517          can help you migrate your source to use SLF4J.
518          </td>
519        </tr>
520
521
522
523        <tr>
524          <td>Support for parameterized log messages</td>
525
526          <td>All SLF4J bindings support parameterized log messages
527          with significantly <a
528          href="faq.html#logging_performance">improved performance</a>
529          results.</td>
530        </tr>
531
532
533  </table>
534
535  <script src="templates/footer.js" type="text/javascript"></script>
536
537</div>
538</body>
539</html>
540