aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatt Gilbride <mattgilbride@google.com>2024-02-16 22:31:55 +0000
committerMatt Gilbride <mattgilbride@google.com>2024-02-20 14:40:13 +0000
commitdb1c67ccaa0dc16b93299917c297a8b9431f3dff (patch)
treeac78ecd141a06ef99874d72dae00891f6a4c1889
parent512a8c6973b2cf03a84489cde5219c77b1388cb7 (diff)
downloadslf4j-db1c67ccaa0dc16b93299917c297a8b9431f3dff.tar.gz
Merge upstream v_2.0.12 into main
Result of running the following git commands locally: ``` git remote add upstream https://github.com/qos-ch/slf4j.git git fetch upstream --tags git merge --squash v_2.0.12 ``` Also includes two manual changes: - Manually updated METADATA per the conventions laid out in go/android3p. - Manually updated Android.bp to exclude src/main/java9 directory for slf4j-jdk14 (breaks the build if included) - Removed reference to log4j in `log4j-over-slf4j/pom.xml` Squashed commit of the following: commit 955209464d517cd91186f6407a60feb202dc26b8 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 5 22:32:22 2024 +0100 increase leniency count Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c1473c957abef18532a6cbbb27a93d7baf58e3f0 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 5 22:21:34 2024 +0100 prepare release 2.0.12 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 98932348fbc5bf9925e0d09357ac4ca90f81d453 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 5 22:20:48 2024 +0100 minor reminder Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c52da92599b1316c5b7216c8ecf5dab68341e861 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 5 22:17:54 2024 +0100 revert Util.report methods removed by mistake Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit da91e4f2198e49121e308de5acca2fd2bbfbf452 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 5 21:45:58 2024 +0100 export provider packages, allow reflection by org.slf4j Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8c4ea8f225bd45719687849f4dc55f08028f6971 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 23 15:51:31 2024 +0100 more comments Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6b2921a52341d881e89e1fafe386fd00c25fb6cf Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 20:50:02 2024 +0100 start wotk on 2.0.12-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3f4717c44e26d586e2b03b1b87cfff63248e993a Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 20:48:59 2024 +0100 get javadoc:aggregate command to work Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d9145fba56fc213646d38a3230f60f76aba10bbf Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 18:58:10 2024 +0100 prepare release 2.0.11 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 68ff7064ecde0867ed97053ecc565eb85beb417c Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 18:50:54 2024 +0100 acceptance test, disabled for the moment Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit db8cd90c10cda662db899e1f72644638013b7ec6 Author: Guillaume Nodet <gnodet@gmail.com> Date: Mon Jan 8 16:41:13 2024 +0100 Use computeIfAbsent with a protected method, make reset protected Signed-off-by: Guillaume Nodet <gnodet@gmail.com> commit d564304a6137c1f5ec0e0ed890658bf4b817371b Author: Guillaume Nodet <gnodet@gmail.com> Date: Mon Jan 8 16:38:48 2024 +0100 Use computeIfAbsent with a protected method, make reset protected Signed-off-by: Guillaume Nodet <gnodet@gmail.com> commit ef8dda71dd8d9b86f623c9fe6d9eaa83d1722ab6 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 15:23:23 2024 +0100 javadoc changed for SimpleLogger constructor Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit fe42ecb5f74cdda9927fe0889229199a08d23ec8 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 15:16:08 2024 +0100 change constructor access modifier instead of Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7029a8b7fda826f425c740a847e97f4c0a063dbe Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 8 15:02:22 2024 +0100 add renderLevel method in SimpleLogger Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8c873b2e75667d284817300c167698ec57572324 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 29 00:03:40 2023 +0100 start work on 2.0.11-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7bcee9aa1f24bc73cab13a9eb59ed6abafd66e0a Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 29 00:02:38 2023 +0100 javadoc configuration tweak Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6fe9c07113feee42d88c8478fc7c404b977fe62e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 28 21:48:34 2023 +0100 more javadoc adjustments Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit df562c22d8617e7ae4e11a56c3defd24c6c1ceda Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 28 21:38:38 2023 +0100 migrator should have javadocs Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6d39ca8bf9d937da8e1b86ce719f5d888f5a00f5 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 28 21:14:08 2023 +0100 prepare release 2.0.10 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 86ee8298d9ff7df30d007a83463bd7f5718aeea3 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Dec 6 20:54:40 2023 +0100 javadoc edit Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5ccbe20b118828f35fd64a887d77fb9b72ad1a6e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 5 10:02:43 2023 +0100 remove unreachable code, see issues/371 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 02b36a269a9b13dac435699839f3200529dd0e10 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Nov 25 20:47:16 2023 +0100 attempt at fixing PR 358 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c12667b9063b2b9409ed49072d9746f34f968440 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 17 12:57:30 2023 +0100 document Reporter class Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 316b5d1727d647250ff791565650070094f5b85e Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Nov 15 19:59:01 2023 +0100 first attempt at fixing issues/361 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7c164fab8d54f823dd55c01a5a839c153f578297 Author: Hervé Boutemy <hboutemy@apache.org> Date: Sun Sep 3 22:56:46 2023 +0200 upgrade maven-bundle-plugin fixes Reproducible Builds issue with OSGi metadata commit 56e42fdb61087ce08d8fc0623de80b205a0394cd Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 3 18:20:34 2023 +0200 start work on 2.0.10-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 216459e5d81c3b066748c51a4eabcda32395fe05 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 3 18:12:02 2023 +0200 prepare release 2.0.9 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2481810f94f32923db5eb86f6cc1bbebb069be34 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 3 18:06:27 2023 +0200 rename slf4j.binding system proerty as slf4j.provider Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 25d742d6669c348fd149b4df1a52bf2f4c0dbe1a Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 3 17:44:47 2023 +0200 start work on 2.0.9-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 10a151756d4ab7c79a95e5a74a3ed33fd7cf82a0 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 29 23:31:08 2023 +0200 further adjusments for successful deployment on Maven Central Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 17f5bf3d87551c2ab7a6e2e842cf4ef8f80b4958 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 29 23:04:24 2023 +0200 fix issues during deployment Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f967033766498679a3d2bd2de8887514a5154ad7 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 29 22:50:25 2023 +0200 move parent-pom.xml to parent/pom.xml as explained in SLF4J-437 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0b9c92cc3a4b24609c4cf93b5c984c7900982310 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 29 22:14:17 2023 +0200 prepare release 2.0.8 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 05698f8d238139f7cd345592a2c1fb78eafda230 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 29 22:06:48 2023 +0200 fine tuning for SLF4J-450 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 9783320b6c4411a0b120cad9e32cd9a981b1dac2 Author: Kengo TODA <skypencil@gmail.com> Date: Tue Jul 14 07:48:20 2020 +0800 feat: allow binding to be explicitly specified commit aa13da39edd4195c25eecb1263c4bf3f8902a3e4 Author: Ethan McCue <ethan@mccue.dev> Date: Mon Aug 7 17:44:11 2023 -0400 Fix typo in "SLF4JPlarformLoggerFactory" Signed-off-by: Ethan McCue <ethan@mccue.dev> commit 7a4da876b361b347acf67611a21c8e14be41e6a0 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 8 18:20:12 2023 +0200 add equals/hashCode to KeyValuePair Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0769bc8182b89b9d8a040decf80d087aa7303c4d Author: Taku Miyakawa <miyakawa.taku@gmail.com> Date: Wed Dec 22 21:46:09 2021 +0900 use MessageFormat insetad of String.format to comply spec of System.Logger.log Signed-off-by: Taku Miyakawa <miyakawa.taku@gmail.com> commit e63f87f02cdc732d9efb0d806675f94e5b7a67fc Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jul 12 22:50:26 2023 +0200 fix SLF4J-595 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3f20e0dfd27909615513a52a56b0ea1b57f59c02 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jul 12 21:52:15 2023 +0200 update certain plugins, add parent-pom.xml as a module fixing SLF4J-596 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 06fa09a2fbdad25317493a7bed0bb8e1ec5388f2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jul 11 11:04:41 2023 +0200 use jar plugin to add MainClass information in MANIFEST.MF instead of the fleix plugin, see SLF4J-594 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6fd9db9b5eef541d9648d486b5db096ed5d00b37 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 16 18:05:17 2023 +0200 add BOM file, fixes SLF4J-437 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f871e7f2e9f3f3959e987967655dfcb15494a3d3 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Thu Jan 12 23:15:08 2023 +0100 Restore 'Main-Class' header in slf4j-migrator Manifest.MF Because the Manifest.MF did not have a terminating new-line it was invalid and its content was ignored, thus the Main-Class entry was missing. To have less files in the project, generate the entry using the maven-bundle-plugin. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit 0b4d88edef0ba705e3de8b948fe44614ea910aa5 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Sun Mar 19 10:11:10 2023 +0100 Use project.name in Bundle-Name and simplify slf4j-api OSGi metadata gen The value of project.name is more expressive than the previously used project.artifactId. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit 2ec7c1034c8e3c30a8c5c94a212cc4e7c69a8c15 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Sat Mar 18 15:03:16 2023 +0100 Replace all remaining OSGi MANIFEST.MF by bundle-plugin instructions This ensures that there is only a single source for OSGi metadata. Additionally this improves the metadata for some Export-Package entries. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit df44ace9c3f9f09ad4fd861ed4b9a304872c08e2 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Thu Jan 12 23:13:47 2023 +0100 Automate OSGi metadata creation and fix metadata for other slf4j-modules Only use the maven-bundle-plugin to generate all OSGi metadata into slf4j's Manifest.MF files. This unifies the resulting MANIFEST.MFs that are currently partly generated and partly statically defined and fixes the following aspects: - Fix the package-export of slf4j-jdk-platform-logging (from 'slf4j.jdk.platform.logging' to 'org.slf4j.jdk.platform.logging') - Import missing packages for slf4j-reload4j and log4j-over-slf4j - Replace the deprecated 'Bundle-RequiredExecutionEnvironment' by a corresponding required 'osgi.ee' capability - Restores the exported packages of jcl-over-slf4j Fixes https://jira.qos.ch/browse/SLF4J-578 Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit 661869eeb29bb02cbbc5747e3b68885fbdb5e794 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Sun Mar 19 10:19:21 2023 +0100 Adapt project names from 'Binding' to 'Provider' Since slf4j 2 Bindings are now called Providers. The corresponding Maven project names and descriptions should be adapted accordingly. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit cff3312e43e7a9bd6ae664ad2f71c0457822f672 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 17 20:41:07 2023 +0100 start work on 2.0.8-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d6a21ae68f8a996bc24526f82ec46907e6688bc0 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 17 20:35:35 2023 +0100 update javadoc plugin to version 3.0.5 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 13950e51a62893eae6a5f6d9f842fe5554b7d4f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 17 19:49:13 2023 +0100 prepare release 2.0.7 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 122e0c18dd59c1c7ef425e89e6097c07ee2358b9 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 17 19:35:56 2023 +0100 add LICENSE.txt files to all modules, rename LICENSE as LICENSE.txt when appropriate Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2a8ca99cafe8a20c2dc57ed7297ec68c574b0b94 Author: TWI <audi-connect@msg.group> Date: Wed Jan 25 10:40:54 2023 +0100 add license file to jar commit b363bb31ed08d3ad9761ccdca5e51bb2327c3287 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Wed Dec 21 00:07:48 2022 +0100 SLF4J-579: Export client packages of slf4j-api in version 1 Fixes https://jira.qos.ch/browse/SLF4J-576 This allows to use the slf4j-api version 2 artifact as drop-in replacement for slf4j-api version 1 in OSGi environments as well. slf4j-api can now be wired to bundles that require packages of slf4j-api in version 1 or 2. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit 2235d3c69829caf19e38ea980a86042cc3ffd1f3 Author: Hannes Wellmann <wellmann.hannes1@gmx.net> Date: Wed Mar 15 21:28:25 2023 +0100 Fully automate OSGi metadata creation and fix brocken OSGi-metadata in slf4j-api (#330) * Improve generated OSGi metadata and restore Bundle-SymbolicName Enhance the generated OSGi metadata for all slf4j-modules in the following ways: - Restore the Bundle-SymbolicName, Bundle-Name, Bundle-Vendor and Bundle-DocURL from SLF4J-2.0.5 and before - Removes Export-Package: META-INF.versions.9 - Removes self-Imports of exported package (has to be added again in a follow up, where desired) - Remove unnecessary BND-internal headers Additionally move the maven-bundle-plugin configuration from the execution configuration up into the configuration of the plugin so that it can be easier overwritten in child-modules. Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> * Automate OSGi metadata creation and restore package-exports of slf4j-api Only use the maven-bundle-plugin to generate all OSGi metadata into slf4j-api's Manifest.MF file. This unifies the resulting MANIFEST.MFs that are currently partly generated and partly statically defined. Furthermore it fixes the following flaws in the currently generated OSGi metadata of slf4j-api: - Import only the exported org.slf4j.spi package (like in slf4j 2.0.5 and before) - Replace the deprecated 'Bundle-RequiredExecutionEnvironment' header by a corresponding required 'osgi.ee' capability Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> --------- Signed-off-by: Hannes Wellmann <wellmann.hannes1@gmx.net> commit a5540ad51066b4b15132fdf27ead630519541d35 Author: Sean C. Sullivan <github@seansullivan.com> Date: Sun Jul 3 10:05:34 2022 -0700 setup-java v3 Signed-off-by: Sean C. Sullivan <github@seansullivan.com> commit 1ed084cbc061f0bcbc9250867771550684be25fa Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 19 20:25:11 2022 +0100 add missing distribution instruction to github action Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b2cb0174225d1163730a209a6a433068fa281903 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 19 20:21:52 2022 +0100 update github action versions Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit fa6721a53eb4b2d13491400908f9ca76c7997300 Author: Sean C. Sullivan <github@seansullivan.com> Date: Mon Dec 19 10:04:38 2022 -0800 add JDK 19 to CI build Signed-off-by: Sean C. Sullivan <github@seansullivan.com> commit f85104040ce44ac545e15e4f41ef771a7a7f7add Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 12 20:19:53 2022 +0100 start work on 2.0.7-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5ff6f2c385c36ea4f8b85cacd69f7ca891c37818 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 12 20:11:11 2022 +0100 prepare for release 2.0.6 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2f4aa754451167e2fef98a07f2e1260cdb08b332 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 10 19:30:48 2022 +0100 fix SLF4J-575 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 363f0a534ea736bb02ced129f3ae27720f95c13f Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 10 00:38:56 2022 +0100 remove unused parts Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 171679baa87e13cfb8ca471242da6fd0d3acbe53 Author: Jonah Graham <jonah@kichwacoders.com> Date: Fri Dec 9 13:42:01 2022 -0500 SLF4J-574: Add full OSGi headers, especially "uses" clauses Fixes: https://jira.qos.ch/browse/SLF4J-574 This uses the BND tool, via org.apache.felix to generate the MANIFEST.MF to be fully compliant with OSGi. Compared to using just the maven-jar-plugin to create the MANIFEST.MF the uses clauses are added to the Export-Package Signed-off-by: Jonah Graham <jonah@kichwacoders.com> commit 921b5b31e179d625d349debf15210ed067a5a153 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 9 13:31:52 2022 +0100 fix FUNDING file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e02244c39f11cdcdb07d6b291f157e3687d5b920 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 9 13:31:16 2022 +0100 fix FUNDING file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 441d4584bed16ec8fe54a9c4acb8d289e51005b8 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 9 13:30:56 2022 +0100 fix FUNDING file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f5e741ba1af6565269499d34c725c32ef8ca467f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 9 13:30:01 2022 +0100 add FUNDING file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2e71327c8ee745927d731e8d9f4e51d331dad138 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Nov 26 20:43:43 2022 +0100 remove unused log4j dependency in the version definition section of pom.xml Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3ff2a30e05e5825d96ddb54da243df48f1a9d897 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 25 13:33:29 2022 +0100 start work on 2.0.6-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7e62e1e6917e19e6eeb8faf97daa9e2469bc946d Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 25 12:40:18 2022 +0100 prepare release 2.0.5 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d250ad79ebbd46f098b07c0868d1cbc8c09c8d6c Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 25 09:56:46 2022 +0100 in jcl-over-slf4j rename LICENSE.TXT as LICENSE, add LICENSE file to log4j-over-slf4j Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3bc58f3e81cfbe5ef9011c5124c0bd13dceee3a9 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Nov 24 20:12:00 2022 +0100 add SecurityManager support Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 207bb299c319886aededb999269c1555abb9deae Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Nov 17 21:38:06 2022 +0100 start work on 2.0.5-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 35dd7ff1e75cf83ffb6784a9537ff92c865e78b2 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Nov 17 21:25:09 2022 +0100 removed unused META-INF/services entry Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 440c2f3000fc0e2d7646f0b3d6e36e8bc2ef2485 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Nov 17 21:04:44 2022 +0100 prepare release 2.0.4 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 43a36303e5a2338c22ec9aad5b01a401034eb553 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Nov 17 20:49:29 2022 +0100 use the class loader that loaded LoggerFactory (instead of the threadContextClassLoader) to find providers Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 557bf7c0bd4e2c2cd85ef389729107461938dd15 Author: Piotr P. Karwasz <piotr.github@karwasz.org> Date: Fri Sep 2 23:01:39 2022 +0200 [SLF4J-548] Fix ServiceLoader usage in servlet environment If both the servlet container and a web application use SLF4J, `ServiceLoader` calls are susceptible to three problems: 1. The SLF4J copy in the webapp detects the common providers by can not instantiate them (they implement a different copy of `SLF4JProviderService`), 2. The SLF4J copy in the common classloader can bind the providers in the webapp classloader and cause a memory leak, 3. If the server uses a SecurityManager the static initialization of `LoggerFactory` fails if called by unprivileged code. This PR should solve these problems. Signed-off-by: Piotr P. Karwasz <piotr.github@karwasz.org> commit 632410565b26e4d67fc7ef2ce4c212380b4e59d1 Author: Stefan Bischof <stbischof@bipolis.org> Date: Fri Oct 28 13:21:26 2022 +0200 enhance manifest with capabilities provide for SLF4JServiceProvider (with name attribute require for registrar Signed-off-by: Stefan Bischof <stbischof@bipolis.org> commit e540299d58bc5f53cab3236cc1b2f29281982074 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 11 21:18:49 2022 +0200 edit blurb on release championing commit dfb41b06a8e5a6aed5e2856edf099fd324822dcf Author: Ceki Gülcü <ceki@qos.ch> Date: Tue Oct 11 21:04:18 2022 +0200 Update README.md commit 47c7cc7fa46d883d46b4000028aab6ef5562a139 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 15:25:09 2022 +0200 clarify Logger.makeLoggingEventBuilder javadoc Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0be1bc15f26f11233ee7f657eb5b50fe552a49f1 Merge: 7cad6082 d60690c0 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 15:24:06 2022 +0200 Merge branch 'master' of github.com:qos-ch/slf4j commit d60690c0b9f0e4c89b71236cee9dc14d967d7778 Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Sep 28 15:23:30 2022 +0200 more flexible way to commit 6720d8db660f5895d1cd08f721e4fe82803fc0c2 Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Sep 28 15:10:51 2022 +0200 Update README.md commit 72a0bc6528a72c514d8fb77f445c0fb3b14eeed6 Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Sep 28 15:04:47 2022 +0200 Update README.md commit f276d52d96fde7f1aad9895e144c166e16d7f368 Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Sep 28 15:04:20 2022 +0200 Update README.md commit 7cad6082dc37dcaab88ead10f37965e6560c9630 Merge: 88b0ee3c 143978ce Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 13:44:04 2022 +0200 Merge branch 'master' of github.com:qos-ch/slf4j commit 143978ce05832d460564cdf857dab7f6672da67a Author: Kengo TODA <skypencil@gmail.com> Date: Fri Sep 9 09:16:39 2022 +0800 annotates new methods to help static analysis tools Signed-off-by: Kengo TODA <skypencil@gmail.com> commit 88b0ee3c1f235facd6d01e5d806f894b919add70 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 13:30:20 2022 +0200 start work on 2.0.4-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b2cb05f16acc21a3266a74ef5c578f2cd9efdead Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 12:15:18 2022 +0200 prepare release 2.0.3 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 4b5bb41ede1cf046e7bfd9dd639d43584020fb41 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 28 12:05:26 2022 +0200 fix SLF4J-546, Fluent logging API doesn't populate timestamp with Reload4JLogger Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b500a6fdfd80772b089cd4069430dd0f6106afb1 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Sep 26 19:58:49 2022 +0200 javadoc explaining using multiple markers instead of nested markers Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d81affb012f37e1d1eb8c2c6fbbb3a4ee15eb3e8 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Sep 26 19:57:31 2022 +0200 comment about ThreadLocal key or value types Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit bcbbe40ffde9b32729198014a771482cf796c5af Author: Ashley Scopes <73482956+ascopes@users.noreply.github.com> Date: Sun Sep 25 14:56:53 2022 +0100 Reword Marker Javadoc to improve grammar. Signed-off-by: Ashley Scopes <73482956+ascopes@users.noreply.github.com> commit 7686020c364bb0567263b14d10752eee6f393fa5 Merge: eb1710af 3f47f87c Author: Ceki Gülcü <ceki@qos.ch> Date: Sun Sep 25 16:02:33 2022 +0200 Merge pull request #310 from ascopes/patch-1 Add missing javadoc to SLF4JServiceProvider.java commit 3f47f87ccce890c6ec8e7e10a882dce9e87db397 Author: Ashley Scopes <73482956+ascopes@users.noreply.github.com> Date: Sun Sep 25 14:49:03 2022 +0100 Add missing javadoc to SLF4JServiceProvider.java Had to do some digging around the logback-classic alpha release for SLF4J2 API integration to work out the nature of this behaviour. This should prevent confusion for developers of other logging implementations in the future. Signed-off-by: Ashley Scopes <73482956+ascopes@users.noreply.github.com> commit eb1710af7bbc4a05efa1078d34ee076e1c591a73 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 21 23:17:52 2022 +0200 start work on 2.0.3-SNAPSHOT, fix SLF4J-564 commit bb49a5aeefc26cd22755951c6088bde670495049 Merge: 0645c18c 768ca7d4 Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Sep 21 23:03:25 2022 +0200 Merge pull request #307 from radio-rogal/slf4j-564-simple-logger-javadoc [SLF4J-564] slf4j-simple: fix javadoc for SimpleLogger commit 768ca7d4c02f475c4ebae2e9f666cd12a6bca45b Author: Witalij Berdinskich <radio_rogal@keemail.me> Date: Wed Sep 21 22:40:56 2022 +0300 [SLF4J-564] slf4j-simple: fix javadoc for SimpleLogger Signed-off-by: Witalij Berdinskich <radio_rogal@keemail.me> commit 0645c18cafbad8dfcebf2d57926cba496c8ab055 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Sep 20 21:36:11 2022 +0200 prepare release 2.0.2 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 894b1890a077a966f8be147e9fac2ad92a610e69 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Sep 20 20:44:05 2022 +0200 fix SLF4J-563 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7c1d86e21e7260093bbef5647cd554e09d64f68b Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 14 16:48:41 2022 +0200 start work on 2.0.2-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 9752442b6e6db0749915dc40e80437dc97cd772d Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 14 16:27:30 2022 +0200 prepare release 2.0.1 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c0f7f16bfb2cdbcf38df6039219ee3f57c99117e Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 14 16:06:16 2022 +0200 minor javadoc change Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 1148b9852997376ab865cfc5e448fee0675cabbd Merge: 593f89f8 03deea9f Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 14 15:39:58 2022 +0200 Merge branch 'master' of github.com:qos-ch/slf4j commit 593f89f85af8d181f0727315224f37fe0aa5fdcb Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 14 15:39:40 2022 +0200 fix SLF4J SLF4J-560 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 03deea9f77c354ccd59c578808cff689299ba5eb Merge: bae56f54 c9d5cc12 Author: Ceki Gülcü <ceki@qos.ch> Date: Mon Aug 29 09:40:18 2022 +0200 Merge pull request #302 from coheigea/coheigea/reload4j_1.2.22 Update reload4j to 1.2.22 commit c9d5cc1257be51d837bf8e3f10f94eb18d1390bb Author: Colm O hEigeartaigh <coheigea@apache.org> Date: Mon Aug 29 08:02:12 2022 +0100 Update reload4j to 1.2.22 commit bae56f544b0c30cedb265729f3c6cce72fa79f10 Merge: 05c0b0a8 24788ac7 Author: Ceki Gülcü <ceki@qos.ch> Date: Thu Aug 25 21:35:07 2022 +0200 Merge pull request #294 from marcwrobel/fix-typos fix typos in documentations commit 24788ac731cdce9f27670f22efd42a7b9f1d771e Author: Marc Wrobel <marc.wrobel@gmail.com> Date: Mon Jul 18 15:51:13 2022 +0200 fix typos in documentations Fix typos in javadoc, comments and README. Signed-off-by: Marc Wrobel <marc.wrobel@gmail.com> commit 05c0b0a88165094a9044e981c7836e10a05c8f6c Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 23 22:42:13 2022 +0200 fix SLF4J-555 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 400a885e7d74c291b728f983a38697553d4e0431 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 22 17:50:40 2022 +0200 remove reference to 1.7 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit a4f165689fb607ed2c6924b2cdbd1e49a95b59e8 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 22 16:36:38 2022 +0200 use https links Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 4685f1ebc04c872b77b8e08b8b4463444826b3ac Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 22 15:01:50 2022 +0200 add reminder in release.sh Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 15d4c1fdd6292c2598b45f172a7e767c89997963 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 22 15:01:17 2022 +0200 fix path to codes.html Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 42f863863fd11c84c65eb11f35cc7025c387e056 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 20 21:56:31 2022 +0200 upodate gpg key information Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 51ceaf6224a96c6c03c8822e9352b1a4a3b10036 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 20 21:31:19 2022 +0200 start work on 2.0.1-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0614d467d7bca81724f45e228f4f871161222b51 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 20 21:04:05 2022 +0200 prepare release 2.0.0 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b1afcd01b1092f0dfda12b4502aa202124e24a8e Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 7 00:04:53 2022 +0200 javadoc edits Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 20cd3ad0abd25d1837f5b9354c6729cb4a978d69 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 7 00:04:28 2022 +0200 start work on 2.0.0-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit aeebb6199d412a3883af2d0c414a69fde26b5971 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 6 23:31:54 2022 +0200 prepare release 2.0.0-beta1 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 1068cd0eb9fb2460d368e3ba6112517ef3fedd2a Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 6 23:25:49 2022 +0200 javadoc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 4e4e56a2df730cdb6877449b6341279208f20a78 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 6 22:44:44 2022 +0200 add CheckReturnValue annotation in org.slf4j.helpers Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0dcfa19040fb2d7f45dfe00823d15bdff0434d6a Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 6 22:03:35 2022 +0200 check for return value in some oggingEventBuilder methods Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e7ca8d17c8db1fc956019404153cc7b90b8f0c61 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 6 21:26:09 2022 +0200 start work on 2.0.0-beta1-SNAPSHOPT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2314de9dd9f9abbef360f5c6240487c0ac7e5fc3 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 5 22:46:46 2022 +0200 add setMessage and log method to the fluent API Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 508a796552640c83d6d814374a9b50a424e88cfa Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 5 22:00:48 2022 +0200 set version to 2.0.0-beta0 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d93a5e0456f83b83e2336f47d12e2493fd67510f Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 21 12:46:38 2022 +0200 minor javadoc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 43005d1d858fb408e93401ff3f37fff16948b26e Merge: c0001d46 14ec6709 Author: Ceki Gülcü <ceki@qos.ch> Date: Thu Jul 21 12:42:02 2022 +0200 Merge pull request #293 from varunsh-coder/token-perms ci: add GitHub token permissions for workflow commit 14ec670971edc669caa20e4e925202a388e8d997 Author: Varun Sharma <varunsh@stepsecurity.io> Date: Sun Jul 10 07:17:58 2022 -0700 ci: add GitHub token permissions for workflow Signed-off-by: Varun Sharma <varunsh@stepsecurity.io> commit c0001d461946ca4b147a24e66b8e9e1582b5d56a Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 15 20:31:10 2022 +0200 remove slf4j-site Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 9feda2c795fda0aeb546b0f58321c5808cf7bb55 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 15 20:30:49 2022 +0200 remove slf4j-site Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 287fe4f97a8a4b15380dcf61e6d54da1c803a0c1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 14 17:01:39 2022 +0200 add closing double quote Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5537ff1699373d8ea99a462924ea456c0941bf64 Merge: ae032b12 996866fa Author: Ceki Gülcü <ceki@qos.ch> Date: Wed Jun 8 15:38:16 2022 +0200 Merge pull request #290 from ckbisk/patch-1 SLF4J-551: fix broken org/org Log4j link in left.js commit 996866fae764bca198f95cdb1e0ec5b47bb26042 Author: Chad K Bisk <ckbisk@gmail.com> Date: Tue Jun 7 23:30:06 2022 -0400 fix broken org/org Log4j link in left.js https://jira.qos.ch/browse/SLF4J-551 commit ae032b12970b0d17b9c5e97c8657619a37e36be3 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri May 27 17:50:14 2022 +0200 remove infra information Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6afe5ab7a72ec73e34ec100e89ff6a04f94365cb Author: Ceki Gulcu <ceki@qos.ch> Date: Fri May 27 17:34:30 2022 +0200 gpg password on a dedicated panel Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 82a592ed790cc8072aef1455f1065b6c9d207501 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue May 17 18:49:07 2022 +0200 info about keystore Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e454d28282e5db980d5be7afb3a5894b9ac9b35c Author: Ceki Gulcu <ceki@qos.ch> Date: Wed May 11 12:02:06 2022 +0200 deny history overwrite Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit db3835d39274d17b7deb45b36442eced8bc5b01d Author: Ceki Gulcu <ceki@qos.ch> Date: Wed May 11 11:49:52 2022 +0200 add SECURITY.md Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 61574d22f4f12e96e29b07845a65f0508e385d58 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed May 11 10:47:13 2022 +0200 discussion header Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 9dd3de0511930c9dffdc60268d70c61a23a5400f Author: Ceki Gulcu <ceki@qos.ch> Date: Thu May 5 20:36:48 2022 +0200 fix name of variable Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6701960a59904e4635c04089ebd4c73839739e9e Merge: ac854c79 98728180 Author: Ceki Gülcü <ceki@qos.ch> Date: Thu May 5 19:43:00 2022 +0200 Merge pull request #287 from srt4/bugfix/SLF4J-549-update-event-recoding-logger-name Update EventRecodingLogger name to EventRecordingLogger (SLF4J-549) commit 98728180ac9dd889380086d6963e16770b46cff0 Author: Spencer Thomas <srt4@uw.edu> Date: Thu May 5 10:20:39 2022 -0700 Update EventRecodingLogger name to EventRecordingLogger (SLF4J-549) Signed-off-by: Spencer Thomas <srt4@uw.edu> commit ac854c79ea58a59679a3c58c140957a38f5efad1 Merge: 2b0e1587 0c0eb127 Author: Ceki Gülcü <ceki@qos.ch> Date: Thu Apr 14 18:42:02 2022 +0200 Merge pull request #282 from tenghuanhe/patch-2 Fix minor typos in README.md commit 0c0eb1275d4dadbfa88b66f4caa2e3f24495bb63 Author: Tenghuan He <tenghuanhe@gmail.com> Date: Fri Apr 15 00:15:17 2022 +0800 Fix minor typos in README.md Signed-off-by: tenghuanhe <tenghuanhe@gmail.com> commit 2b0e15874aaf5502c9d6e36b0b81fc6bc14a8531 Merge: 045f502f d8b223e3 Author: Ceki Gülcü <ceki@qos.ch> Date: Tue Apr 5 20:10:11 2022 +0200 Merge pull request #249 from gnp/master Fix typo: "apllications" --> "applications" commit 045f502fa915bf1749deddabcd534f74c9dfd1af Merge: 23182d44 a188a3ed Author: Ceki Gülcü <ceki@qos.ch> Date: Sat Apr 2 21:56:18 2022 +0200 Merge pull request #281 from josephw/typo-in-reload4j-logger-adapter-variable-name Fix typo abbreviation for fully-qualified class name. commit a188a3ed734e3d551d0404854e7795d74534c0a6 Author: Joseph Walton <joe@kafsemo.org> Date: Fri Apr 1 22:01:20 2022 +1100 Fix typo abbreviation for fully-qualified class name. Signed-off-by: Joseph Walton <joe@kafsemo.org> commit 23182d44680e2cab0869fd8db4b53ceeb2f807eb Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 30 20:36:13 2022 +0200 delete unused import Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit aa0de34dc6d99af14fdd6a46666dd6977004e133 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 17 20:45:02 2022 +0100 start work on 2.0.0-alpha8 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5c4fe1d48c434b8a1f79d63c342864aa66e934ba Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 17 20:40:33 2022 +0100 minor edits Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 90f3f1ea0770e2b0d7fa5587ecacc34e02f6b335 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 17 20:34:10 2022 +0100 update news about release 2.0.0-alpha7 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5fcbb283a323e2c5be9653b399475b6f582907ee Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 17 18:38:36 2022 +0100 slf4j-log4j12 relocated, prepare release 2.0.0-alpha7 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 956acb06d62ac33f975f312819b929bcdfbc70fa Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 17 17:03:38 2022 +0100 add info about version99.qos.ch going away at the end of the year Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6df6053c24fe0920a594fd0e63738181756d4432 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 9 23:08:54 2022 +0100 caller data extraction support - SLF4J-511 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 74ccf20fab1a35243ae41c2f56f2167e86afbd0c Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 28 21:23:39 2022 +0100 typo fixes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8806a45ede9504903cf871c3d25e07c916f54f62 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 18 11:22:44 2022 +0100 doc edits Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2287768293c3f34e51a0f5c066e6540549569c09 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 8 14:39:04 2022 +0100 fix SLF4J-541 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit bef80280e6b973f6abaf45749ccd0259834ba8f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 26 20:50:23 2022 +0100 add sponsorship request to header Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c1282ba08c3b4fc7f4fb9973fdafcd6956e27040 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 25 15:39:50 2022 +0100 update stable versions Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 81a0568d680a97e11cc9a767b7ea6ae1182f7526 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 25 15:38:35 2022 +0100 update docs Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f04cf16b6664304f7e8e1a7a2b1a309a6e82e100 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 24 00:07:40 2022 +0100 fix comments, less bragging Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c69570fc511680331c4a764e4a9a8f28c19a00f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 23:37:27 2022 +0100 mvn install seems to work better Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 85541d5669ad0e8849c189961a9d0c1b3878f340 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 23:33:05 2022 +0100 try maven package Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 483538176765283c91bcdad7959711f552f1af8d Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 23:23:13 2022 +0100 try maven install Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c9c5492ded2caf7ceab0f395df032bfb818382a5 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 22:21:52 2022 +0100 add test in relation with LOGBACK-1612 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 510cc99e3713d878db3ce37c44315707332a9146 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 22:20:13 2022 +0100 try using JDK 11 and 17 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit a20a22299da69f4888fb82d0cfa41d15a909ed8e Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 22:17:23 2022 +0100 github actions Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2d6b6344f03785f00d1df14026474e5fb28bcf99 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 22:16:29 2022 +0100 doc edit Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 16ab482cab7e8fdc6468ce7da425f10660bf4057 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jan 17 22:11:33 2022 +0100 added paragraph on JEP264, doc changes, minor refactoring Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 39a07b9ce452cd615d5454a04a852660ec6d9f69 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jan 14 16:42:33 2022 +0100 make VersionUtil more robust Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 10bd70ca75de5066008738bd10a270655acf263e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 17:01:39 2022 +0100 start work on 2.0.0-alpha7-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 66e9c2555fc0b0cac18ac5820cc438429515ac2c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 16:56:49 2022 +0100 prepare release 2.0.0-alpa6 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 28528094b94038fcd24cdc7fc4accf2190229de6 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 16:27:04 2022 +0100 mentioned reload4j in the docs Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6abaf6897bb3044ab57838404d7422ab7c7aced9 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 16:26:36 2022 +0100 rename slf4j-reload4j classes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 39cf0fc837134ec0942ef2f2c8befa49bf067f67 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 16:25:23 2022 +0100 fix SimpleLogger javadoc comment Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0e04efdbf6c6a67245ef3fe34328330473a07bf5 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 15:21:26 2022 +0100 add slf4j-reload4j module Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0d4167abe7e5bfe164eb37d9defd51bf739d6b8c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 13 15:19:10 2022 +0100 fix SLF4J-499 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 60e70fbc83aebd2dc41c6b30386dce27445e9220 Author: ceki <ceki@hope> Date: Thu Jan 13 11:55:50 2022 +0100 Fix SLF4J-499 - log thread id in SimpleLogger commit 9e4a358634ca9f01a4e84f88b463680ec85c130a Merge: f6076c14 34547b2f Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 12 22:43:15 2022 +0100 Merge branch 'master' of github.com:qos-ch/slf4j commit f6076c140980109c020e69500ded1b6fcb71b927 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 12 22:42:52 2022 +0100 mention reload4j in log4Shell.html Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 34547b2f325def790f166d06adab87c7ae06a8f9 Merge: f09e33dd ea47492d Author: Ceki Gülcü <ceki@qos.ch> Date: Mon Jan 10 11:07:33 2022 +0100 Merge pull request #276 from japzio/japzio-patch-doc-typo minor typo fix commit ea47492d7a3107e3268cf857656eee82c37b6326 Author: Jasper C <japzio@users.noreply.github.com> Date: Mon Jan 10 16:00:59 2022 +0800 typo Signed-off-by: Jasper C <jculongit10@gmail.com> commit f09e33dd15f60b4480d9a60bfb9083ef739fea2f Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 5 22:10:34 2022 +0100 add support for keyed deques in MDC Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 12b5a6b6760709a19dc7806f9e14076ecf8e9dd9 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 5 22:09:59 2022 +0100 mvn compile in slf4j-site should copy images Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 23c8cc0121927ec7f111276b0dc7e198b6ef9769 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 5 22:09:05 2022 +0100 fix SubstitutableLoggerTest Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0877cb64102a9bccf6c4881d20056d56371961a8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 4 18:32:23 2022 +0100 add github sponsors link Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7144b50915ff3c7f9bec4af102973437d1210080 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 4 15:03:13 2022 +0100 add FUNDING.yml file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0e8713e1eb770ee8e9a65ad632e48450f9daa67d Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 2 23:30:41 2022 +0100 minor doc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 62a265d3c5a2bde82f2e025ee10f115564d951bb Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 2 23:26:23 2022 +0100 add keyedStack interface to MDC - SLF4J-531 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 59100d75e1e24af49e464928856fafb2bed0fccd Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 24 11:39:21 2021 +0100 add atLevel method to SubstituteLogger Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b655c0a2b7351dfc695d51e14a2e41f65a2e1620 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 24 11:38:28 2021 +0100 site updates Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6208cbbded554fa04051773b4db4f3bb69805423 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 24 11:37:18 2021 +0100 site updates Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7c62cf825468c4b9fd38a9a7814cc35b8cc210cb Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 16 18:25:14 2021 +0100 added atLevel method to Logger Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c61f01783a5dd65bed594db953c72250b49992f5 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 16 00:56:42 2021 +0100 added at() as an alias for makeLoggingEventBuilder() Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit ce15e71dd890061915f36277df2716e626f9ea70 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Dec 15 08:51:26 2021 +0100 less drama commit c6ea154309aa4220c62e678723cd8a4f384b600b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 14 17:51:11 2021 +0100 doc fixes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2a9bcb15e0397bf5856ea3d4eb7fe72fe7d75356 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 14 17:17:33 2021 +0100 doc fixes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 53a9833a3cdac18aed9dab7a0e6894fa1c77edfb Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 13 20:16:44 2021 +0100 read only access Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 71d5c081e8a386431bf5ad517153a99cd7c8b90e Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 13 14:23:45 2021 +0100 typo fixes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 81d57c271b25bcf24e8c3970fe49941477476540 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 13 14:06:04 2021 +0100 doc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 65524de79af27b4d73e130873c4feab88530be3c Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 13 13:49:59 2021 +0100 AS IS with no warranty Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 45fbb1ebc86ebee42cbb1634801168d198947259 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Dec 13 01:00:02 2021 +0100 css improvements Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7a68675fc6669473eac1a26ba15c0b93f18dabc5 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Dec 12 00:39:53 2021 +0100 updates to log4shell comments Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 25ddfaaab055a5ac813e77123590deca1329d6f3 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 11 17:20:02 2021 +0100 comments on CVE-2021-44228 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 98f1f2f46533eba4945dda995225cf3c4017a075 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Sep 27 23:23:14 2021 +0200 fix typo in version name Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit cf09b2e34de6216c9aa5b8ba5e7e5db3d5a4da27 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Sep 8 17:28:33 2021 +0200 Class.getPackageName is new to JDK 9 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 1cea7b72e34854ca142cd08bc89f9f322b0c2290 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 5 13:20:05 2021 +0200 removed link to instructions for contributors Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 50a68fe8cc3680d1bc8281dccaa0ae72881539d2 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Sep 3 20:24:42 2021 +0200 tinkering with right.js Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6f0c54caa4b339f285bf5e70d00741bc89c6ed4b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Sep 3 19:34:45 2021 +0200 add jquery to pages Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 590434e55fb1dbca0ed5fd34d635344d4e7b40b0 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 21:38:21 2021 +0200 start work on 2.0.0-alpha6-SNAPSNOT commit 545755c2b7ef55ab3ce8a98b8448e003fe7556cb Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 21:36:34 2021 +0200 bump junit version, remove unused repo reference commit 0a34a87495b39f0d70204ee0d07129e9c22dfb98 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 18:02:34 2021 +0200 preparing release of 2.0.0-alpha5 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 252593b9340f51d9548fced3a13d303eca9c3f34 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 18:01:02 2021 +0200 news update in relation with 2.0.0-alpha5 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 43bcc961a28dda90140d3cdae5324dfddf46cec9 Merge: 1d4535ad f8bb0da4 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 17:05:50 2021 +0200 Merge pull request #266 from dfa1/master minor code cleanups commit f8bb0da47b6a4dadfef7c79a8202bee6c4e99f4f Merge: 6e784e4c 1d4535ad Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 17:05:18 2021 +0200 Merge branch 'master' into master commit 1d4535ad23dc8809a42fd91dc655774657d8a7f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 16:58:30 2021 +0200 rename SLF4JPlarformLogger as SLF4JPlatformLogger Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit baadb616813a690caed1bdc6fc576281d69990e9 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 15:11:36 2021 +0200 attempting to check for incorrect info META-INF/services/ Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 41b612d1504f74bfc01949c6a4dc681e67698df7 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 30 14:46:06 2021 +0200 updates to faq Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6e784e4ca3a5ae9c5dc421fcd01a417af5bf5ace Author: Davide Angelocola <davide.angelocola@gmail.com> Date: Sun Aug 29 12:12:34 2021 +0200 minor code cleanups - more private final fields - avoiding C-style array declarations - few typos, notably JPlarformLogger -> JPlatformLogger Signed-off-by: Davide Angelocola <davide.angelocola@gmail.com> commit b977791f50483a4a7072c6e208bb1f95d3688471 Merge: d0836be0 4672a6fd Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 29 15:04:55 2021 +0200 Merge pull request #265 from nipafx/patch-1 Fix platform logging service registration commit 4672a6fd52eeb0f8c5ee4ed356408235db661d15 Author: Nicolai Parlog <nicolai@nipafx.dev> Date: Sun Aug 29 11:23:57 2021 +0200 Fix platform logging service registration Related to #232 and SLF4J-442[1]. [1]: https://jira.qos.ch/browse/SLF4J-442 commit d0836be06f72363a975d6d719b53e577b0701021 Merge: 9bc01523 c7d79d86 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 27 01:16:43 2021 +0200 Merge pull request #264 from dfa1/master upgrading code to Java 8 commit c7d79d86a935de93a9f5b20c4e2547bc495b524a Author: Davide Angelocola <davide.angelocola@gmail.com> Date: Wed Aug 25 19:45:19 2021 +0200 upgrading code to Java 8 - for each - diamond operator - some typos Signed-off-by: Davide Angelocola <davide.angelocola@gmail.com> commit 9bc01523710a0706e6eff1083824642ab2fec00f Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 16 16:13:05 2021 +0200 doc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 21af69f3eb5ba657ac8f1437cc7e7870cabcafe1 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 16 16:12:45 2021 +0200 add travis build cache Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 55357d2270715933101cb30f78d612ccc8f630ea Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 15 10:09:12 2021 +0200 doc changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 66aed4dfb1578e1a7b93f06329fbdacd24041622 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 13 14:41:53 2021 +0200 javadoc fix Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit ccbd8f8c96dce39235ded6952ba92ad66d5b1211 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Aug 12 23:47:02 2021 +0200 start work on 2.0.0-alpha5-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7836be3be57840bf76b8e9bf44f592a48674c631 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Aug 12 23:20:04 2021 +0200 minor last minute fixes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c2e02170bb8943164fcedfab3071008b224af579 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Aug 12 22:33:11 2021 +0200 preparing 2.0.0-alpha4 release Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e240abe9b10c0a8aa088103208ec183b6cbf7170 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Aug 12 22:28:39 2021 +0200 testing caller info extraction with slf4j-jpl Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit eaa9fae39d6d33521e8232c3f4f439d7db3c3532 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Aug 12 13:05:04 2021 +0200 ongoing work on the slf4j-jdk-platform-logging commit a42ad1f4f7b19b75b7d5f7b121cdf21f86837e2b Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Aug 11 17:09:18 2021 +0200 ongoing work on the slf4j-jdk-platform-logging module Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e0448ad699d0e5cb72f9c28ab8e5c46fb531ad1f Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Aug 11 13:49:45 2021 +0200 minor tweaks transparent to users Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit cc8e690ee8ac99e57b549460e03ec2d16e5a239d Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 23:03:23 2021 +0200 initial version of PlatformLoggingTest Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 4083b3dd0fc5edb1f396b5f0f1f0f44c8613ecc6 Merge: 1754a892 877817a5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 19:56:16 2021 +0200 Merge branch 'master' of github.com:qos-ch/slf4j In relation with PR 232 commit 1754a89208227cb9df5066f1cb24c75616a513cb Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 16:09:37 2021 +0200 start work on 2.0.0-alpha4-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit d6c2ddbe89503c0c077c7c916e8e34b588fdefa4 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:55:43 2021 +0200 latest stable is 1.7.32 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 551283ba4c0e3e1e4938139d3254be0c88712250 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:53:40 2021 +0200 prepare release 2.0.0-alpha3 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c0bacabab2d80cb626c38f7aff835215fb7f8fd5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:53:16 2021 +0200 updated build-helper plugin version, removed lifecycle plugin Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2d3e9f7d2bf10ae3dbb6b29fdf9113ba36b7f54e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:41:51 2021 +0200 release 2.0.0-alpha3 notes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit e6d5d12c035f77211f07c276a7e2b663fa626d08 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 14:37:32 2021 +0200 add toString method in KeyValuePair Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5958599ca9ee09e006465f27b523c1039b2a4fb2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 14:36:40 2021 +0200 make fields protected in DefaultLoggingEventBuilder Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 66dda1a323e96f8a3b10ac7a5a84b4fc06b46c44 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 9 17:47:44 2021 +0200 in DefaultLoggingEventBuilder renamde innerLog to log Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 280129046e53fd60e6743a57f04bbcfc91cbf3ce Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 9 15:11:43 2021 +0200 very minor changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit cf4d011ac03b7c80c17af6768af89d94c8604d69 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 1 21:34:11 2021 +0200 simplify compilation directives Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8d5df5a41c3572f92b01f34429644bc6d7c0f235 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jul 31 22:27:04 2021 +0200 move test to test packages Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit fc66b1fc68c040fbfae5bdbdf081d5d6271fcb1e Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jul 31 22:26:35 2021 +0200 correct path for NOPServiceProvider Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 316e59084d87e36698376094aad58002d7f4f636 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 11 07:08:08 2021 +0200 rename org/slf4j/helpers/NOPServiceProvider as NOP_FallbackServiceProvider Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 7483a11dd6ba1398f4b51c2e673800325cc609fc Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 11 07:00:09 2021 +0200 fix SLF4J-516 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 47e751d63c7197ef6d7b257bf88b3faa3f6f473d Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 22:56:53 2021 +0200 make CONFIG_PARAMS aa final field Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit fb1929011f2c214daa8aae1ccfb05ec7b081ad40 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 10:16:01 2021 +0200 version should have a SNAPSHOT suffix at this stage Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5b3e70a3539fc6380f258d752dd8096ca8d8f2ba Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 10:12:49 2021 +0200 align with changes in the 1.7 branch Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 19d037f11a5ebe26eba08663e139b41fa2b2d412 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 23:28:38 2021 +0200 blurb about SLF4J-515 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 75f6c0b2f98f161b3b8db26f110e97c576cb3aad Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 23:24:30 2021 +0200 fixing SLF4J-515 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5a0eba57e55c327770a087ef73e33502bfe3628b Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 19:55:53 2021 +0200 allow unit tests to run in a new thread Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3321b220b8b4271b868e802a4dfcf54224c64a42 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 15:55:03 2021 +0200 add info for verifying signed artifacts Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b682787a2ef93ff1b0c9238b57cab8cbeed145da Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 17:03:34 2021 +0200 start work on 2.0.0-alpha3 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 252fbffede5836a6cbf31d2762ea6b96351e3e3c Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:52:58 2021 +0200 allow slf4j-site to build Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8601beed763dc0ed4128608085f508db47c3c518 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:43:17 2021 +0200 prepare release 2.0.0-alpha2 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8571f5d7f2ff32e1717d4f54d1fba64ad47f548a Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:23:48 2021 +0200 removing unused file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 62d6497f6ab82b450d24f13d95bd6e7363a5ab1f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:23:17 2021 +0200 fix unit tests Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit b5446d67bb2d0b63ac715e9ac5ee6ff9aebe32e9 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 14:08:37 2021 +0200 blurb on DCO Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8f602c309a7e8c4735eb145ca30cdd8f32bb65f6 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 13:25:41 2021 +0200 testing sign-off hook Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 04f3d418d1345e732f53cfd91a0169720e1a12dd Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 13:24:48 2021 +0200 testing sign-off hook commit 8859a8a01916e62ecd7fc96a3bdb36530839a421 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 00:21:14 2021 +0200 edits Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 0ae15e3981750beb277831bf3803fc4110ea2a05 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 00:19:53 2021 +0200 document DCO requirement commit c233c86457273d63a32d3091d6887ad0ccba709e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 23:26:31 2021 +0200 typo fixes and minor edits commit e74699276bf3a38a13ff3ffefc06d8f0bf39280e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 22:37:39 2021 +0200 Fix SLF4J-414 commit 65eacb35a8bae1651f25e59ce34044d213c231f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 21:32:31 2021 +0200 Fix SLF4J-421 and SLF4J-287 commit 3e0016d8d148f8884417c3e560cfe07a17fdb1ec Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 11:02:24 2021 +0200 add JMPS module names in FAQ (fixes SLF4J-465), other edits commit 601405b76f7b816d9558ddc8a8121c482eb00cb3 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 10:03:25 2021 +0200 fix bugs detected by SubstituteLoggerTest commit 10d78b04d655a39923bfc11d433fd62296ec3677 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 23:13:52 2021 +0200 fix SLF4J-435 commit 7547d1c871d7d47f631d6354ba3ca3e009528651 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:40:14 2021 +0200 add isEnabledForLevel method in Logger commit 45b177c2d23b2d8b4d40de3c0ff352653024c325 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:39:30 2021 +0200 make NOPLoggingEventBuilder constructor private and allow access via the singleton commit 730ee35665717604ba0c895e3e22e8fea11e7667 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:05:53 2021 +0200 removed unused NOPLogger, NOPLoggerFactory and NOPMDCAdapter from slf4j-nop module, these were moved to slf4j-a4j-ap-api module commit 3afcb8e8c40ed870637459b4ed1d22708dc22195 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 20:11:52 2021 +0200 formatting changes only. applied slf4j/codeStyle.xml in Eclipse commit 8a83b1bd344c90d8b4547dd730b939d40a47a3ef Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 17:25:21 2021 +0200 cleaning up deprecated usage commit 4cd41f799d23901c9aaf6fc3c23adf69ba31aa76 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:33:27 2021 +0200 upgade plugin versions, clean up commit 9558b2103e6e9b44d129bb965c4b98ccf48bc38b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:29:49 2021 +0200 the second -jar- goal is redundant commit a1683d93230c6d1ec2e579a5620d41cf99a8ee4f Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 18:52:57 2021 +0200 formatting changes only commit da6b46d8d7f6d4f108432d193aa6eac56e20d415 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 10:27:56 2021 +0200 stable version is 1.7.31 commit 092d527971365645ddb95a1b8f13966e94c43ee9 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 10:25:15 2021 +0200 keep highlighted info for 2.0.0-alpha0 commit 153a6cabda08a400ab9f292f499cbe5d595b519b Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 23:09:44 2021 +0200 minimal version is 8 commit 494bd9aee905c044cabd2be2d673d9caeed318c7 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 17:02:03 2021 +0200 minor doc changes commit 160061185084dae0329ffef22d8cef5b5f0c0136 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 10:52:38 2021 +0200 fix SLF4J-514 commit b56a878bc209718a90c88a512d75a12559a97a6a Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 10:49:03 2021 +0200 fix SLF4J-514 commit 865c88e340bf7ea46d08cfb257051a077f97ebe5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:08:55 2021 +0200 slightly higher tolerance commit 91eb61c3c97c2e2090037493bba7ada0219dc3ad Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:48:11 2021 +0200 news blurb about SLF4J-497 commit 63ac275a5f6aff03e0cbb7a7ff71dcbd10fb2ebc Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:29:08 2021 +0200 unused imports commit ccce832b8f3c01be68f36c2805adc64572dca1cf Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:28:32 2021 +0200 fix SLF4J-485, LoggingEventBuilder addArgument() should take Supplier<?>, not Supplier<Object> commit b38727956dea48993591ff38ec84b7940986e35e Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:23:37 2021 +0200 formatting changes only commit 0b1d536e04eecb4bc399089dc7033cf99be56d10 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:17:16 2021 +0200 formatting changes only commit 6359e55d52226387784eb12db2c846b8fc893cbd Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:14:39 2021 +0200 formatting changes only commit 4c1b6832f6a8f6d3a6b6f30897ab532f6123c3ff Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:02:24 2021 +0200 formatting and minor cleanup commit a9d4187fad1da6aa40a79c7b36dfb59e4a91cd6e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:59:31 2021 +0200 news update commit 03c37619d5df72cea11652d1017dcb5ceb98d4d1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:51:03 2021 +0200 fix SLF4J-511 commit 6a09a76bb6930ceb7fd436169e15140fb9b393f3 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:03:21 2021 +0200 rename private method commit 4a11208ae405644102102958fb8b8a78f0e39f31 Author: Antonio Tomac <Antonio.Tomac@infobip.com> Date: Thu Aug 6 16:15:33 2020 +0200 Avoid potentially "expensive" rendering of message Object to String when log level is disabled SLF4J-497 commit 65009d8e62c74aa5b1a394ed27747882bd876ef3 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jun 14 15:55:02 2021 +0200 minor doc fix commit 2f1ccdddae867049364de574aecd488c472c095a Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jun 14 15:53:45 2021 +0200 fix SLF4J-511 for j.u.l commit a739d541a55a480c50491e6fabdaee3b93727fa3 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 24 10:28:51 2020 +0100 minor edit commit 76cc29cb47596eba4c64bb9325b625da2f175e1c Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 19 08:48:56 2020 +0100 update link to Maven central commit 230573ab101feee4bbdfdd6c2134db32b8eaacb0 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 20 16:27:47 2019 +0100 news about 1.7.30 commit b0e3ad34f430bdeea9e9509647ab1d8a4c8442d0 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 10 09:17:29 2019 +0100 minor refactoring, docs commit a0319ce7259862dc85e9ff91dbc47b3d5d2e700b Author: David Harsha <davishmcclurg@gmail.com> Date: Mon Dec 9 20:16:33 2019 -0800 Fix NOP fallback memory leak Substitute loggers are not getting "fixed" when no SLF4J provider is found, which means `SUBST_PROVIDER` will add messages to its `LinkedBlockingQueue` until the process runs out of memory. `NoBindingMultithreadedInitializationTest` doesn't contain any assertions of its own because `MultithreadedInitializationTest` already asserts loggers are fixed in `assertAllSubstLoggersAreFixed`. https://jira.qos.ch/browse/SLF4J-469 commit 78b1f19a6400723462b4eba7c0fbe4394d324bf7 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Nov 4 19:15:33 2019 +0100 latest stable is 1.7.29 commit 2d3c03622eac8b6d806203ae8eaf2732c3e2e68e Author: Björn Kautler <Bjoern@Kautler.net> Date: Fri May 18 15:38:40 2018 +0200 Make slf4j with java.util.ServiceLoader properly work in OSGi by using the Service Loader Mediator Specification commit 6719babbce4fdb9c1c587f45d2129a55fd74caaa Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Oct 16 20:32:17 2019 +0200 minor edit commit 17528421bf0d6929f69285ea3244b7ef2021e9bd Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Oct 16 20:27:50 2019 +0200 fix SLF4J-475 commit 6ec50c7b474fe0c93667eb738280cdb537ff4fcf Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:10:39 2019 +0200 minor javadoc edits commit ce640dbce2294dc3640154a2adf3485529af1446 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:10:13 2019 +0200 skip assembly commit fbadf47724efca2062d61719dedb0016a1224523 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:04:37 2019 +0200 updated redirect.html commit d779d080e4b5b1c75ba044757da75efbd4dc1655 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:04:00 2019 +0200 don't put on Maven Central commit ec75e2b0f330fa5a01cc83cdefe823a65765c178 Author: Hervé Boutemy <hboutemy@apache.org> Date: Sun Oct 13 17:28:33 2019 +0200 this module is Apache 2.0 licensed commit d03c5fe0165ca4e978cf9092af5efa7b25b3ddda Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 11 12:37:41 2019 +0200 add redirect.html to src control commit 9213667ba21185c4887524d8f1bca6aa8731094a Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 11 12:33:53 2019 +0200 remove link to tar.gz or zip distributions commit 8ee427d6bb1df41af837417e1cc55edec5687286 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 4 20:28:51 2019 +0200 document release info for 2.0-alpha1 commit ed1ffb325a37025ac7ee6d38a0226c63e4f4fea6 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 21:25:16 2019 +0200 start work on 2.0.0-alpha2-SNAPSHOT commit fdf496daf224ac13654be19d42200d74ec1cf396 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 21:22:21 2019 +0200 version 2.0.0-alpha1 commit 7fbe973ad90ed309711bd278b42639340ecf6ebb Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 20:06:40 2019 +0200 have slf4j log markers and key-value pairs by default commit 13736433b1dff7dc1bff0d40b2aca4f15764b856 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 17:53:15 2019 +0200 makeLoggingEventBuilder made public commit c81f6cfdbdbf9433dd253b58446fbecafa314a04 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 17:04:27 2019 +0200 cosmetic changes commit 72023025374756858c9187a4d11176ac41624ce6 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 16:53:00 2019 +0200 fix test commit 6eaeb0f6af0cd18c54b4ebb8cad1756327d45dd4 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 15:42:29 2019 +0200 'fix build, other changes commit a9f84d58b3c3ede5970d3d47f56c295700bcb53d Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Sep 7 10:57:35 2019 +0200 API consolidation commit c1c8d21bc41133d13a543736be11977259928678 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 19 22:01:52 2019 +0200 minor edits commit 854d6fbf790034a9ffea548396ce99da70c93695 Author: Sebastian Schuberth <sschuberth@gmail.com> Date: Mon Jun 19 22:07:53 2017 +0200 Fix the SCM connection URL in pom.xml The "connection" should be an URL valid for read-only access and has to follow the syntax as described at https://maven.apache.org/pom.html#SCM. commit a35c1d331d8989daca7ee9388f4495f5d492cd4a Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Wed Aug 14 00:00:29 2019 +0200 Fix the build and a typo commit ea8da7feddc269d3419ce98102526346a58177cc Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 13 17:30:17 2019 +0200 refactored EventRecodingLogger and EventRecodingLoggerTest commit 7e6e3d1f24c3a6a0b49d2f7a4319db65689e790b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 13 15:38:32 2019 +0200 move methods from Util back to MessageFormatter commit 176e067fb956f0ccf3e72191b2979009ad615d8e Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 17:40:47 2019 +0200 SLF4j-466: if was missing a space commit 1238dbcb0bd549cc456139c9eb3c53652c4a8ede Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:49:37 2019 +0200 SLF4j-466: fixed typo in javadoc commit 1df318d08afee38f6d00196c1b327e4547f1e6ad Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:42:41 2019 +0200 SLF4j-466: added missing newline at end of file commit 315a95824b5646198727614ac8cf7863016cef4c Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:40:13 2019 +0200 SLF4j-466: only call arraycopy if we have elements to copy commit 21c1be85ab93b5207268667c599e22b63d4d61db Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:01:42 2019 +0200 SLF4j-466: put the throwable at the right place of the SubstituteLoggingEvent, introduced two more recordEvent methods for the two object argument log statements commit 7af8f7e2f4f986af98131bdbc62db55898fa2ad3 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:59:14 2019 +0200 SLF4j-466: Move two methods from MessageFormatter to Util so they can be used by the EventRecordingLogger as well commit 50eec4afd63a5e095a73f771d264e195e124a13a Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:58:02 2019 +0200 SLF4j-466: add missing marker in one of the warn methods commit 1cd31dc9bb226e21b199b00d580ee7a2ef0e48eb Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:56:52 2019 +0200 SLF4j-466: Add test for all happy flow cases commit 3a06ff0b19380f7c3b70a91c019149023964949c Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 17:46:11 2019 +0200 Change the java indent from 2 to 4. commit f9b0656ad8ac8472f0f76ebacf3de950ea2b8085 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 10 10:58:36 2019 +0200 1.7.28 notes commit 01340b2bcf6a59a15644c46c8c1d4b4c3c89edf9 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 23:33:53 2019 +0200 typo fix commit 9ce38e487bc6db1321fa6db74019a1c92d09c293 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 23:30:23 2019 +0200 update to README.md commit a73b7448535798e821a64c7422991263f70d0a63 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 22:30:47 2019 +0200 misplaced test class commit cebdf810d6c4ccdbfa48aafe567df70ec7b370f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 22:30:23 2019 +0200 misplaced test class commit 21be0bccef1c4f29e29bad72d447ece8d841d170 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 14:51:04 2019 +0200 minor edit commit df48717c871a6a5abce4b1a38923ca84735a63b5 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 14:47:48 2019 +0200 fix SLF4J-463 commit 334ef9a2662a9a308274b23ee9100bd0919f19ec Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 6 12:22:55 2019 +0200 update 1,7,27 release information commit a0030b6e6a1b2e17d24e04d93538632202050dac Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 18:25:07 2019 +0200 allow SubstitutableLoggerTest to pass commit e108a279c72e2e40ee41abd32ce1972d5df9a0da Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 17:18:22 2019 +0200 bump version commit 5f4522556539aac04d145efde39fda9a19afae08 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 17:13:08 2019 +0200 refactor EventBuilder construction commit efeb3665c1cc2ac1cb3daa5426eb7577537df83a Author: Artsiom Chapialiou <achapialiou@gmail.com> Date: Thu Jul 25 17:09:52 2019 -0400 fix JavaDoc typo commit 456e8a8841e9b70b51d7a543123b634c9372921e Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 13:11:01 2019 +0200 ongoing doc improvements commit 383f008a05ab99cd68544174f9beb0180a53aa17 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 12:08:20 2019 +0200 doc fixes commit 6f1583fb01f05c09e16c13d98afadf0505c6ee63 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 02:06:42 2019 +0200 document fluent api commit 69338e78f3b53ad490898de85772d65771d6a3f9 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 18:40:10 2019 +0200 documentating fluent api commit f0674e96481a1a37778dc9834e838f298eb4483d Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 01:19:32 2019 +0200 attempt to fix slf4j-migrator Maven Central upload issue commit 3c4b29b061f1bccd0cc70436096592706ca76edb Author: Nicolai Parlog <nipa@codefx.org> Date: Thu Mar 12 09:53:19 2020 +0100 Relax service discovery in test commit fa20cc51be654cce9a56b8310f6dec36864b4479 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 22:17:19 2020 +0100 Ensure `ResourceBundle::getString` can't crash program commit 258caf4a61058c3e0b0d4044f0a5c9e584810a67 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 21:59:35 2020 +0100 Polish commit b67dabb03da81e30579ea6d8d732b453d856a387 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 21:22:49 2020 +0100 Set up testing commit e2f0fca4ad37f07eabbe814eb488b1a564055f97 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 21:22:27 2020 +0100 Add service provider-configuration file for use on class path commit 1d4daa1c530cd19f9976c442d887e554f3d74879 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 19:57:43 2020 +0100 Import proof of concept commit 8c2ee1378e2902574f20b4e278bcea5f5a7ead62 Author: Nicolai Parlog <nipa@codefx.org> Date: Tue Mar 10 19:22:33 2020 +0100 Create project structure commit 877817a5a3ed85c11c3abede90f0f686c4ffe3cb Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 16:09:37 2021 +0200 start work on 2.0.0-alpha4-SNAPSHOT Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 8eea071d3e090587c58ffe62444b4bf2fa9acdf9 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:55:43 2021 +0200 latest stable is 1.7.32 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 11d5b0bd8d9a83f3f7df34c42591a8e001d96688 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:53:40 2021 +0200 prepare release 2.0.0-alpha3 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit caa81d7368bf6dcd4ad471c847049758d8f0dcf7 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:53:16 2021 +0200 updated build-helper plugin version, removed lifecycle plugin Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2dc0cd2b321edaf765c98dd30fa43164df3b9e45 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 15:41:51 2021 +0200 release 2.0.0-alpha3 notes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit ba8506c47ba1aa57024fde4aac0610b018672745 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 14:37:32 2021 +0200 add toString method in KeyValuePair Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 947654aa64425681894c677244ccd609575048e6 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 10 14:36:40 2021 +0200 make fields protected in DefaultLoggingEventBuilder Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 9df53fb9686df1e9560afd83db5bded964ac0979 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 9 17:47:44 2021 +0200 in DefaultLoggingEventBuilder renamde innerLog to log Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit c87ac7bb29b08d8ac7cb3b9e2107c54a578ac55f Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 9 15:11:43 2021 +0200 very minor changes Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit a1c763e6e1cfea2a1df0148834c317233ad93cf4 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Aug 1 21:34:11 2021 +0200 simplify compilation directives Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 5f6f92a8d1be16c5337cc3dd9c1928a9ff76adff Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jul 31 22:27:04 2021 +0200 move test to test packages Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit bb1ca6886a452bb4fb87b46f5b26542d4b5f9b85 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jul 31 22:26:35 2021 +0200 correct path for NOPServiceProvider Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 975a9a1e7e15e1e9ab8b34487aecba15048a7ded Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 11 07:08:08 2021 +0200 rename org/slf4j/helpers/NOPServiceProvider as NOP_FallbackServiceProvider Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3e2381ea694c23c897433d675facd9a799a52256 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 11 07:00:09 2021 +0200 fix SLF4J-516 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit edb09d7ffa1eae0b67c7733be2b3db95c0047f21 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 22:56:53 2021 +0200 make CONFIG_PARAMS aa final field Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f91024f676b3b1dd4adf5a01a6dabd23c39f6a6b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 10:16:01 2021 +0200 version should have a SNAPSHOT suffix at this stage Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 28e07908a2249ca88582306b6528967835120418 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 9 10:12:49 2021 +0200 align with changes in the 1.7 branch Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6a61c433ee601371e9335e29194c6214959f594c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 23:28:38 2021 +0200 blurb about SLF4J-515 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 50e1c635d5e8a96fb2635dc672c5cdfbe08715e8 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 23:24:30 2021 +0200 fixing SLF4J-515 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 36e39dd0cf51a42fc866fede049f009a82c01d3f Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 19:55:53 2021 +0200 allow unit tests to run in a new thread Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 666533989a5dfd644dd279d634aeae3b64228095 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 8 15:55:03 2021 +0200 add info for verifying signed artifacts Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 39e3b81e5ea69c6610c8d5fd57fd974e090d9fc1 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 17:03:34 2021 +0200 start work on 2.0.0-alpha3 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 3f4d3d91f3096de658d6ce4390b35e9b177569ba Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:52:58 2021 +0200 allow slf4j-site to build Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 81b95ab868bdedfa3540c09583978ab0fbc91651 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:43:17 2021 +0200 prepare release 2.0.0-alpha2 Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 2c914492fd2c8facb844875a5e36ee779b634f10 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:23:48 2021 +0200 removing unused file Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit ff4a3a438ef9a10898f80dd0242d8f93cb24bdd4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 16:23:17 2021 +0200 fix unit tests Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 15e1e7704b3cb2b5b69f6978d6d8a973e5a0630b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 14:08:37 2021 +0200 blurb on DCO Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit 6a06d84243badf7f6d1483b773d650609547d985 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 13:25:41 2021 +0200 testing sign-off hook Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit a9caf3ee3cff9477edf7cfb5dedec4cb938826e5 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 13:24:48 2021 +0200 testing sign-off hook commit 280335bf1470293d13f8667d6d8ecc8947cfa4a5 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 00:21:14 2021 +0200 edits Signed-off-by: Ceki Gulcu <ceki@qos.ch> commit f9c4dcd1dda3d722aa0535075d3ade8721774e92 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 2 00:19:53 2021 +0200 document DCO requirement commit dd2bb115b0b777c0902d24add23fcd6c9c7b8584 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 23:26:31 2021 +0200 typo fixes and minor edits commit d7786eafa7a5e46589faf423b5d23cbba12fd3e6 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 22:37:39 2021 +0200 Fix SLF4J-414 commit 684dfca280532101a7107eee4b6511b79db133d8 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 21:32:31 2021 +0200 Fix SLF4J-421 and SLF4J-287 commit 05486b909a414e88c5035985c4e2557a58b0df67 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 11:02:24 2021 +0200 add JMPS module names in FAQ (fixes SLF4J-465), other edits commit 86e45d7728d8a19ca654cfd0b5649b407e94a980 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jul 1 10:03:25 2021 +0200 fix bugs detected by SubstituteLoggerTest commit b4b2f6fef7f0131be61ab352c90d4189ace96d84 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 23:13:52 2021 +0200 fix SLF4J-435 commit 49831a3f065b8b6b310e04a6fe5e04dd10eeec12 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:40:14 2021 +0200 add isEnabledForLevel method in Logger commit 49356a792ac8b2c7fde6fe8429784c6e706802b2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:39:30 2021 +0200 make NOPLoggingEventBuilder constructor private and allow access via the singleton commit 3d01cc2ca3589fb453d7f063c6fe17140c94d98d Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 22:05:53 2021 +0200 removed unused NOPLogger, NOPLoggerFactory and NOPMDCAdapter from slf4j-nop module, these were moved to slf4j-a4j-ap-api module commit 61220a8b42eb24b0058f079f44841e6a6eb6f25b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 20:11:52 2021 +0200 formatting changes only. applied slf4j/codeStyle.xml in Eclipse commit be3007c6cded1f191896d16532a8fdc72dcbd429 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 17:25:21 2021 +0200 cleaning up deprecated usage commit 9e9a64bcb6dac61d8a71ff37102444870a314ea5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:33:27 2021 +0200 upgade plugin versions, clean up commit 854ce8aa7df6e7189d0c417bff420ae39fe0afb1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:29:49 2021 +0200 the second -jar- goal is redundant commit 7b753d69b0dc645c306148d5d04242407a052a41 Merge: 5c586f11 17e73cee Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:09:44 2021 +0200 Merge branch 'master' of github.com:qos-ch/slf4j commit 5c586f1192c695de2e289e13be842f861f5c38fb Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 29 15:08:55 2021 +0200 slightly higher tolerance commit 17e73cee3a333a7d0650a15202a664f98100114d Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 18:52:57 2021 +0200 formatting changes only commit 990b5087032c8ffc3c51a85152a2c2d69cc8c550 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 10:27:56 2021 +0200 stable version is 1.7.31 commit cb4ac02d7b2dd6284aa2175dbe9ea1370a2f82b3 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Jun 19 10:25:15 2021 +0200 keep highlighted info for 2.0.0-alpha0 commit 92d20a66be20e97b808efa46cbf745d3eeb12bfb Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 23:09:44 2021 +0200 minimal version is 8 commit 6f23d94201daf3c1b15740de2264a71ffaa02364 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 17:02:03 2021 +0200 minor doc changes commit ba62fdc694d2ff94688b04abdbd7572512e29211 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 10:52:38 2021 +0200 fix SLF4J-514 commit 0ef8cb472158af84e396a32f26714a52d2f0b29a Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 17 10:49:03 2021 +0200 fix SLF4J-514 commit d0dad8aa38814a9b4c0e92fe45366114f5c4ff43 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:48:11 2021 +0200 news blurb about SLF4J-497 commit 5c0f12afae45c0ecb0b946c5e20d1302a651ce1c Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:29:08 2021 +0200 unused imports commit 5fb5ecb98a8df95b019441fb7b38b22ee2ab2668 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:28:32 2021 +0200 fix SLF4J-485, LoggingEventBuilder addArgument() should take Supplier<?>, not Supplier<Object> commit a405c8db97d908ba326b775494359049f31c2fe9 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:23:37 2021 +0200 formatting changes only commit 82aca890f0904d2d08c7d3271a1d62b7da6b4927 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:17:16 2021 +0200 formatting changes only commit ade6380f1af465862b7f4c897e2de3ac261a5579 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:14:39 2021 +0200 formatting changes only commit 44371046e0dcbd96f04c1326eeed26476ebcbd13 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 16 00:02:24 2021 +0200 formatting and minor cleanup commit 3c927fa7edd378874d6242e0718c79a99d95ad15 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:59:31 2021 +0200 news update commit 2d1d948c5e25b8fbd13f6b646f77971e7e3a2fef Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:51:03 2021 +0200 fix SLF4J-511 commit c34960912ac24aee60b62499210b1ee08c1f2f45 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jun 15 23:03:21 2021 +0200 rename private method commit 3e5110501cad3c77527d1c94eb6c6b5b67de892a Author: Antonio Tomac <Antonio.Tomac@infobip.com> Date: Thu Aug 6 16:15:33 2020 +0200 Avoid potentially "expensive" rendering of message Object to String when log level is disabled SLF4J-497 commit 57a06aaa2c0f3a018006923a7da919e245bea359 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jun 14 15:55:02 2021 +0200 minor doc fix commit 61e879fa3293b4cb6d946dbdbd8c99c344f14aac Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Jun 14 15:53:45 2021 +0200 fix SLF4J-511 for j.u.l commit d8b223e379fd1446911ba9f2891fc208b96f2bd5 Author: gnp <gnp@acm.org> Date: Tue Oct 13 09:29:15 2020 -0700 Fix typo: "apllications" --> "applications" commit e2c29c81df6fb405a3c5a6dfd1cf28ba26a7c1d6 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 24 10:28:51 2020 +0100 minor edit commit 76ee1112e5ec4d26227ba1f398e834d9ac51e2c4 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 19 08:48:56 2020 +0100 update link to Maven central commit 715b5911858b13a89e5fa9df13f4ca03d72850f7 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Dec 20 16:27:47 2019 +0100 news about 1.7.30 commit 2ac2e807ea498524fc946baae1fde94b3552435c Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 10 09:17:29 2019 +0100 minor refactoring, docs commit 306d8fd23d89b0ad510172c7a15d10175efe691d Merge: 9a3f1f49 27358d39 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 10 08:51:02 2019 +0100 Merge pull request #228 from davishmcclurg/SLF4J-469 Fix NOP fallback memory leak commit 27358d395c8b1f47a9c13ca47bbff33e75dd1fa3 Author: David Harsha <davishmcclurg@gmail.com> Date: Mon Dec 9 20:16:33 2019 -0800 Fix NOP fallback memory leak Substitute loggers are not getting "fixed" when no SLF4J provider is found, which means `SUBST_PROVIDER` will add messages to its `LinkedBlockingQueue` until the process runs out of memory. `NoBindingMultithreadedInitializationTest` doesn't contain any assertions of its own because `MultithreadedInitializationTest` already asserts loggers are fixed in `assertAllSubstLoggersAreFixed`. https://jira.qos.ch/browse/SLF4J-469 commit 9a3f1f4928ab9d0e0f423e377bec9754507d9e8e Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Nov 4 19:15:33 2019 +0100 latest stable is 1.7.29 commit 4a1d5194fe63e503959cffb0ba05be0cb26e0eab Merge: 7c56fe22 acf62ef1 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Oct 17 11:48:48 2019 +0200 Merge pull request #198 from Vampire/serviceloader-in-osgi Make slf4j with java.util.ServiceLoader properly work in OSGi by using the Service Loader Mediator Specification commit 7c56fe22ebdcadecca12db136c4535c25d9622b5 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Oct 16 20:32:17 2019 +0200 minor edit commit 043e9f2d6db2722f5a9cb68e243b61c992bcf4db Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Oct 16 20:27:50 2019 +0200 fix SLF4J-475 commit e00d9a145ba298939d1d90e466ef7aacf78343ef Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:10:39 2019 +0200 minor javadoc edits commit 11bc6c56e3c650871e16d5ef3b9ac12c9bea6ac9 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:10:13 2019 +0200 skip assembly commit fd5c84fabc27d106cdc2c01f423a2772f27c64ba Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:04:37 2019 +0200 updated redirect.html commit 1f49dffdf38216aded83932ea64c7292f5dc2d7c Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 18:04:00 2019 +0200 don't put on Maven Central commit 78a2bf73521800c89f6e890e7e680c8bb29cbcf3 Merge: 340b8204 a04a1f31 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Oct 13 17:54:42 2019 +0200 Merge pull request #226 from hboutemy/master this module is Apache 2.0 licensed commit a04a1f31cf9b1884fbf12927b13abf7dcbc0c04d Author: Hervé Boutemy <hboutemy@apache.org> Date: Sun Oct 13 17:28:33 2019 +0200 this module is Apache 2.0 licensed commit 340b820478f744035098786bcd16056820fbf635 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 11 12:37:41 2019 +0200 add redirect.html to src control commit 33dc75073058265fcd53d3e36ce3780b4ed9a6d7 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 11 12:33:53 2019 +0200 remove link to tar.gz or zip distributions commit 8756e69497cb70d4311762a813672fe74867eb58 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 4 20:28:51 2019 +0200 document release info for 2.0-alpha1 commit 233803688a809fa8ea599306a058351d4c4246a4 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 21:25:16 2019 +0200 start work on 2.0.0-alpha2-SNAPSHOT commit 0c1d72b602da6599e1637c92e9ecb3292afdc3b7 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 21:22:21 2019 +0200 version 2.0.0-alpha1 commit a4010572cbe9810d184359e9944583c635f6446a Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Oct 1 20:06:40 2019 +0200 have slf4j log markers and key-value pairs by default commit b726801a9be39b78cd4f4cf98a7f95e9b0128ec6 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 17:53:15 2019 +0200 makeLoggingEventBuilder made public commit 80b7d224e81e33eeba0415627b0af8cfa6f36bb6 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 17:04:27 2019 +0200 cosmetic changes commit 0ae60630b57aa5b174cbeeb304f9fa113dccefb1 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 16:53:00 2019 +0200 fix test commit 112271b8f6d0542f8d34c7d90885ab1afae1e536 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Sep 8 15:42:29 2019 +0200 'fix build, other changes commit 93e9f097a10899df08a9ab5810322cb7129bfa28 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Sep 7 10:57:35 2019 +0200 API consolidation commit 6f217bbf630596b27c4f8dd59ffba1985b2367b7 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 19 22:01:52 2019 +0200 minor edits commit 0d0f187b14c63bd3f61b857351b702ef990ee0f7 Merge: 32532107 c025afe5 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 19 21:52:22 2019 +0200 Merge pull request #178 from sschuberth/patch-1 Fix the SCM connection URL in pom.xml commit c025afe5361ed10d80c693e93dd928bf5934b82e Author: Sebastian Schuberth <sschuberth@gmail.com> Date: Mon Jun 19 22:07:53 2017 +0200 Fix the SCM connection URL in pom.xml The "connection" should be an URL valid for read-only access and has to follow the syntax as described at https://maven.apache.org/pom.html#SCM. commit 32532107f5b520fcaeb1220cac91dc72f36915d6 Merge: 78c10ee6 e757c41a Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Aug 14 00:06:04 2019 +0200 Merge pull request #218 from delgurth/SLF4J-466-Fix-build Fix the build and a typo commit e757c41a57f7d57f5889144ad09d77a8b57f92ac Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Wed Aug 14 00:00:29 2019 +0200 Fix the build and a typo commit 78c10ee651d0c8317971982cbcfdf963aabc8285 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 13 17:30:17 2019 +0200 refactored EventRecodingLogger and EventRecodingLoggerTest commit 178e836f714c3024c6317fb1b09760d4b5c9e2fe Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 13 15:38:32 2019 +0200 move methods from Util back to MessageFormatter commit 4ed24489fa807d9150f4cd9b46b207a4f4373324 Merge: 8a5c449b b0b57b9f Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 13 14:38:31 2019 +0200 Merge pull request #215 from delgurth/SLF4J-466 Fixes SLF4J-466 commit 8a5c449bd82427113581f8c6c381b1d7a05274f1 Merge: 206449b6 b266bb29 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Aug 12 18:04:24 2019 +0200 Merge pull request #217 from delgurth/fix-intellij-java-indent Change the java indent from 2 to 4. commit b266bb29374e37b63ae106f3177941df10b9aa6f Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 17:46:11 2019 +0200 Change the java indent from 2 to 4. commit b0b57b9f9b261158d4c888f6527018c5f80eed8b Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 17:40:47 2019 +0200 SLF4j-466: if was missing a space commit a98bd22216fabe015635445be7ba9e77caabee72 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:49:37 2019 +0200 SLF4j-466: fixed typo in javadoc commit 587ec03af793126782efb6f8196b2487e524801f Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:42:41 2019 +0200 SLF4j-466: added missing newline at end of file commit 7c3d35596f93142cd75a7c1d00c677c9c3051d0b Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:40:13 2019 +0200 SLF4j-466: only call arraycopy if we have elements to copy commit 9df5d4fe915b887ff610a50fca30fe1064d63c66 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 16:01:42 2019 +0200 SLF4j-466: put the throwable at the right place of the SubstituteLoggingEvent, introduced two more recordEvent methods for the two object argument log statements commit a09d78831003bc155ca9ea5374d24dde24dd2976 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:59:14 2019 +0200 SLF4j-466: Move two methods from MessageFormatter to Util so they can be used by the EventRecordingLogger as well commit b99ad9f80f937a91209accd9561332bb9fa30312 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:58:02 2019 +0200 SLF4j-466: add missing marker in one of the warn methods commit fe440ce9cdf1637dfd8aa9998114c627ff7c1078 Author: Wessel van Norel <wessel.van.norel@delgurth.com> Date: Mon Aug 12 15:56:52 2019 +0200 SLF4j-466: Add test for all happy flow cases commit 206449b67433696c3ab85a1d9f990468b7839dd7 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Aug 10 10:58:36 2019 +0200 1.7.28 notes commit 173b06ad885c1b4fa6f506ceeabe76860d9bfb03 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 23:33:53 2019 +0200 typo fix commit 999539196e687d3b4eb9b15dcd7c1cb8b7cd3cbd Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 23:30:23 2019 +0200 update to README.md commit 94393567276108257bacc34bd460d742d93d9d08 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 22:30:47 2019 +0200 misplaced test class commit 96783aab43ea798f4c3695a91c4d5612084d819f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 22:30:23 2019 +0200 misplaced test class commit e0a6d06fc03935ef5ae559f46fa6e96c1c348480 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 14:51:04 2019 +0200 minor edit commit acc915075b4932ebf99c2febf2fb60b4144200aa Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Aug 9 14:47:48 2019 +0200 fix SLF4J-463 commit d5074263f87b1b8b824e51cfc6e72d25b01c1ccb Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Aug 6 12:22:55 2019 +0200 update 1,7,27 release information commit b05e7fe90da3583d343d26cea424dcb0a6cd640a Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 18:25:07 2019 +0200 allow SubstitutableLoggerTest to pass commit a5eb9ce00ca119da55b3a05c986f8bfe795608b0 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 17:18:22 2019 +0200 bump version commit fde8ca480c86bd01dcca4d492e0fc5db56eb2619 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jul 28 17:13:08 2019 +0200 refactor EventBuilder construction commit 7533fde7657e9577cd30bcf82584fb37207a99d4 Merge: a5357c8d 83b88c50 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jul 26 12:01:17 2019 +0200 Merge pull request #210 from ArtsiomCh/patch-1 fix JavaDoc typo commit 83b88c502a322742f855bbb6e9d2f856dbd0d02d Author: Artsiom Chapialiou <achapialiou@gmail.com> Date: Thu Jul 25 17:09:52 2019 -0400 fix JavaDoc typo commit a5357c8d49aab89659d40da25f2e31487add20b3 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 13:11:01 2019 +0200 ongoing doc improvements commit f9c1d25113eec6a89a3da818c402fcc58478ee9f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 12:08:20 2019 +0200 doc fixes commit 4faf891b8a1e9c56fe6eea0618a707a6acb16dd2 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jun 14 02:06:42 2019 +0200 document fluent api commit 890fc5b0e60c9d0003b6fa98aa271eaf6c1cd540 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 18:40:10 2019 +0200 documentating fluent api commit d3f50a9185266cf03a0c1a93c15cffcd4bc32c1e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 01:19:32 2019 +0200 attempt to fix slf4j-migrator Maven Central upload issue commit 365edc7c32cd8258fe78f09d370e0bcb94c96c27 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 00:54:15 2019 +0200 actually uploadable build commit 669c550ab8e0e772d44993fc1f3d7fafb12a7d79 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 13 00:34:57 2019 +0200 fix javadoc generation work commit 68c7c99adf55deed2e01d19a2e3e8e72a0a8bc04 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 12 22:23:14 2019 +0200 more javadoc fixes commit c243bc6476b53d0557b012d736ab955892caf215 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 12 22:14:51 2019 +0200 more javadoc fixes commit abad55509a99b39d82965769b552d6f3a9a535d3 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 12 22:13:22 2019 +0200 javadoc fixes commit e52fb5ae15dff5a411a5644cf53305d766793830 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jun 12 21:07:41 2019 +0200 ongoing work on fluent api commit d9690a131ecd335fdaa1e19848fe79198e5d03c4 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun May 5 17:25:17 2019 +0200 fix notification adress commit 029eab156923374c858a85ab656bddc48f2e33e5 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu May 2 14:50:35 2019 +0200 ongoing work commit 4d4ebb395ed994263b848e300cd3e282db5fd795 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Apr 29 22:35:08 2019 +0200 initial backward compatible implementation of fluent API commit c7b22182838120ab148973d7d1e960d076ff3287 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Apr 29 21:29:13 2019 +0200 changes to the LoggingEvent interface commit 1f3b8726d160c51befdf57ec42c6bafbd8b8652c Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Apr 28 23:49:20 2019 +0200 ongoing work on fluent api commit 8c51d8ea7cdfa8d804876463d1c9c6b1543bfce9 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Apr 28 21:28:47 2019 +0200 mark pom as 2.0.0-alpha0-SNAPSHOT commit 8705978bb7543d03f570119361bce0d787ab8e77 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Apr 28 13:38:25 2019 +0200 ongoing api changes commit 1cb6b26288896649cbe97def0cb60a125fcb3f6e Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Apr 28 11:48:09 2019 +0200 start 2.0.0-alpha0 commit 875442057f41ec9af218dfafb812a138caa9b170 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Feb 20 22:15:52 2019 +0100 very basic experimental version commit 905443f39fadd88a8dd2c467e44affd8cb072a4d Merge: 5ddfa9c6 abe7a783 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Feb 20 21:16:18 2019 +0100 Merge pull request #205 from rgansevles/master Additional fix for SLF4J-449 commit abe7a7835c8a63cdbaf65a50461c6d9a35854692 Author: Rob Gansevles <rgansevles@gmail.com> Date: Wed Feb 20 20:44:41 2019 +0100 Additional fix for SLF4J-449 commit 5ddfa9c6b3252834cf3be5f88ea27c821f70a577 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:30:30 2019 +0100 tweak VII .travis.yml commit e2dc9174e8ea3f972b4b0fcf7148d19861ebeb42 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:26:06 2019 +0100 tweak VI .travis.yml commit 08f378764a8bf664bb5a8ae373b5f252f599d0bf Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:24:47 2019 +0100 tweak V .travis.yml commit 51be1dfe0b1636c35ec76e091537ce1ca634c4cf Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:15:35 2019 +0100 tweak IV .travis.yml commit a9b3d222c450fbbbb2d3b41d5885e67976426eee Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:13:02 2019 +0100 tweak III .travis.yml commit f7c0d367dc90449b546339f658a4fa8c7428469e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:09:16 2019 +0100 tweak II .travis.yml commit 6b65bbd86b610c633d3c61cc6e389db93569ff08 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 23:05:15 2019 +0100 tweak .travis.yml commit 91a30c89678d597b11582e51c460f3c0354ceda2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 22:53:59 2019 +0100 remove toolchain dependency to simplify build, make travis happy commit 379d96b30443ab91a86aad63b5c5047badc6537d Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 22:39:37 2019 +0100 upgrade Travus build to JDK 11 commit 9928d80daf022e6461647109d62e237498f0270c Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 22:38:04 2019 +0100 SLF4J-445 commit 458525e2e194e8d5eab27df1d75955602f627b1c Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 21:15:32 2019 +0100 fix SLF4J-449 commit 603ae2cb2268619f9aaaef43eab0028d15742fa0 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 21:00:18 2019 +0100 SLF4J-439 commit a822fd76158c091cac066843c7f13298b6c3fd23 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 20:52:40 2019 +0100 fixed SLF4J-233 commit fc7bf4dee401b8c1a3ddfd5bb9a7b01ac1febfec Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 19:24:01 2019 +0100 maven build without warnings commit 7092ce68af0b0bb21615bf915de780d5623756f4 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 18:43:24 2019 +0100 start work on 1.8.0-beta5 commit c7e0311517153d72e6edcf0ab52be7fb42ea36a7 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 18:27:52 2019 +0100 prepare release 1.8.0-beta4 commit fb418db538a4990293b1afa47d735cd506497865 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 19 17:21:46 2019 +0100 fix SLF4J-456 commit e9d4b6a4a83ce987a9ad011c6256a256e5648551 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Feb 16 14:18:58 2019 +0100 blurbp on SLF4J-454 commit c15d3c1dab0c3398011dec3a16ad3e45b75ae70d Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Feb 16 14:12:44 2019 +0100 prepare 1.8.0-beta3, fix CVE-2018-8088 commit acf62ef1cff3f5b3c8df5e44fe01a2aac1e97642 Author: Björn Kautler <Bjoern@Kautler.net> Date: Fri May 18 15:38:40 2018 +0200 Make slf4j with java.util.ServiceLoader properly work in OSGi by using the Service Loader Mediator Specification commit 5e93462dd781677fb75aefc6cc7df65822970ca0 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 22 17:25:16 2018 +0100 unit test SLF4J-409 and add to news.html commit 3e7e72e70b6f3db504bda07f394e1e14832829f8 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 22 17:16:49 2018 +0100 fix SLF4J-409 commit 1c713e7c1042ca1fcba550df79a4ad7fce055211 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 22 11:06:23 2018 +0100 cater for JDK 10 and later commit 74b0999f9513d340f50832d0bf59ccb2d2cdbfee Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 22 10:42:26 2018 +0100 cater for JDK 10 commit 39824d8c8bb4c2c7ceedf286b4f1b90e0229ac7a Merge: c960e863 c85e3e2e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 22 08:18:11 2018 +0100 Merge pull request #195 from Oseenix/compile_error_when_1.5_exsist Reslove compile error: 'javac: invalid flag: -s', when exist 1.5 tool… commit c85e3e2e9c5e21a41193db5cde77146bb30ebdbd Author: zhoujinze <zhoujinze@gmail.com> Date: Thu Mar 22 13:47:16 2018 +0800 Reslove compile error: 'javac: invalid flag: -s', when exist 1.5 toolchain commit c960e8630cdf0ec4a6c5ea687ebe536e9e43ab68 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 21 23:11:21 2018 +0100 start work on 1.8.0-beta3 commit 26731d281940483d8777a8a7a4146329a28496aa Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 21 22:56:32 2018 +0100 it's beta not bata commit 64d5b7d83e2769fb56bd70120a8ff112777480d9 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 21 22:46:30 2018 +0100 news on SLF4J-411 commit d7d1710d99afa657f3f8bd41583741ba4ad3eeb7 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 21 22:42:14 2018 +0100 fix SLF4J-411 commit 59e497eacb07c1380c65fa6057c1213b248bdb99 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 21 22:29:06 2018 +0100 fix link to 'sttic problem' article in apache commons wiki commit fc22d9c24d85a2e3340c414bf0a470a31223a9ab Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 20 10:33:29 2018 +0100 prepare release 1.8.0-bata2 commit 34486e4ea5ec6a4960930a239e80f868f1bf66e3 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 20 10:30:21 2018 +0100 SLF4J-431 commit 9b536f4259adf2f01852e86306a3a2d7e4a238c0 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 14 01:14:19 2018 +0100 news on SLF4J-431 commit d2b27fba88e983f921558da27fc29b5f5d269405 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 14 01:09:26 2018 +0100 fix SLF4J-431 commit 0ec1f6aac8648e87a7dda2f5730fef6db3b4fa33 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 13 16:17:59 2018 +0100 remove autoads.js commit d8f5ba8ea54132b8ac98b9a906257df632b731ab Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 8 11:02:24 2018 +0100 google autoads commit 67d5be0f569e24d373c07f97aa443702a0b60f8e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 8 10:31:31 2018 +0100 google autoads commit 78332e5be05c245c76c46d272b983f0855dcdfaf Merge: 8bc0a97a 49d61b7d Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 2 20:14:33 2018 +0100 Merge pull request #194 from stephengroat/patch-1 upgrade travis img type commit 49d61b7d3c9e9bc58f85bb43e92a72fb5c01ff02 Author: Stephen <stephengroat@users.noreply.github.com> Date: Thu Mar 1 14:51:13 2018 -0800 upgrade img type commit 8bc0a97ad58e0fa7875c00edd5035e077e31f05c Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 31 10:40:15 2018 +0100 fix SLF4J-428 commit cf2fca3441fea6b7dc224f5232319d621f3a0422 Merge: c0beff4a 5889ca54 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 31 10:11:07 2018 +0100 Merge pull request #192 from sothawo/automatic-module-name-jul-to-slf4j add automatic module name to manifest commit 5889ca541530bfadc98e1043fcd60d1323af94d9 Author: P.J.Meisch <pj.meisch@sothawo.com> Date: Wed Jan 31 08:18:30 2018 +0100 add automatic module name to manifest commit c0beff4ab7ff9daaf3df4fab5b9796ad65bcf221 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 13:50:26 2018 +0100 start work on 1.8.0-bata2-SNAPSHOT commit 287004f70bc1b238b41e69f2aa5d1db18a2b6a00 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 13:48:01 2018 +0100 fix wagon plugin version and target host commit dfe42a4ff34157497d0a2f7e59c535b825126cce Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 13:18:21 2018 +0100 prepare release 1.8.0-beta1 commit 805df52bdcb86718b01b3e9e20c7db639bb57a18 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 13:15:29 2018 +0100 fix SLF4J-426 commit f8a590ea676cecd814bcb577e413ff2e39f8142f Merge: cda79c4e 2de3bc7e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 11:24:08 2018 +0100 Merge branch 'javabrett-travis' commit 2de3bc7edd446e5859ce748941d322651e756fc5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 11:23:26 2018 +0100 inverse Java 1.6/Java 9 jdk element in toolchains. This allows javadoc to be built commit b0fba1b48bb7e893905b9bb302f73dc72e8ef6b0 Merge: cda79c4e a8aa7832 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 11:14:44 2018 +0100 Merge branch 'travis' of git://github.com/javabrett/slf4j into javabrett-travis commit cda79c4eca3c96637f94438ff51fcde164e67d24 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Jan 30 11:11:45 2018 +0100 make createdPostInitialization variable final public commit 0b1e6d38cfabd4b7ed335aec1aa6b2ae0c770f08 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 16 20:20:38 2017 +0100 fix mailman urls commit d186d5fbd35d826fc85b5cd82b066d0655d6e1da Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 2 21:30:08 2017 +0100 failing OSGi/ServiceLoader integration commit 3556e7c87bb209e2dd99cf0aa771e0f6e28433b6 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 2 20:30:46 2017 +0100 doc updates commit 5f00780faba08756932de6c165a153dd1dd7558a Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Dec 2 20:27:37 2017 +0100 slf4j-api now requires Java 6 commit a8aa7832b7cb8091bc638d12a4fc1abfaaf44d8e Author: Brett Randall <javabrett@gmail.com> Date: Sat Nov 11 03:29:08 2017 -0500 Added JDK9 to toolchains. commit f13c8c20c26f268463879b2c4ffb408bca815f2c Author: Brett Randall <javabrett@gmail.com> Date: Sat Nov 11 03:23:48 2017 -0500 Added a profile for Travis executions and disabled maven-toolchains-plugin on Travis. Note that Travis will not support maven-toolchains-plugin, see https://github.com/travis-ci/travis-ci/issues/2727 . commit 2ed2565fe474a691171956c4572beef734d1180b Author: Brett Randall <javabrett@gmail.com> Date: Sat Nov 11 03:23:00 2017 -0500 Set Travis to run on Trusty and oraclejdk9. commit 2d4a1324b64ab2ee6af997743e9e829c939e0438 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 20 16:53:05 2017 +0200 start work on 1.8.0-beta1 commit 755bf3d42b43a82a528b182fe6667375b3920dd3 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 20 14:55:53 2017 +0200 preparing release 1.8.0-beta0 commit d9280190fb7368b21a2d8ca49bebdf6c9bb6a40e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 22 23:45:39 2017 +0200 bump version to 1.8.0-beta0-SNAPSHOT commit 6ac20c6a0ae96ea6609f24d92eb235d87d8a0f8b Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jun 22 23:43:18 2017 +0200 remove org.slf4j.impl package - fixes SLF4J-407 commit bc03976da8bc0b4e83bae3dc7404336e03e22017 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Apr 27 17:34:01 2017 +0200 typo fix commit 4772fff68123c337e1b39de4ab8789faa8c98f1b Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Apr 27 17:33:41 2017 +0200 start work on 1.8.0-alpha3-SNAPSHOT commit 70ec42263abf188950cd2a8f8eb4502c9c372ac1 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Apr 26 00:08:47 2017 +0200 prepare release 1.8.0-alpha2 commit 2ff447be268ab736dd64d908d4ec922292341c8e Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Apr 26 00:01:31 2017 +0200 doc improvements commit 3823bd18e8829e72bf4a63cca62eb6c27e9132b6 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Apr 25 23:35:40 2017 +0200 no need to export 'org.slf4j.jul' package commit ec8419c5163ff50999b17ceca0f27fd49553d079 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Apr 25 23:26:02 2017 +0200 news.html update commit eec2336e6287288276cc49750d2ab5ae098cddc1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Apr 25 23:17:57 2017 +0200 fix SLF4J-408 commit d168ea7f128ebe6485048524b52a975be439375e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Apr 25 23:01:19 2017 +0200 start work on 1.8.0-alpha2-SNAPSHOT commit ae16a03219821ec78e8dd456cb3e0c20e5adcda8 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Apr 13 16:07:02 2017 +0200 update new and faq commit 5ece81efcb5c5ad0f23f0be19f46c890c3db4625 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Apr 13 15:48:37 2017 +0200 prepare release 1.8.0-alpha1 commit bcb318771cc50d7c8cd0183285f65c7e335e35ed Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Apr 13 15:32:57 2017 +0200 fix SLF4J-406 commit 248aa303ce22047a282468c498a455bb2ca8c517 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Apr 12 21:27:12 2017 +0200 fix typos commit 83f6fe4f44fc6ed636b445c4c33b23c7bb64b2f6 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 17:13:54 2017 +0200 Revert "slf4j-log4j12 modularization with Java9-EA163" This reverts commit 067a618c4ba77f96868d9e10a9b3d2ebe0d3b8f1. Given that MDCFriend must be located in the org.apache.log4j package, it is impossible to modularize slf4j-log4j12. It must forever reside in the class path rather than the module path. commit 067a618c4ba77f96868d9e10a9b3d2ebe0d3b8f1 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 16:26:58 2017 +0200 slf4j-log4j12 modularization with Java9-EA163 commit 1448f05fb87cf7a03c6189e5205a5f81f6d55a16 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 16:07:45 2017 +0200 start work on 1.8.0-alpha1-SNAPSHOT commit 685d0598cd47c6cc23ad655e60322a7583b959af Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 15:27:50 2017 +0200 site update commit 541e6f7d181ff3405ae9495724430825aefff6a9 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 11:01:47 2017 +0200 update maven site-plugin to 3.6 commit 578cce94f755c6f53c72b661d9ffbd89111279d3 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 10:45:48 2017 +0200 better luck with default java 9 toolchain commit ef31abdd138fe7cdd0a8ef8370bfcc8e3f7325b9 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 7 10:45:05 2017 +0200 attempt release 1.8.0-alpha0 commit 7a1d11ef60fe38f158c967f5630a33863ae2269c Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Mar 25 14:35:29 2017 +0100 (OSGi-related) commented out Import-Package: org.slf4j.impl in slf4j-api MANIFEST.MF file commit 89810489a18e323680c1bc3ffd5da2f267d46847 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Mar 25 14:31:19 2017 +0100 deleteing log4j-over-slf4j/src/test/java/module-info.java commit 129cf98bbdc1b901af73c690ff13d792ca4711d0 Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Mar 25 14:29:59 2017 +0100 J2SE 1.5 is required commit 054e720426103cb22d699a513b64bf6624ca020b Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Mar 25 14:01:27 2017 +0100 following recommendations found at https://maven.apache.org/plugins/maven-compiler-plugin/examples/module-info.html commit 20570d8ebacca9978afbdbd936cc88db19d10b9a Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 23 23:57:53 2017 +0100 it's all modules baby commit 1c13755b2520e511bc41b5c6fdc8bd6c58e529c0 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 23 23:41:47 2017 +0100 tests pass except log4j-over-slf4j commit 99e356974859a4cac2f5e533de2d8232d9d5dbe6 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 22 23:41:49 2017 +0100 slf4j-api tests pass commit e47cdb00363734e679915f22f9e18b0f41ae4617 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Mar 22 11:53:27 2017 +0100 use standard location for module-info.java; start simple by assuming Java 9 as exec environment commit d29b6921ed1cbbf93be048510ab7a3e59be41f53 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 21:36:27 2017 +0100 initial attempt at introducing modules commit 916959d5a61b3e4cdee42c63f09633d3bad6b525 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 21:33:30 2017 +0100 skip osgi tests under Java 9 commit e44f0d773ebe9948cf4ef1a6d27fbfee1ce1b229 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 20:21:56 2017 +0100 Removing slf4j-api's dummy StaticXBinder is not longer needed commit b9d4a8cc405799e56fe71813dda776375ed847c1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 17:19:38 2017 +0100 require JDK 1.6 profile for anianimal-sniffer plugin commit ab389a9b82abe35034a3026c7eb0d4b9a07b4ae7 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 17:11:42 2017 +0100 removed 'Fragment-Host: slf4j-api' from MANIFEST.MF files, set Bundle-RequiredExecutionEnvironment to J2SE-1.6 commit 73874fa327c61b5b05807050986792916a5173c1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 17:02:03 2017 +0100 update packages, migrate test to Junit4 commit 369beaa1583a267bb5848ed2f1eabea6bf6c785a Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 16:32:18 2017 +0100 all tests pass commit 45c12f86c84c7b8c9479c275ec17ceed312b1cd1 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 14:50:48 2017 +0100 ongoing work, removed slf4j-android and slf4j-jcl modules commit 89e93009ea58b35e20a89fd896be6d8d97cc6e33 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 21 10:35:54 2017 +0100 document 1.8 error messages commit 7b82bd29e40fbac20fd373c0bc9148ebb97df6fd Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 20 23:13:52 2017 +0100 further progress commit 0a27822547087edbd1de4f1102f86392ed5d76c5 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 20 22:31:31 2017 +0100 ongoing work commit ed9b3712a03cb3e6617745616b9afb0a6c646a85 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 20 21:51:05 2017 +0100 ongoing work commit 1232e8529f5844e03e4d528a88185413761853e2 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Mar 19 20:34:22 2017 +0100 document MethodHandles.lookup() pattern commit c7d479e43f17f02693f095f4063b61d4163ac2e2 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 16 17:49:15 2017 +0100 start 1.7.26-SNAPSHOT commit a81440ea36676f3b090f5a4ccba70d17c7b80f6e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 16 17:46:41 2017 +0100 fix date issue in news.html commit c2a7cca6cbbba49e452522d2fa3358f83ccb2c99 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 16 16:54:09 2017 +0100 prepare release 1.7.25 commit a8489127b08bd5b8e1fa7ca5e5d33f93c0676986 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 16 14:34:31 2017 +0100 change serialVersionUID since internals changed commit 2fc2dc1deb3767b2c84a0d50eb5935f7fba59217 Merge: 2f06933c 60eb95e0 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 10 11:49:04 2017 +0100 Merge pull request #173 from hazendaz/master [license] Update copyright year to 2017 commit 60eb95e0f58728dea8e71f770cf5951ca8270ed2 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Sat Mar 4 21:02:11 2017 -0500 [license] Update copyright year to 2017 commit 2f06933ccd22748fbe5d6ab45314eae5c586977b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 28 15:11:28 2017 +0100 use SLF4J formatter commit 97472ca10ae82c3244f5c8e6d6fea5847cb90731 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 27 15:14:55 2017 +0100 fix deprecation issues commit 4a8c16635cf59a88521fdcbba74735244dec9f6b Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 27 15:14:33 2017 +0100 fix SLF4J-395 commit 509c3444ac72913309999367782055fb40cbe184 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Feb 26 21:32:50 2017 +0100 fix SLF4J-394 commit 898e22225909c4c84ef4885b6d346ca0a8565e38 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Feb 26 21:32:06 2017 +0100 type fix commit e5ce0d5e41a47133b2a5d7fd4cb5e8ab9bf44073 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 24 12:13:19 2017 +0100 start work on 1.7.25-SNAPSHOT commit e49d591fc6f3e4f1517edb7ac56f2ca62b4660ce Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 24 11:25:16 2017 +0100 mark final fields as final commit 1e715a79b5ded4b6f33f757bde4ef2a257019afe Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 24 09:39:41 2017 +0100 prepare release 1.7.24 commit cfa8f7519b9e47e4f0b5c9e16754166bb09919fd Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 24 00:07:56 2017 +0100 avoid syncronization commit 9e441fe9f99b13943cd6b98a3608a39806e69b6c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 23:47:53 2017 +0100 fix SLF4J-385 commit b19ba5b87d10e3cf2d0493322bc3c7f3daf69478 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 23:47:31 2017 +0100 point to root cause of initialization failure commit 1b93bb138d300ef6d00f4754c91628d4c2cdc34b Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 23:28:55 2017 +0100 add entry for #unsuccessfulInit commit 379574b7445e7b0b1f1907d9f6edc61a4242105c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 22:42:42 2017 +0100 fix SLF4J-369 commit c6e1c3d495d19c636aa923f012235b48e2878d9e Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 22:36:51 2017 +0100 fix SLF4J-240 commit f3dc4dd8a32741951458eaa0605c37bd6e716e9c Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 23 22:26:59 2017 +0100 fix SLF4J-383 commit e0120c1473b5c2d3888443738493cf635ce275be Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 21 15:00:07 2017 +0100 make m2eclipse happy commit d82a2e9ab7aad93efefbb65a94a56a02e97ea3e8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 14 23:39:42 2017 +0100 start work on 1.7.24-SNAPSHOT commit 5c822203c9c334d8e4e5451e716f38c2fd4202c5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 14 23:38:20 2017 +0100 release 1.7.23 commit 983b04b546935bda09f3619c9435191e19757482 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 14 23:03:55 2017 +0100 minor edits commit 2651ad2a386cad909fe3e1ee2dc52558b552fba8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 14 23:00:44 2017 +0100 slf4j is on Java 5 commit 01e56add155e723640a1c75ba917615317b2e73f Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 14 22:51:29 2017 +0100 fix SLF4J-393 commit 7ef791c4ae9c0865c5cdc650f68f56bd7cacd4ef Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jan 27 19:42:04 2017 +0100 correct bugzilla links commit 1ddc1f72d1281af6cad5956ed8736ad5114fa62f Merge: b8b881b7 7df8afcb Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 11 20:19:05 2017 +0100 Merge pull request #169 from ipolevoy/master SLF4J-389 - added a test commit 7df8afcb22dd25fd156b4336ba4ade4f85014a4d Author: Igor Polevoy <igor@expresspigeon.com> Date: Wed Jan 11 13:14:14 2017 -0600 SLF4J-389 - added a test commit b8b881b7395ead1d2316a740b6a633b3ed16e994 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 11 18:56:49 2017 +0100 follow java conventions for enums commit 69be5f7f9875347ed0feb54577bff3b1bb9063a0 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 11 12:43:02 2017 +0100 fix SLF4J-389 commit d0d9536dc9bf2468aa9e379d1bc644e1e5ed3cca Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Jan 11 12:01:37 2017 +0100 update year, remove external project references commit fe664d8dd09b2a01c378b1a748aecbd4e61bad06 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 15 18:42:30 2016 +0100 added full name for Jonas Neukomm commit 66883348500a60ed26e5bf2289d0d26dce3d10bf Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 15 11:20:35 2016 +0100 fix SLF4J-379 commit 6de782333123937964d4020c75e6a1bc8eaa0b4d Merge: e83fe502 a1ef84cf Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 15 11:13:32 2016 +0100 Merge pull request #165 from barney2k7/SLF4J-379 EventRecodingLogger stores Marker in SubstituteLoggingEvent commit a1ef84cf001b57cb6085d578109000dcc8cae92e Author: barney2k7 <barney2k7@gmail.com> Date: Thu Dec 15 09:24:16 2016 +0100 EventRecodingLogger stores Marker in SubstituteLoggingEvent fixes SLF4J-379 commit e83fe50258f6fd3c386e1113ac264c5167ad11e2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 18:12:35 2016 +0100 start work on 1.7.23-SNAPSHOT commit 3ec4456cd318a3091f2659e1dfcbbe813e6b9642 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 18:05:25 2016 +0100 correct site id in distributionManagement commit a94437fda8c90ef248bfcc7cd72fd4ca572a5270 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 18:02:38 2016 +0100 prepare release 1.7.22 commit f9d6a4de0b934c1c58da81f8930db920a1a83077 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 17:58:22 2016 +0100 fix SLF4J-370 commit 5ed4a1a9a7f59a2430162b64e649bfac0364ecdc Merge: d1d06b0d baea9dba Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 17:10:57 2016 +0100 Merge pull request #164 from barney2k7/SLF4J-377 closing InputStream in case of IOException, too commit d1d06b0da8d5aed3e72abf4a67e9a8a64be3b9f2 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 16:27:42 2016 +0100 SLF4J-332 commit 03ff2624e71fe0e3b4624f8d324f74247f2aa56a Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 11:46:57 2016 +0100 remove slf4j-bom commit 80d972e3e5529f3cf4dabb974ff30cac4d4f686b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 11:45:19 2016 +0100 fix import warnings commit 6f19cb8c3dc085f3b934594efcfb0a5512fc8283 Merge: 64fa52c2 7761fa43 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 13 11:39:19 2016 +0100 Merge pull request #163 from barney2k7/SLF4J-332 add log level 'off' to SimpleLogger commit baea9dbaa9825661d5513d7f211ef65f227e2235 Author: barney2k7 <barney2k7@gmail.com> Date: Tue Dec 13 10:35:37 2016 +0100 fixes SLF4J-377 note: cannot use try-with-resources as slf4j is still on java 1.5 commit 7761fa43b2cb61ede4c4dc10090ff1559bd6a482 Author: barney2k7 <barney2k7@gmail.com> Date: Thu Dec 8 15:56:13 2016 +0100 SimpleLogger now has level 'off' Implements feature request from SLF4J-332 commit 64fa52c2f8d32cfa4f8505e27706209b28090bed Merge: 1c6cbf05 9fe38af5 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Nov 8 08:29:35 2016 +0100 Merge pull request #162 from sebkur/fix_typos Fix typos commit 9fe38af528ac072d6400c4f0e9658e78fd8efdb6 Author: Sebastian Kürten <sebastian@topobyte.de> Date: Mon Nov 7 14:54:43 2016 +0100 Fix some typos in comments commit 42e9b19c77d4e9a77ee8be897e1dd470558ca7b1 Author: Sebastian Kürten <sebastian@topobyte.de> Date: Mon Nov 7 14:51:58 2016 +0100 Fix some typos in author names commit 1c6cbf05e6a99a8805397d1c06008021fdc96527 Merge: 19bfd0f0 c2463021 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 29 13:47:41 2016 +0200 Merge branch 'master' of github.com:qos-ch/slf4j commit 19bfd0f011ce429434c6d274b3ac5a3ac62484e7 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 29 13:46:58 2016 +0200 add blurb on adding slfj4-nop.jar on the class path commit c2463021fe0944a03d3fdcc14c3914c86d4a7a4f Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Apr 5 13:59:38 2016 +0200 fix SLF4J-365 commit f518171e197bde70b22766cb942c96ec726ece16 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Apr 4 20:47:46 2016 +0200 set next version commit 25aba2ea4febeb35ba910c249826b5a62001a7e4 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Apr 4 20:10:18 2016 +0200 prepare release 1.7.21 commit f544bcead5c71c9697755a9bf99cc4576116a90b Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Apr 4 18:42:27 2016 +0200 refactor MultithreadedInitializationTest commit af188829dcc13237fad161db9629ed028bc12b14 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Apr 3 21:52:39 2016 +0200 fix memory leak bug commit 81b237672cf1b02e0d44e870dcf5e963bdf47617 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 31 21:11:21 2016 +0200 ongoing work, does not compile commit 29e7da07a23709afb59afc563935da5f4056bc69 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 31 14:35:46 2016 +0200 fix SLF4J-366 commit 8f536317cbeabc1396b9bfdfffc7c486e9944dcc Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 29 17:20:52 2016 +0200 next version is 1.7.21 commit 0aa7c8c8c38e25405d3241235646a9cedeb80eb8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 29 17:16:52 2016 +0200 minor edits commit b8bd41a454f108493759d69b10c5a9d63390f5c9 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 29 16:57:33 2016 +0200 preparing release 1.7.20 commit 0c89ee480a2d833690318b64e929b1a251d508c3 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 29 16:56:50 2016 +0200 fix SLF4J-363 commit 8bf1f8cf5ca1bc9df8cedd63d8685ab961110113 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 28 23:36:33 2016 +0200 add adds on right panel commit 0a873d74ae1944567523ad12f63c4b3a9b5a80b4 Merge: 7c2f6cd1 4043dcd4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Mar 25 14:05:17 2016 +0100 Merge pull request #148 from laurio/patch-1 Fixed a typo in LoggerFactory.java file commit 4043dcd45a5b51f9c6d8a3f57a40f8f410e9cde6 Author: Lauri Oherd <lauri.oherd@gmail.com> Date: Fri Mar 25 12:14:26 2016 +0200 Fixed a typo in LoggerFactory.java file commit 7c2f6cd1dc8e2fe26f6ca7334d1319ffced995a4 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 21:21:26 2016 +0100 still more lenient commit 105c2ee18cf51118e4a2dc0b5f466a461b2bbb11 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 21:15:58 2016 +0100 more lenient assertions commit 79698d67a2cac4db0539f9edbf3b0e3a1c3c89d4 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 18:55:02 2016 +0100 record event count commit 3fc58f2256b2c94661a435dafea8148e5c8e06dc Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 17:43:32 2016 +0100 minor change commit b46c356232ab3b6da4b5c896b1f640115fc6d689 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 17:33:17 2016 +0100 bug fix commit f3ca982135b7e7a5905d7ffe455c067e27ff1551 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 15 17:29:52 2016 +0100 clean MultithreadedInitializationTest(s) commit 9d7ad8152b142d122b8b993d50183b7b87c87bc6 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 14 22:41:34 2016 +0100 set version 1.7.20-SNAPSHOT commit 227f986525ce611069e7bf7f8cc300149002b9b2 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Mar 14 22:30:49 2016 +0100 fix SLF4J-361 commit f7c83932a4590de50944534cc609138064bfc9d8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 8 18:03:58 2016 +0100 typo fix commit b37cde09bf0c8787024c664eee0c7fd288eadf82 Merge: 06eb9226 aef1ff54 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Mar 3 17:12:42 2016 +0100 Merge pull request #145 from oreissig/update-junit update junit 4.10 -> 4.12 commit aef1ff545be8b4d03fbdcb418f6f9cb26448e341 Author: Oliver Reissig <o.reissig@intershop.de> Date: Mon Feb 29 10:15:58 2016 +0100 update junit 4.10 -> 4.12 commit 06eb9226f3a82273bfc6fa6548e7957bba7a5d5b Merge: df2a37d3 36614f76 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 1 01:23:24 2016 +0100 Merge branch 'master' of github.com:qos-ch/slf4j commit df2a37d333b2796e7c158d0410027f1fc33de14b Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Mar 1 01:23:08 2016 +0100 remove Jigloo license header commit 36614f76a3e152b2edb9c8c14fc6ae2be0d86dda Merge: 3c031c14 9ebc3fa2 Author: Ceki Gulcu <ceki@qos.ch> Date: Mon Feb 29 10:29:54 2016 +0100 Merge pull request #144 from oreissig/fix-scm-url fix scm url commit 9ebc3fa2bf6086aa55780181ccb2726d623f517d Author: Oliver Reissig <o.reissig@intershop.de> Date: Mon Feb 29 10:14:25 2016 +0100 fix scm url commit 3c031c14b9e7bcc8c8dfcc09e2192b58c66281a4 Merge: 7b62d948 343e0a8e Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Feb 28 20:35:51 2016 +0100 Merge pull request #143 from motlin/master Fix problems in Javadoc references. commit 343e0a8ef48793a42685fc0c69e75a18a2c01e91 Author: Craig P. Motlin <craig.motlin@gs.com> Date: Tue Feb 23 15:42:27 2016 -0500 Fix problems in Javadoc references. commit 7b62d9485ea04c79204ad6343c64f0e340588d9d Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Feb 27 00:29:13 2016 +0100 add blurn on SLF4J-358 and 359 commit 4b43a8009b399be521dd03c097c8ae07f2c4902e Author: Ceki Gulcu <ceki@qos.ch> Date: Sat Feb 27 00:04:46 2016 +0100 make MultithreadedInitializationTest more robust commit 94f513997fc99552be3a804236700046a13c6837 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 23:27:20 2016 +0100 fix test failure commit 961da6ad23d49e9a4be69c5c5b26d1fec4dc3a1c Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 23:18:50 2016 +0100 ongoing work on SLF4J-359 commit f7b7eed4873dd6074bd07ab3e3693568eebc2e30 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 23:04:10 2016 +0100 ongoing work on SLF4J-359 commit 5f90edad8d15ac40a1213f9364c9a76442444f00 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 22:25:36 2016 +0100 fix SLF4J-359 by piggybacking on LoggerFactory thread safety commit 111b8e581e247b33bb2fe66bd0118399e0b49a90 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 22:03:38 2016 +0100 fix SLF4J-358 by piggybacking on LoggerFactory thread safety commit 78c02f08b03f35b550d550cc0d7ff925da64c7d8 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 20:20:45 2016 +0100 set version to 1.7.19-SNAPSHOT commit c25881c13e4905a14817ce13a2a9a3819183f791 Merge: ed2903d0 8bf2d64b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 19:47:54 2016 +0100 Merge branch 'master' of github.com:qos-ch/slf4j commit ed2903d00b938780a4cd85d91e97be9cb2f83d96 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 19:47:31 2016 +0100 preparing release 1.7.18 commit 8bf2d64b6dad0120281f015b19784da5984f9d08 Merge: f2ae5e39 c314069d Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 26 19:37:41 2016 +0100 Merge pull request #142 from msebire/master SLF4J-357 Fix improper Import-Package for slf4j-log4j12 commit c314069d3cea70b894935dfbbebbb482c6c106e1 Author: Mathieu SEBIRE <msebire@users.noreply.github.com> Date: Fri Feb 26 16:46:10 2016 +0100 SLF4J-357 Fix improper Import-Package for slf4j-log4j12 commit f2ae5e39cdc27340eb018150d70dc2a5dfc47595 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 25 23:50:51 2016 +0100 docs on java.lang.NoClassDefFoundError: org/slf4j/event/LoggingEvent commit 207351051d8d821c30ff17e4ae63df074423bedb Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Feb 24 16:53:22 2016 +0100 applied formatter commit ac099e427eb18fda3b48e9947b514fb75565fe4d Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Feb 21 23:15:12 2016 +0100 fix SLF4J-356 by piggybacking on LoggerFactory thread safety commit c2f1cc61a07c7e1853635993b643ee1bf9520a2f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 19 14:12:01 2016 +0100 typo fix commit 17e1201e79fce0aa38c99b65bce34d9753e03da1 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 19 14:10:13 2016 +0100 set version as 1.7.18-SNAPSHOT commit b732747165d93215358019e36d5598b4fb25d7c8 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 19 14:02:21 2016 +0100 prepare release 1.7.17 commit 51ccd9a444c1338ec01c95f7cec7483975730889 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 19 14:00:40 2016 +0100 blurb on android fix commit 5a95202d93c6994d845aebf4d2712de8c29f889b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Feb 19 13:53:10 2016 +0100 effectively skip binding ambiguity check under Android SLF4J-328 commit 6420cfa9b55de27b7b1c3899b622bbc8f0dd4f9a Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 11 22:26:43 2016 +0100 send travis notification to a different email address commit 46395b27a3fb15e660fd8bf3d1c41522f7bbb527 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 11 21:46:43 2016 +0100 next release is 1.7.17 commit cdc7773e8e02d4cc34c3dc3461831bc280c5dbb9 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Feb 11 21:27:51 2016 +0100 FIX SLF4J-354, prepare release 1.7.16 commit 5c2959ec3aadedc75d0075224632a46a9a0d435d Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Feb 10 15:15:48 2016 +0100 add PSI probe, remove bitronix commit d0bd3641370bc9fb5d67485745944fa855e1935f Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 18:22:07 2016 +0100 set version as 1.7.16-SNAPSHOT commit 31c509e9a6fdc6902b531b62ec556e3fa757228e Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 17:31:40 2016 +0100 release 1.7.15 commit d2e89fa99d8b725c5710a67b712ea89089a41ba8 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 17:28:09 2016 +0100 minor edits commit 2f5d369d67f2532bff5ff7cafcc050318641c222 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 16:50:08 2016 +0100 faster tests commit 0151ac3aeb3058b5bed89dd88296652511a68dff Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 16:45:35 2016 +0100 fix tests commit 2d4074c65ab9bcd6f7e745d98bd0597146914464 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 9 16:34:46 2016 +0100 testing SLF4J-353 support commit c3751df9afec9b412de6f888a97397af67063717 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Feb 2 21:45:35 2016 +0100 add event recording support SLF4J-353 commit 12697364d0a5506821557fff50594ed0a3b7d977 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 24 22:01:39 2016 +0100 next version is 1.7.15 commit 6b7721b507e0d609d20cb4dfc7e7084b95cc231d Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 24 21:45:50 2016 +0100 add blurb on SLF4J-341 commit 12a35307b665e55688de7c1713d41cf3a69c0984 Author: Ceki Gulcu <ceki@qos.ch> Date: Sun Jan 24 21:21:14 2016 +0100 prepare release 1.7.14 commit fc0ad8652b8485175a6295648c05425284b8619a Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jan 22 13:20:35 2016 +0100 fix SLF4J-328 commit 638d74d2b31591bd5d9d7a0cb1297a1120ec86c6 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jan 22 12:51:10 2016 +0100 blurb about SLF4J-167 commit 039df718381c45a0bd454c875b20b5b638e8741c Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Jan 22 11:02:52 2016 +0100 minnor edits and improvements commit ea3cca72cd5a9329a06b788317a17e806ee8acd0 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 21 19:37:07 2016 +0100 fix SLF4J-347 commit 36209914a29ebf3a475c5c7c7e823006ce66e162 Merge: dac5171d cb7f03af Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Jan 21 17:15:15 2016 +0100 Merge branch 'master' of github.com:qos-ch/slf4j commit cb7f03af9c461b5732f0b30ec2e414aa2776dece Merge: 9c8046d9 3e749c3d Author: Matt Bishop <matt@thebishops.org> Date: Sat Jan 9 17:52:30 2016 -0800 Merge pull request #130 from qos-ch/slf4j-341 Replaced maven-bundle-plugin with jar manifest template commit dac5171d96256f6033913e4263590ef289604928 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 15 20:59:26 2015 +0100 better docs, minor changes commit 9c8046d9fe9610ff81ad266bccbd11b96f150ccf Merge: 96d32b3b dbe2d727 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Dec 15 20:31:54 2015 +0100 Merge pull request #134 from forsel/slf4j-345 SLF4J-345: Move delegation check loop from log4j-over-slf4j.jar to slf4j-log4j12.jar commit dbe2d7271939a2e7f3197fd4ca5ce399e563dd31 Author: Frans Orsel <frans.orsel@klm.com> Date: Tue Dec 15 17:26:35 2015 +0100 Fix ordering of import and static variable/method commit 7a23ca74ae94f87675b25414d6c67a9e9ba9d98f Author: Frans Orsel <frans.orsel@klm.com> Date: Tue Dec 15 17:11:48 2015 +0100 Move delegation loop check from log4j-over-slf4j.jar to slf4j-log4j12.jar, see also SLF4J-345 commit 3e749c3d6f5a4d74e31f49bd50956f3dbe3add76 Author: Matt Bishop <matt@thebishops.org> Date: Tue Dec 8 15:29:27 2015 -0800 Set framework version requirement commit 6c461383d568611c27be92eb2e0167dc3b50e9bf Author: Matt Bishop <matt@thebishops.org> Date: Sat Dec 5 21:13:41 2015 -0800 Add Bundle-Category entry. Remove unnecessary Export-Package entry. commit a4c645d18874ae7568a7ca8788ddd43bcfa67e27 Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 3 19:31:23 2015 +0100 revert REQUESTED_API_VERSION to 1.6.99 commit 96d32b3b6603e75aa4c92496a59b111f8dbda5eb Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Dec 3 19:31:23 2015 +0100 revert REQUESTED_API_VERSION to 1.6.99 commit ae2029fae55e08ebf0cd3826c3c1b78342b6e4ae Author: Matt Bishop <matt@thebishops.org> Date: Tue Dec 1 15:09:29 2015 -0800 Replaced maven-bundle-plugin with jar manifest template. Picks up build-helper-maven-plugin config correctly. commit c5ae9916681574e782a1bd7e4a0838109519e10d Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 13 19:15:19 2015 +0100 update REQUESTED_API_VERSION to 1.7.x, as 1.6.x and 1.7.x are binary compatible this change should have no effect commit b4f20e193bd209b3f8b9791e0709a92dd2082864 Author: Ceki Gulcu <ceki@qos.ch> Date: Wed Nov 11 23:12:25 2015 +0100 prepare for next version snapshot commit fc84778ffe721edafe6863ceb5407133fc2c285c Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Nov 10 22:02:33 2015 +0100 releasing 1.7.3 commit 46a49f4303b770f285fc0e73cb7ab9dfae887943 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Nov 10 20:35:17 2015 +0100 SLF4J-324: lazy initializaiton of ClassContextSecurityManager in o.s.helpers.Util commit 37229d8d62198bff31072f2a38e2d57ecdadc483 Author: Ceki Gulcu <ceki@qos.ch> Date: Tue Nov 10 19:54:10 2015 +0100 fix SLF4J-324 commit c41df923f2ec31c635ad9c4dd71d68f23ff5fbd4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 6 17:43:14 2015 +0100 fixing SLF4J-337 commit 715615cd36f020d840de9d93edfc6532a3201a94 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 6 15:19:09 2015 +0100 correct line numbering commit acfc07008bb89952ce77c3a6eabbeaa6220566f5 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 6 14:38:39 2015 +0100 migrate test to Junit 4 conventions commit 18e6156c09bb6da8e9d8bcfa36ae2491e9361814 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 6 13:10:07 2015 +0100 minor edits, code formatting commit fd5d546503b1b7ba3d865382da2a0dbda0c13cb3 Merge: 52fcbbe8 32783459 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Nov 6 13:01:11 2015 +0100 Merge pull request #99 from lukecwik/master Fixed BasicMDCAdapter leaks MDC information to non-child threads commit 52fcbbe855fbd89942bf0cb450301471851b386f Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 21:03:02 2015 +0200 minor update to news.html commit 572dabfa7c0a7d7bb2e381bda6e2ad92b086bb6b Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 20:05:15 2015 +0200 less in MANIFEST.MF commit 91aa1de92b0ce7fd5b5cd86d38c09aa9b91ea237 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 13:40:56 2015 +0200 define and use value where it is needed commit b3de4f127bc9cc3ba275b8b79aec9c1216f1e930 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 13:35:17 2015 +0200 removed animal-sniffer from execution during the test phase commit 4feb697f446158d5d9cd9b8649c2ea5a6c1bf9cd Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 13:31:12 2015 +0200 added comment on why not to pass arguments to JUL commit 5ec3e30cbf1884d587ae51a928f1611fcbc1c062 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 11:55:35 2015 +0200 Revert "Pass arguments to JUL as record parameters" This reverts commit 2a21579335d746989f60b46434cd71768a73092b. Reasons explained in comments to pull request 97 commit 014780fde9660511f67cf9cace0d9511bcfab475 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 11:41:01 2015 +0200 Revert "Unit test update for JUL record parameters" This reverts commit 5e3eebc08d9ef4eaeb035db175d54d96a07358c2. Reasons explained in comments to pull request 97. commit f29c85d0adae7e74fc829c9efe550a54bc58f8a1 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Oct 16 11:40:33 2015 +0200 updated to news.html commit 3bdcd7f7327e7a9b3a5e833a6066ba852ace469a Author: Ceki Gulcu <ceki@qos.ch> Date: Thu Oct 15 17:40:08 2015 +0200 reverting commit 7371d14010d1 dated 2015-04-11 due to issues with the maven-eclipse-plugin commit 32783459528cc64ad1253c641bc1d03155801399 Merge: 26e7a4f0 2b23d26b Author: Luke Cwik <lcwik@google.com> Date: Mon Jul 6 09:22:37 2015 -0700 Merge remote-tracking branch 'upstream/master' Fix merge conflict in BasicMDCAdapter.java commit 2b23d26bb008b9eec151cc8244deec3bb4eed778 Merge: 3b369ef6 85d506b3 Author: Matt Bishop <matt@thebishops.org> Date: Thu Jul 2 15:02:08 2015 -0700 Merge pull request #110 from panchenko/SLF4J-218 SLF4J-218 removed org.apache.log4j.spi.Layout should be without "spi" commit 3b369ef6cfc6395ad4786438b57fb9e42f04ac6c Merge: d8139b0e a0454e35 Author: Matt Bishop <matt@thebishops.org> Date: Wed Jun 3 10:18:02 2015 -0700 Merge pull request #119 from SvenBunge/removeLegacyJava Use Java5 features and remove legacy code commit a0454e35356ade7ec1ff681711db1b7557efb028 Author: Sven Bunge <sven.bunge@holisticon.de> Date: Tue Jun 2 22:51:27 2015 +0200 Remove JDK1.4 legacy check and use more Java5 features (for-each, String#contains, typed collections doesn't need casts) commit d8139b0ecf7d067181e310255a8359ba38acb45d Merge: 4dcada51 0d01426f Author: Matt Bishop <matt@thebishops.org> Date: Tue May 12 06:32:10 2015 -0700 Merge pull request #117 from hazendaz/master Move MANIFEST build to Parent commit 4dcada51bddd9286b65a320993f057660f93f29d Merge: 8caa2ed1 a6027b3c Author: Matt Bishop <matt@thebishops.org> Date: Mon May 11 17:24:26 2015 -0700 Merge pull request #105 from jmthibault79/jmthibault79-patch-1 Update comments to point to JIRA equivalents of old Bugzilla bugs commit 0d01426fb6c75e11768f1ad404cf49cce6af910f Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:40:47 2015 -0400 Add resources directory to site pages commit 9c8a2b7cd0aa6cc2d833b3e768b5c726ab2cfacc Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Tue Apr 7 22:52:01 2015 -0400 Move MANIFEST build to Parent Add two empty manifest files for integration and slf4j-site Remove all pieces of manifest building on jar that can be in parent commit 26e7a4f0bfa1c5b9f68c763b78f5abd1c88d4b4a Merge: 734c5e44 8caa2ed1 Author: Luke Cwik <lcwik@google.com> Date: Thu Apr 30 13:32:33 2015 -0700 Merge remote-tracking branch 'upstream/master' Resolved formatting changes for BasicMDCAdapater.java commit a6027b3ce8873b3b4e7682b39b73d4add7e62c9e Author: jmthibault79 <thibault@broadinstitute.org> Date: Fri Apr 3 13:09:25 2015 -0400 Update comments from old Bugzilla to new JIRA commit 8caa2ed1045f5483e9b3aa9e7e9b65b4f3b3f576 Merge: 10c170c9 9a267a64 Author: Matt Bishop <matt@thebishops.org> Date: Thu Apr 30 10:06:25 2015 -0700 Merge pull request #116 from hazendaz/master Minor Sonar Corrections. 3 cheers for Sonar! commit 9a267a648dce42c93edfcf954d396b0dc4b883fc Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:44:17 2015 -0400 Avoid using underscore for method names commit eb4e1b8f483860da8bff0784458dff0790efc4aa Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:44:00 2015 -0400 Per sonar, move array indicator to the type rather than property name. commit 10c170c92773ad7e42b610cf7b30b4ef059c241d Merge: 8cd6d3e3 5b52c710 Author: Matt Bishop <matt@thebishops.org> Date: Wed Apr 29 10:07:01 2015 -0700 Merge pull request #107 from hazendaz/master Added Animal Sniffer to police interface changes. commit 5b52c710e984bb6b821fdfeb6ab4e64eca747531 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Fri Apr 10 20:41:55 2015 -0400 Add animal sniffer plugin Due to some signatures in slf4j-api has some ignores because signatures cannot be determined and will error otherwise. This is isolated to interfaces and code that shouldn't otherwise be present in usage per various javadocs around these. commit 8cd6d3e37ad51b6dbb216ac4d1ed3ab70d94884b Merge: 94a6b8cc 5e3eebc0 Author: Matt Bishop <matt@thebishops.org> Date: Mon Apr 27 19:22:12 2015 -0700 Merge pull request #97 from bnorm/master Pass arguments to JUL as record parameters commit 5e3eebc08d9ef4eaeb035db175d54d96a07358c2 Author: Brian Norman <brian.e.norman@gmail.com> Date: Mon Jan 19 18:59:23 2015 -0600 Unit test update for JUL record parameters commit 2a21579335d746989f60b46434cd71768a73092b Author: Brian Norman <brian.e.norman@gmail.com> Date: Thu Jan 15 22:27:18 2015 -0600 Pass arguments to JUL as record parameters commit 94a6b8cc1c614e0bc1a13c2ea2658324c717e081 Merge: 68b6f8b9 f4d67771 Author: Matt Bishop <matt@thebishops.org> Date: Fri Apr 24 14:01:42 2015 -0700 Merge pull request #113 from mciezadlo/patch-1 Added Category.assertLog(boolean, String) commit f4d6777117296107c866a73e80316a901ededce1 Author: mciezadlo <mciezadlo@poczta.onet.pl> Date: Wed Apr 22 13:53:36 2015 +0200 Update Category.java Added missing method from log4j Category class, which is quite useful and can be easily implemented. (Found it when using library which called this method so I received NoSuchMethodError) commit 85d506b3026be3a3122ff907606225b84a5e0d14 Author: Alex Panchenko <alex.panchenko@gmail.com> Date: Thu Apr 16 00:35:32 2015 +0600 SLF4J-218 removed org.apache.log4j.spi.Layout should be without "spi" commit d6e34cd57c90700aed723631bf390760cc34b752 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Fri Apr 10 20:37:58 2015 -0400 Update compiler plugin Use latest maven compiler version commit 7371d14010d1be21f0a9ca4659c00c621d40ff8f Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Fri Apr 10 20:35:50 2015 -0400 simplify site build directory location using ${project.basedir} changes the location of target from 'slf4j-site/target/site' to start right in 'slf4j-site' so it only needs to go back once. This finalizes usage of project.basedir throughout. commit dade4c08dffce507910232091b6f538bbf6f6b1e Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:41:50 2015 -0400 Correct modelVersion location commit 66f85cff91d9ead312bd796682297f7aafc594b3 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:39:34 2015 -0400 Use project.basedir where appropriate in poms. commit 38d675838cec71065730e001eeb9ba48f8638712 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:38:37 2015 -0400 Set Additional Resources as UTF-8 Set build resource encoding and reporting output encoding to UTF-8. commit 68b6f8b95fb30a80008b3ce48e982857c18d46d4 Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 10 18:34:37 2015 +0200 update news.html with info on SLF4J-309 commit 6972f3e530a9653489004811b3de1ef373d0863e Author: Dimitrios Liapis <dimitrisli@gmail.com> Date: Thu Apr 9 01:14:18 2015 +0100 SLF4J-309 Adding getAdditivity() method to log4j Category with same signature SLF4J-309 Adding getAdditivity() method to log4j Category with same signature commit 4b4515a1ca60d3194cd62a91ba4d5a8426417f22 Author: Dimitris <dimitrisli@gmail.com> Date: Thu Apr 9 00:46:29 2015 +0100 SLF4J-312 Eliminating one stack frame by using AbstractStringBuilder#append(str,start,end). A bit more readable compared to inlined String#substring(start,end). commit 489862dc4853b037a92b4746c51845c12d2fbaef Author: Ceki Gulcu <ceki@qos.ch> Date: Fri Apr 10 18:16:04 2015 +0200 explicitly set the compiler souce/target commit 734c5e441080f98aa86af4a50f25a683370a25c8 Author: Luke Cwik <lcwik@google.com> Date: Thu Apr 9 16:35:18 2015 -0700 Rename Map -> map based upon mattbishop comment for https://github.com/qos-ch/slf4j/pull/99 commit 95a6f46ebae7e39b94bd0323c5359df427bcb045 Author: Luke Cwik <lcwik@google.com> Date: Tue Apr 7 15:37:31 2015 -0700 Removed Google Copyright. commit 58f018d4e0607bc661df34fbfab7e4fa9bb7e595 Merge: f5cc8f20 2cae64b2 Author: Matt Bishop <matt@thebishops.org> Date: Mon Apr 6 14:39:07 2015 -0700 Merge pull request #106 from hazendaz/master Set Java 5 in parent and remove elsewhere commit 2cae64b236c439dae423d140ee26195a6ba23f4f Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:36:17 2015 -0400 Set Java 5 in parent and remove elsewhere parent can fully control this. Also no need to add separate configuration as this uses native maven settings to control java versions. commit f5cc8f20fa393dfa6661ba997c1dd27ad7921896 Merge: 2cd94e0a 6f5ab20a Author: Matt Bishop <matt@thebishops.org> Date: Fri Apr 3 14:45:42 2015 -0700 Merge pull request #104 from hazendaz/master Format Poms - no changes in build commit 6f5ab20a78093d4104a62704628e035d5191bcfe Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Thu Apr 2 22:23:12 2015 -0400 Remove empty or commented out elements from poms commit 9be0269b7a031cb8682bd4a18b11e0f951619d14 Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Tue Mar 31 22:34:33 2015 -0400 Format Poms - no changes in build commit 2cd94e0a7350f9e11e56557656c1277465c0f60c Merge: 7122d7eb 06c0e168 Author: Matt Bishop <matt@thebishops.org> Date: Wed Apr 1 21:14:28 2015 -0700 Merge pull request #103 from hazendaz/master Add xml version / encoding utf-8 to poms and format project tag commit 06c0e1680783f7b592b495d30aa0816f34f5ee1c Author: Jeremy Landis <jeremylandis@hotmail.com> Date: Tue Mar 31 22:19:09 2015 -0400 Add xml version / encoding utf-8 to poms and format project tag commit 22ef2008ec109617d15353e6c8eb47ffcb61cdaa Author: Luke Cwik <lcwik@google.com> Date: Tue Jan 27 15:41:43 2015 -0800 Fix bug: http://bugzilla.slf4j.org/show_bug.cgi?id=325 BasicMDCAdapter leaks MDC information to non-child threads BasicMDCAdapter uses a ConcurrentHashMap which is passed by reference from the parent to the child. All child threads then share the same map reference and any modifications by one child is visible to the parent thread and also all other child threads. Swapped to creating a copy of the parents map instead of storing reference. Also, since this is expected to be only accessed from within the same thread, swapped to use a hash map instead of a concurrent hash map. Signed-off-by: Luke Cwik <lcwik@google.com> Change-Id: Id11e57b3fd65d7a3b7d30e143033a5ed3984f241
-rw-r--r--.github/FUNDING.yml2
-rw-r--r--.github/workflows/main.yml47
-rw-r--r--.github/workflows/toolchains.xml12
-rwxr-xr-x.idea/codeStyleSettings.xml4
-rwxr-xr-x.travis.yml19
-rw-r--r--Android.bp2
-rw-r--r--FUNDING.yml1
-rw-r--r--LICENSE.txt2
-rw-r--r--METADATA12
-rw-r--r--README.md72
-rw-r--r--SECURITY.md69
-rw-r--r--binderVersion.pl42
-rw-r--r--goVersion.sh7
-rwxr-xr-x[-rw-r--r--]integration/build.xml114
-rw-r--r--integration/lib/slf4j-simple-1.5.4-SNAPSHOT.jarbin7472 -> 0 bytes
-rwxr-xr-x[-rw-r--r--]integration/osgi-build.xml36
-rwxr-xr-xintegration/pom.xml54
-rw-r--r--integration/src/IBUNDLE-META-INF/MANIFEST.MF2
-rw-r--r--integration/src/policy/java-eclipse.policy10
-rw-r--r--integration/src/policy/java-under-ant.policy13
-rw-r--r--integration/src/test/java/org/slf4j/CompatibilityAssertionTest.java23
-rw-r--r--integration/src/test/java/org/slf4j/IncompatibleMultiBindingAssertionTest.java24
-rw-r--r--integration/src/test/java/org/slf4j/MissingSingletonMethodAssertionTest.java83
-rw-r--r--integration/src/test/java/org/slf4j/MultiBindingAssertionTest.java30
-rw-r--r--integration/src/test/java/org/slf4j/NoProviderAssertionTest.java (renamed from slf4j-ext/src/test/java/org/slf4j/dummyExt/MDCStrLookupTest.java)41
-rw-r--r--integration/src/test/java/org/slf4j/OldAPIVersionMismatchAssertionTest.java (renamed from integration/src/test/java/org/slf4j/VersionMismatchAssertionTest.java)23
-rwxr-xr-xintegration/src/test/java/org/slf4j/OutputVerifier.java54
-rw-r--r--integration/src/test/java/org/slf4j/StringPrintStream.java2
-rw-r--r--integration/src/test/java/org/slf4j/issues/Issue324Test.java16
-rw-r--r--integration/src/test/java/org/slf4j/test_osgi/CheckingBundleListener.java10
-rw-r--r--integration/src/test/java/org/slf4j/test_osgi/FelixHost.java10
-rw-r--r--integration/src/test/java/org/slf4j/test_osgi/FrameworkErrorListener.java8
-rwxr-xr-xjcl-over-slf4j/pom.xml53
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/Log.java64
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogConfigurationException.java2
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogFactory.java46
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/NoOpLog.java2
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLocationAwareLog.java52
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLog.java4
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLogFactory.java22
-rw-r--r--jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SimpleLog.java85
-rwxr-xr-xjcl-over-slf4j/src/main/java/org/apache/commons/logging/package.html2
-rwxr-xr-xjcl-over-slf4j/src/main/java9/module-info.java4
-rw-r--r--jcl-over-slf4j/src/main/resources/META-INF/MANIFEST.MF9
-rw-r--r--jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/InvokeJCLTest.java (renamed from jcl-over-slf4j/src/test/java/org/apache/commons/logging/InvokeJCLTest.java)69
-rw-r--r--jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/SerializationTest.java (renamed from jcl-over-slf4j/src/test/java/org/apache/commons/logging/impl/SerializationTest.java)28
-rw-r--r--jul-to-slf4j/LICENSE.txt (renamed from slf4j-android/LICENSE.txt)2
-rwxr-xr-xjul-to-slf4j/pom.xml38
-rwxr-xr-xjul-to-slf4j/src/main/java/org/slf4j/bridge/SLF4JBridgeHandler.java76
-rw-r--r--jul-to-slf4j/src/main/java/org/slf4j/bridge/package.html2
-rw-r--r--jul-to-slf4j/src/main/java9/module-info.java7
-rw-r--r--jul-to-slf4j/src/main/resources/META-INF/MANIFEST.MF7
-rw-r--r--jul-to-slf4j/src/test/java/org/slf4j/bridge/ListAppender.java2
-rw-r--r--jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerPerfTest.java28
-rwxr-xr-xjul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerTest.java85
-rw-r--r--log4j-over-slf4j/LICENSE.txt176
-rw-r--r--log4j-over-slf4j/compatibility/build.xml2
-rw-r--r--log4j-over-slf4j/compatibility/readme.txt4
-rwxr-xr-xlog4j-over-slf4j/pom.xml44
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Appender.java9
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Category.java86
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/ConsoleAppender.java12
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Layout.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Level.java122
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Log4jLoggerFactory.java20
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/LogManager.java9
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Logger.java14
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/MDC.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/PatternLayout.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/Priority.java65
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/PropertyConfigurator.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/RollingFileAppender.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/helpers/LogLog.java18
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Configurator.java5
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/spi/HierarchyEventListener.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Layout.java20
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerFactory.java2
-rw-r--r--log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerRepository.java4
-rwxr-xr-xlog4j-over-slf4j/src/main/java9/module-info.java8
-rw-r--r--log4j-over-slf4j/src/main/resources/META-INF/MANIFEST.MF8
-rw-r--r--log4j-over-slf4j/src/test/java/org/apache/log4j/test/NDCTest.java (renamed from log4j-over-slf4j/src/test/java/org/apache/log4j/NDCTest.java)19
-rw-r--r--log4j-over-slf4j/src/test/java/org/apache/log4j/test/Trivial.java (renamed from log4j-over-slf4j/src/test/java/org/apache/log4j/Trivial.java)2
-rw-r--r--log4j-over-slf4j/src/test/java/org/dummy/Bug131.java8
-rw-r--r--log4j-over-slf4j/src/test/java/org/dummy/Bug139.java8
-rw-r--r--log4j-over-slf4j/src/test/java/org/dummy/ListHandler.java2
-rw-r--r--osgi-over-slf4j/LICENSE.txt (renamed from slf4j-jcl/LICENSE.txt)2
-rwxr-xr-xosgi-over-slf4j/pom.xml17
-rw-r--r--parent/pom.xml397
-rwxr-xr-xpom.xml439
-rwxr-xr-xrelease.sh61
-rwxr-xr-xslf4j-android/.gitignore2
-rwxr-xr-xslf4j-android/AndroidManifest.xml7
-rw-r--r--slf4j-android/pom.xml63
-rwxr-xr-xslf4j-android/project.properties14
-rwxr-xr-xslf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerAdapter.java553
-rwxr-xr-xslf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerFactory.java124
-rw-r--r--slf4j-android/src/main/java/org/slf4j/impl/StaticLoggerBinder.java81
-rw-r--r--slf4j-android/src/main/java/org/slf4j/impl/StaticMDCBinder.java58
-rw-r--r--slf4j-android/src/main/java/org/slf4j/impl/StaticMarkerBinder.java67
-rw-r--r--slf4j-android/src/main/resources/META-INF/MANIFEST.MF9
-rw-r--r--slf4j-android/src/test/java/org/slf4j/impl/AndroidLoggerFactoryTest.java79
-rw-r--r--slf4j-api/LICENSE.txt2
-rwxr-xr-xslf4j-api/pom.xml55
-rw-r--r--slf4j-api/src/main/java/org/slf4j/ILoggerFactory.java2
-rw-r--r--slf4j-api/src/main/java/org/slf4j/Logger.java236
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/LoggerFactory.java467
-rwxr-xr-x[-rw-r--r--]slf4j-api/src/main/java/org/slf4j/LoggerFactoryFriend.java (renamed from slf4j-jcl/src/main/java/org/slf4j/impl/StaticMDCBinder.java)41
-rw-r--r--slf4j-api/src/main/java/org/slf4j/MDC.java94
-rw-r--r--slf4j-api/src/main/java/org/slf4j/Marker.java25
-rw-r--r--slf4j-api/src/main/java/org/slf4j/MarkerFactory.java27
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/DefaultLoggingEvent.java140
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/EventConstants.java13
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/EventRecordingLogger.java84
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/KeyValuePair.java32
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/Level.java56
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/LoggingEvent.java45
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/event/SubstituteLoggingEvent.java115
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/AbstractLogger.java423
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/BasicMDCAdapter.java95
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/BasicMarker.java61
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/BasicMarkerFactory.java2
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/CheckReturnValue.java30
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/FormattingTuple.java22
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/LegacyAbstractLogger.java39
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/MarkerIgnoringBase.java1
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/MessageFormatter.java134
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/NOPLogger.java225
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/NOPLoggerFactory.java3
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/NOPMDCAdapter.java18
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/NOP_FallbackServiceProvider.java47
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/NamedLoggerBase.java5
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/NormalizedParameters.java116
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/Reporter.java181
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLogger.java291
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/SubstituteLoggerFactory.java37
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/SubstituteServiceProvider.java41
-rw-r--r--slf4j-api/src/main/java/org/slf4j/helpers/ThreadLocalMapOfStacks.java89
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/helpers/Util.java64
-rw-r--r--slf4j-api/src/main/java/org/slf4j/impl/StaticLoggerBinder.java73
-rw-r--r--slf4j-api/src/main/java/org/slf4j/impl/StaticMDCBinder.java57
-rw-r--r--slf4j-api/src/main/java/org/slf4j/impl/StaticMarkerBinder.java70
-rw-r--r--slf4j-api/src/main/java/org/slf4j/impl/package.html17
-rw-r--r--slf4j-api/src/main/java/org/slf4j/package.html2
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/CallerBoundaryAware.java25
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/spi/DefaultLoggingEventBuilder.java246
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/LocationAwareLogger.java7
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/LoggerFactoryBinder.java5
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/LoggingEventAware.java23
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/spi/LoggingEventBuilder.java169
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/MDCAdapter.java46
-rw-r--r--slf4j-api/src/main/java/org/slf4j/spi/MarkerFactoryBinder.java5
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/spi/NOPLoggingEventBuilder.java100
-rwxr-xr-xslf4j-api/src/main/java/org/slf4j/spi/SLF4JServiceProvider.java60
-rwxr-xr-xslf4j-api/src/main/java9/module-info.java8
-rw-r--r--slf4j-api/src/main/resources/META-INF/MANIFEST.MF8
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/LoggerAccessingThread.java62
-rw-r--r--slf4j-api/src/test/java/org/slf4j/LoggerFactoryTest.java91
-rw-r--r--slf4j-api/src/test/java/org/slf4j/basicTests/BasicMarkerTest.java (renamed from slf4j-api/src/test/java/org/slf4j/BasicMarkerTest.java)22
-rw-r--r--slf4j-api/src/test/java/org/slf4j/basicTests/Differentiator.java (renamed from slf4j-api/src/test/java/org/slf4j/Differentiator.java)2
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/basicTests/DoubleCheckedInt.java141
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/basicTests/FluentAPIUsage.java27
-rw-r--r--slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingMultithreadedInitializationTest.java (renamed from slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMDCBinder.java)43
-rw-r--r--slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingTest.java (renamed from slf4j-api/src/test/java/org/slf4j/NoBindingTest.java)18
-rw-r--r--slf4j-api/src/test/java/org/slf4j/eventTest/EventRecordingLoggerTest.java531
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/helpers/BasicMDCAdapterTest.java17
-rw-r--r--slf4j-api/src/test/java/org/slf4j/helpers/BogoPerf.java150
-rw-r--r--slf4j-api/src/test/java/org/slf4j/helpers/BubbleSortTest.java100
-rw-r--r--slf4j-api/src/test/java/org/slf4j/helpers/MDCAdapterTestBase.java147
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterPerfTest.java111
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterTest.java37
-rw-r--r--slf4j-api/src/test/java/org/slf4j/helpers/MyRandom.java51
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/helpers/StringPrintStream.java74
-rw-r--r--slf4j-api/src/test/java/org/slf4j/helpers/SubstitutableLoggerTest.java81
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/helpers/SubstituteLoggerFactoryTest.java21
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/rule/BlaTest.java38
-rwxr-xr-x[-rw-r--r--]slf4j-api/src/test/java/org/slf4j/rule/RunInNewThread.java (renamed from slf4j-api/src/test/java/org/slf4j/helpers/BubbleSort.java)36
-rwxr-xr-x[-rw-r--r--]slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadRule.java (renamed from slf4j-ext/src/main/java/org/slf4j/ext/MDCStrLookup.java)47
-rwxr-xr-xslf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadStatement.java68
-rw-r--r--slf4j-api/src/test/java/org/slf4j/testHarness/MultithreadedInitializationTest.java79
-rw-r--r--slf4j-ext/LICENSE.txt (renamed from slf4j-site/LICENSE.txt)2
-rwxr-xr-xslf4j-ext/pom.xml57
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/NDC.java2
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/agent/AgentOptions.java4
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java27
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/agent/package.html5
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/cal10n/LocLogger.java2
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/cal10n/LocLoggerFactory.java22
-rwxr-xr-xslf4j-ext/src/main/java/org/slf4j/ext/EventData.java305
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/ext/EventException.java66
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/ext/LoggerWrapper.java97
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/ext/XLogger.java29
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java10
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java49
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/instrumentation/ToStringHelper.java6
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/instrumentation/package.html2
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/profiler/Profiler.java6
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/profiler/ProfilerRegistry.java4
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/profiler/StopWatch.java2
-rw-r--r--slf4j-ext/src/main/java/org/slf4j/profiler/TimeInstrument.java4
-rw-r--r--slf4j-ext/src/main/resources/META-INF/MANIFEST.MF8
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/NDCTest.java18
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/LocLoggerTest.java20
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/PackageTest.java14
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/dummyExt/EventLoggerTest.java106
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/dummyExt/ListAppender.java2
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/dummyExt/PackageTest.java16
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/dummyExt/XLoggerTest.java57
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/instrumentation/ToStringHelperTest.java7
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/profiler/PackageTest.java14
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/profiler/ProfilerTest.java14
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/profiler/SortAndPruneComposites.java4
-rw-r--r--slf4j-ext/src/test/java/org/slf4j/profiler/UtilTest.java17
-rwxr-xr-xslf4j-jcl/pom.xml53
-rw-r--r--slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerAdapter.java531
-rw-r--r--slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerFactory.java83
-rw-r--r--slf4j-jcl/src/main/java/org/slf4j/impl/StaticLoggerBinder.java82
-rw-r--r--slf4j-jcl/src/main/java/org/slf4j/impl/StaticMarkerBinder.java67
-rw-r--r--slf4j-jcl/src/main/resources/META-INF/MANIFEST.MF10
-rw-r--r--slf4j-jcl/src/test/java/org/slf4j/InvocationTest.java125
-rw-r--r--slf4j-jdk-platform-logging/LICENSE.txt24
-rw-r--r--slf4j-jdk-platform-logging/pom.xml85
-rw-r--r--slf4j-jdk-platform-logging/src/main/java/module-info.java28
-rw-r--r--slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLogger.java181
-rw-r--r--[-rwxr-xr-x]slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLoggerFactory.java (renamed from slf4j-ext/src/main/java/org/slf4j/ext/EventLogger.java)53
-rw-r--r--slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JSystemLoggerFinder.java59
-rw-r--r--slf4j-jdk-platform-logging/src/main/resources/META-INF/services/java.lang.System$LoggerFinder1
-rw-r--r--slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/SLF4JPlatformLoggingTest.java119
-rw-r--r--slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/StringPrintStream.java67
-rw-r--r--slf4j-jdk14/LICENSE.txt2
-rwxr-xr-xslf4j-jdk14/pom.xml41
-rwxr-xr-xslf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerAdapter.java651
-rw-r--r--slf4j-jdk14/src/main/java/org/slf4j/impl/StaticLoggerBinder.java80
-rw-r--r--slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMDCBinder.java58
-rw-r--r--slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMarkerBinder.java67
-rwxr-xr-xslf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerAdapter.java298
-rw-r--r--slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerFactory.java (renamed from slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerFactory.java)15
-rwxr-xr-xslf4j-jdk14/src/main/java/org/slf4j/jul/JULServiceProvider.java48
-rwxr-xr-xslf4j-jdk14/src/main/java9/module-info.java9
-rw-r--r--slf4j-jdk14/src/main/resources/META-INF/MANIFEST.MF9
-rwxr-xr-xslf4j-jdk14/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider1
-rw-r--r--slf4j-jdk14/src/test/java/org/slf4j/impl/PerfTest.java76
-rwxr-xr-xslf4j-jdk14/src/test/java/org/slf4j/issue/CallerInfoTest.java122
-rw-r--r--slf4j-jdk14/src/test/java/org/slf4j/issue/LoggerSerializationTest.java15
-rw-r--r--slf4j-jdk14/src/test/java/org/slf4j/jul/CountingHandler.java24
-rwxr-xr-xslf4j-jdk14/src/test/java/org/slf4j/jul/FluentApiInvocationTest.java144
-rwxr-xr-xslf4j-jdk14/src/test/java/org/slf4j/jul/InvocationTest.java (renamed from slf4j-jdk14/src/test/java/org/slf4j/InvocationTest.java)52
-rw-r--r--slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14AdapterLoggerNameTest.java (renamed from slf4j-jdk14/src/test/java/org/slf4j/impl/JDK14AdapterLoggerNameTest.java)53
-rw-r--r--slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14MultithreadedInitializationTest.java77
-rwxr-xr-xslf4j-jdk14/src/test/java/org/slf4j/jul/ListHandler.java23
-rw-r--r--slf4j-log4j12/LICENSE.txt2
-rwxr-xr-xslf4j-log4j12/pom.xml57
-rwxr-xr-xslf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerAdapter.java598
-rw-r--r--slf4j-log4j12/src/main/java/org/slf4j/impl/StaticLoggerBinder.java88
-rw-r--r--slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMarkerBinder.java67
-rw-r--r--slf4j-log4j12/src/main/resources/META-INF/MANIFEST.MF9
-rw-r--r--slf4j-migrator/LICENSE.txt24
-rwxr-xr-xslf4j-migrator/pom.xml27
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/FileSelector.java6
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/InplaceFileConverter.java4
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/Main.java10
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/ProjectConverter.java27
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/helper/Abbreviator.java4
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/internal/MigratorFrame.java28
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/line/EmptyRuleSet.java2
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/line/JCLRuleSet.java4
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/line/JULRuleSet.java4
-rwxr-xr-xslf4j-migrator/src/main/java/org/slf4j/migrator/line/Log4jRuleSet.java4
-rw-r--r--slf4j-migrator/src/main/java/org/slf4j/migrator/line/MultiGroupConversionRule.java4
-rw-r--r--slf4j-migrator/src/main/resources/META-INF/MANIFEST.MF1
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/AternativeApproach.java8
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/FileConverterTest.java24
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/ProjectConverterTest.java10
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/helper/AbbreviatorTest.java24
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/helper/RandomHelper.java2
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/line/JCLRuleSetTest.java12
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/line/NoConversionTest.java10
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcher.java12
-rw-r--r--slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcherTest.java7
-rw-r--r--slf4j-nop/LICENSE.txt2
-rwxr-xr-xslf4j-nop/pom.xml42
-rw-r--r--slf4j-nop/src/main/java/org/slf4j/impl/StaticLoggerBinder.java80
-rw-r--r--slf4j-nop/src/main/java/org/slf4j/impl/StaticMDCBinder.java56
-rw-r--r--slf4j-nop/src/main/java/org/slf4j/impl/StaticMarkerBinder.java67
-rwxr-xr-xslf4j-nop/src/main/java/org/slf4j/nop/NOPServiceProvider.java46
-rwxr-xr-xslf4j-nop/src/main/java9/module-info.java7
-rw-r--r--slf4j-nop/src/main/resources/META-INF/MANIFEST.MF9
-rwxr-xr-xslf4j-nop/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider1
-rw-r--r--slf4j-nop/src/test/java/org/slf4j/nop/InvocationTest.java (renamed from slf4j-nop/src/test/java/org/slf4j/InvocationTest.java)41
-rwxr-xr-xslf4j-nop/src/test/java/org/slf4j/nop/MultithreadedInitializationTest.java150
-rw-r--r--slf4j-reload4j/LICENSE.txt24
-rw-r--r--slf4j-reload4j/pom.xml71
-rw-r--r--slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerAdapter.java213
-rw-r--r--slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerFactory.java (renamed from slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerFactory.java)33
-rw-r--r--slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jMDCAdapter.java (renamed from slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jMDCAdapter.java)57
-rw-r--r--slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jServiceProvider.java62
-rw-r--r--slf4j-reload4j/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider1
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/EventFieldsTest.java61
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/InvocationTest.java (renamed from slf4j-log4j12/src/test/java/org/slf4j/InvocationTest.java)74
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/ListAppender.java (renamed from slf4j-log4j12/src/test/java/org/slf4j/ListAppender.java)4
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/RecursiveInitializationTest.java (renamed from slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveInitializationTest.java)25
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMDCAdapterTest.java39
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMultithreadedInitializationTest.java72
-rw-r--r--slf4j-reload4j/src/test/java/org/slf4j/reload4j/testHarness/RecursiveAppender.java (renamed from slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveAppender.java)44
-rw-r--r--slf4j-reload4j/src/test/resources/eventFields.properties4
-rw-r--r--slf4j-reload4j/src/test/resources/recursiveInit.properties (renamed from slf4j-log4j12/src/test/resources/recursiveInit.properties)5
-rw-r--r--slf4j-reload4j/src/test/resources/recursiveInitWithActivationDelay.properties9
-rw-r--r--slf4j-simple/LICENSE.txt2
-rwxr-xr-xslf4j-simple/pom.xml46
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/impl/SimpleLogger.java648
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/impl/StaticLoggerBinder.java81
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/impl/StaticMDCBinder.java56
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/impl/StaticMarkerBinder.java68
-rwxr-xr-xslf4j-simple/src/main/java/org/slf4j/simple/OutputChoice.java55
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/simple/SimpleLogger.java475
-rwxr-xr-xslf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerConfiguration.java193
-rw-r--r--slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerFactory.java (renamed from slf4j-simple/src/main/java/org/slf4j/impl/SimpleLoggerFactory.java)32
-rwxr-xr-xslf4j-simple/src/main/java/org/slf4j/simple/SimpleServiceProvider.java50
-rwxr-xr-xslf4j-simple/src/main/java9/module-info.java6
-rw-r--r--slf4j-simple/src/main/resources/META-INF/MANIFEST.MF10
-rwxr-xr-xslf4j-simple/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider1
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/impl/SimpleLoggerTest.java78
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/AcceptanceTest.java50
-rwxr-xr-xslf4j-simple/src/test/java/org/slf4j/simple/DetectLoggerNameMismatchTest.java (renamed from slf4j-simple/src/test/java/org/slf4j/DetectLoggerNameMismatchTest.java)18
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/DoubleInitializationPitfallTest.java37
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/InvocationTest.java (renamed from slf4j-simple/src/test/java/org/slf4j/InvocationTest.java)46
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/LoggerTestSuite.java274
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/SilentPrintStream.java (renamed from slf4j-simple/src/test/java/org/slf4j/SilentPrintStream.java)2
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerMultithreadedInitializationTest.java73
-rw-r--r--slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerTest.java152
-rwxr-xr-xslf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/MultithereadedExecutionTest.java131
-rwxr-xr-xslf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/StateCheckingPrintStream.java140
-rwxr-xr-xslf4j-site/pom.xml43
-rw-r--r--slf4j-site/src/site/images.src/bindings.flwbin7661 -> 0 bytes
-rwxr-xr-xslf4j-site/src/site/images.src/bridging-black.flwbin5751 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/bridging.flwbin5579 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/concrete-bindings.odgbin19544 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/core-bindings.flwbin4568 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/core-bindings1.flwbin4479 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/core-bindings2.flwbin4458 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/core-bindings3.flwbin4554 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/follow_us.odgbin8824 -> 0 bytes
-rw-r--r--slf4j-site/src/site/images.src/legacy.odgbin26372 -> 0 bytes
-rw-r--r--slf4j-site/src/site/pages/.htaccess1
-rwxr-xr-xslf4j-site/src/site/pages/bug-reporting.html90
-rw-r--r--slf4j-site/src/site/pages/changes/changes-1.3.txt45
-rwxr-xr-xslf4j-site/src/site/pages/codes.html483
-rwxr-xr-xslf4j-site/src/site/pages/compatibility.html269
-rw-r--r--slf4j-site/src/site/pages/css/popup.css67
-rw-r--r--slf4j-site/src/site/pages/css/prettify.css29
-rwxr-xr-xslf4j-site/src/site/pages/css/site.css449
-rw-r--r--slf4j-site/src/site/pages/docs.html153
-rw-r--r--slf4j-site/src/site/pages/download.html123
-rwxr-xr-xslf4j-site/src/site/pages/extensions.html886
-rwxr-xr-xslf4j-site/src/site/pages/faq.html1615
-rw-r--r--slf4j-site/src/site/pages/inde_base.html28
-rwxr-xr-xslf4j-site/src/site/pages/index.html170
-rw-r--r--slf4j-site/src/site/pages/js/decorator.js101
-rw-r--r--slf4j-site/src/site/pages/js/jquery-min.js4
-rw-r--r--slf4j-site/src/site/pages/js/prettify.js23
-rwxr-xr-xslf4j-site/src/site/pages/legacy.html267
-rw-r--r--slf4j-site/src/site/pages/license.html68
-rwxr-xr-xslf4j-site/src/site/pages/localization.html158
-rwxr-xr-xslf4j-site/src/site/pages/mailing-lists.html128
-rwxr-xr-xslf4j-site/src/site/pages/manual.html539
-rwxr-xr-xslf4j-site/src/site/pages/migrator.html226
-rwxr-xr-xslf4j-site/src/site/pages/news.html1638
-rw-r--r--slf4j-site/src/site/pages/support.html43
-rwxr-xr-xslf4j-site/src/site/pages/templates/footer.js28
-rw-r--r--slf4j-site/src/site/pages/templates/header.js12
-rwxr-xr-xslf4j-site/src/site/pages/templates/left.js59
-rw-r--r--slf4j-site/src/site/pages/templates/right.js1
-rw-r--r--slf4j-site/src/site/resources/css/anchor12.pngbin624 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/css/anchor16.pngbin945 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/css/anchor20.pngbin1269 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/css/anchor24.pngbin1685 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/PythonPowered.pngbin945 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/beginnerSLF4J.pngbin106458 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/bindings.pngbin51523 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/bridging.pngbin35850 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/buyDirect.jpgbin24142 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/concrete-bindings.pngbin82592 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/devoxx09.jpegbin12634 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/follow_us.pngbin16337 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/gnu-head-tiny.jpgbin3049 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/jazoon09.gifbin1338 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/legacy.pngbin180307 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/logos/qosLogo.pngbin3370 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/logos/qoslogo.gifbin2743 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/logos/slf4j-logo.jpgbin32793 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/logos/slf4j-small.jpgbin17838 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/logos/valid-html401.pngbin2404 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/mailman.jpgbin2022 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/myjob.pngbin2468 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/slf4j-migrator.gifbin15512 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/twitter-bird-light-bgs.pngbin4392 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/images/twitter.pngbin1847 -> 0 bytes
-rw-r--r--slf4j-site/src/site/resources/slf4j-in-10-slides.pptbin240128 -> 0 bytes
-rwxr-xr-xsrc/main/assembly/source.xml342
-rw-r--r--test0
-rw-r--r--version.pl44
400 files changed, 11466 insertions, 16657 deletions
diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml
new file mode 100644
index 00000000..b87dccda
--- /dev/null
+++ b/.github/FUNDING.yml
@@ -0,0 +1,2 @@
+tidelift: maven/org.slf4j:slf4j-api
+github: qos-ch \ No newline at end of file
diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml
new file mode 100644
index 00000000..faa5af5b
--- /dev/null
+++ b/.github/workflows/main.yml
@@ -0,0 +1,47 @@
+name: CI
+
+on:
+ push:
+ branches:
+ - '*'
+ pull_request:
+ branches:
+ - '*'
+
+# https://help.github.com/en/actions/automating-your-workflow-with-github-actions/software-installed-on-github-hosted-runners
+
+concurrency:
+ # On master/release, we don't want any jobs cancelled so the sha is used to name the group
+ # On PR branches, we cancel the job if new commits are pushed
+ # More info: https://stackoverflow.com/a/68422069/253468
+ group: ${{ (github.ref == 'refs/heads/branch_1.2.18' || github.ref == 'refs/heads/main' || github.ref == 'refs/heads/release' ) && format('ci-main-{0}', github.sha) || format('ci-main-{0}', github.ref) }}
+ cancel-in-progress: true
+
+permissions:
+ contents: read
+
+jobs:
+ Test:
+ name: JDK ${{ matrix.jdk }}, ${{ matrix.os }}
+ runs-on: ${{ matrix.os }}
+ strategy:
+ matrix:
+ jdk: [11, 17, 19]
+ os: [ubuntu-latest, windows-latest, macos-latest]
+ fail-fast: true
+ max-parallel: 4
+ steps:
+ - uses: actions/checkout@v3
+ with:
+ fetch-depth: 50
+ - name: Set up Java ${{ matrix.jdk }}
+ if: ${{ matrix.jdk != '8' }}
+ uses: actions/setup-java@v3
+ with:
+ distribution: 'temurin'
+ java-version: ${{ matrix.jdk }}
+ - name: Install
+ # download dependencies, etc, so test log looks better
+ run: mvn -B install
+
+
diff --git a/.github/workflows/toolchains.xml b/.github/workflows/toolchains.xml
new file mode 100644
index 00000000..e75a4d31
--- /dev/null
+++ b/.github/workflows/toolchains.xml
@@ -0,0 +1,12 @@
+<?xml version="1.0" encoding="UTF8"?>
+<toolchains>
+ <toolchain>
+ <type>jdk</type>
+ <provides>
+ <version>1.8</version>
+ </provides>
+ <configuration>
+ <jdkHome>${env.JAVA_HOME_8}</jdkHome>
+ </configuration>
+ </toolchain>
+</toolchains>
diff --git a/.idea/codeStyleSettings.xml b/.idea/codeStyleSettings.xml
index 31cb3222..3507c0b8 100755
--- a/.idea/codeStyleSettings.xml
+++ b/.idea/codeStyleSettings.xml
@@ -31,8 +31,8 @@
<option name="KEEP_SIMPLE_CLASSES_IN_ONE_LINE" value="true" />
<option name="KEEP_MULTIPLE_EXPRESSIONS_IN_ONE_LINE" value="true" />
<indentOptions>
- <option name="INDENT_SIZE" value="2" />
- <option name="TAB_SIZE" value="2" />
+ <option name="INDENT_SIZE" value="4" />
+ <option name="TAB_SIZE" value="4" />
</indentOptions>
</codeStyleSettings>
<codeStyleSettings language="XML">
diff --git a/.travis.yml b/.travis.yml
index 49af9f15..2f8e805e 100755
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,4 +1,21 @@
+dist: trusty
+
language: java
+
+jdk:
+ - oraclejdk11
+
notifications:
email:
- - slf4j-dev@qos.ch
+ - notification@qos.ch
+
+install: /bin/true
+
+script:
+ - mvn clean
+ - mvn install
+
+cache:
+ directories:
+ - $HOME/.m2
+ \ No newline at end of file
diff --git a/Android.bp b/Android.bp
index db9ce707..8b05e6e7 100644
--- a/Android.bp
+++ b/Android.bp
@@ -58,7 +58,7 @@ java_library {
host_supported: true,
hostdex: true,
srcs: [
- "slf4j-api/src/main/**/*.java",
+ "slf4j-api/src/main/java/**/*.java",
"slf4j-jdk14/src/main/java/**/*.java",
],
exclude_srcs: [
diff --git a/FUNDING.yml b/FUNDING.yml
new file mode 100644
index 00000000..18dbb116
--- /dev/null
+++ b/FUNDING.yml
@@ -0,0 +1 @@
+github: qos-ch \ No newline at end of file
diff --git a/LICENSE.txt b/LICENSE.txt
index 43112bc7..1a3d0532 100644
--- a/LICENSE.txt
+++ b/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2014 QOS.ch
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/METADATA b/METADATA
index 7ae255df..b509b128 100644
--- a/METADATA
+++ b/METADATA
@@ -1,4 +1,16 @@
+name: "slf4j"
+description:
+ "Simple Logging Facade for Java"
+
third_party {
+ homepage: "https://github.com/qos-ch/slf4j"
+ identifier {
+ type: "Git"
+ value: "https://github.com/qos-ch/slf4j.git"
+ primary_source: true
+ }
+ version: "v_2.0.12"
+ last_upgrade_date { year: 2024 month: 2 day: 16 }
license_note: "would be NOTICE save for:\n"
" log4j-over-slf4j/compatibility/src/main/java/test/Log4j12Calls.java\n"
" log4j-over-slf4j/compatibility/src/main/java/test/Log4j13Calls.java"
diff --git a/README.md b/README.md
index 69663535..6d2e395c 100644
--- a/README.md
+++ b/README.md
@@ -1,14 +1,70 @@
# About SLF4J
-The Simple Logging Facade for Java (SLF4J) serves as a simple facade or abstraction for various logging frameworks (e.g. java.util.logging, logback, log4j) allowing the end user to plug in the desired logging framework at deployment time.
+
+The Simple Logging Facade for Java (SLF4J) serves as a simple facade
+or abstraction for various logging frameworks (e.g. java.util.logging,
+logback, reload4j, log4j 2.x) allowing the end user to plug in the desired logging
+framework at deployment time.
+
More information can be found on the [SLF4J website](http://www.slf4j.org).
+
# Build Status
-[![Build Status](https://travis-ci.org/qos-ch/slf4j.png)](https://travis-ci.org/qos-ch/slf4j)
+[![Build Status](https://travis-ci.org/qos-ch/slf4j.svg)](https://travis-ci.org/qos-ch/slf4j)
+
+# Search org.slf4j artifacts on Maven Central
+[![Maven Central](https://img.shields.io/badge/Search%20org%2Eslf4j%20artifacts%20on%20Maven%20Central-2.0.x-green)](https://search.maven.org/search?q=g:org.slf4j%20AND%20v:2.0.%3F)
+
+
+# In case of problems
+
+In case of problems please do not hesitate to post an e-mail message
+on the slf4j-user@qos.ch mailing list. However, please do not
+directly e-mail SLF4J developers. The answer to your question might
+be useful to other users. Moreover, there are many knowledgeable users
+on the slf4j-user mailing lists who can quickly answer your
+questions.
+
+# Urgent issues
+
+For urgent issues do not hesitate to [champion a release](https://github.com/sponsors/qos-ch/sponsorships?tier_id=77436).
+In principle, most championed issues are solved within 3 business days ensued by a release.
+
+# How to build SLF4J
+
+SLF4J uses Maven as its build tool.
+
+SLF4J version 2.0.x will run under Java 8 but requires Java 9 or later to build.
# How to contribute pull requests
-If you are interested in improving SLF4J, great! The SLF4J community looks forward to your contribution. Please follow this process:
-1. Start a discussion on the [slf4j-dev mailing list](http://www.slf4j.org/mailing-lists.html) about your proposed change. Alternately file a [bug report](http://www.slf4j.org/bug-reporting.html).
-2. Fork qos-ch/slf4j. Ideally, create a new branch from your fork for your contribution to make it easier to merge your changes back.
-3. Make your changes on the branch you hopefuly created in Step 2. Be sure that your code passes existing unit tests. Please add unit tests for your work if appropriate. It usually is.
-4. Push your changes to your fork/branch in github. Don't push it to your master! If you do it will make it harder to submit new changes later.
-5. Submit a pull request to SLF4J from from your commit page on github.
+If you are interested in improving SLF4J, that is great! The SLF4J
+community looks forward to your contribution. Please follow this
+process:
+
+1. Start a discussion on the [slf4j-dev mailing
+list](http://www.slf4j.org/mailing-lists.html) about your proposed
+change. Alternately, file a [bug
+report](http://www.slf4j.org/bug-reporting.html) to initiate the
+discussion. Note that we ask pull requests to be linked to a [Jira
+ticket](https://jira.qos.ch/).
+
+2. Fork qos-ch/slf4j. Ideally, create a new branch from your fork for
+your contribution to make it easier to merge your changes back.
+
+3. Make your changes on the branch you hopefully created in Step 2. Be
+sure that your code passes existing unit tests. Please add unit tests
+for your work if appropriate. It usually is.
+
+4. All commits must have signed off by the contributor attesting to
+[Developer Certificate of Origin
+(DCO)](https://developercertificate.org/). Commits without sign off
+will be automatically rejected by the [DCO GitHub
+check](https://probot.github.io/apps/dco/) application.
+
+5. Push your changes to your fork/branch in GitHub. Don't push it to
+your master! If you do it will make it harder to submit new changes
+later.
+
+6. Submit a pull request to SLF4J from your commit page on GitHub.
+
+7. Did we mention that you will be asked to link your pull request
+with a Jira ticket?
diff --git a/SECURITY.md b/SECURITY.md
new file mode 100644
index 00000000..9c361c27
--- /dev/null
+++ b/SECURITY.md
@@ -0,0 +1,69 @@
+
+## Reporting security issues
+
+Please report security issues related to the SLF4J project to the
+following email address:
+
+ support(at)qos.ch
+
+
+
+
+## Verifying contents
+
+All SLF4J project artifacts published on Maven central are signed. For
+each artifact, there is an associated signature file with the .asc
+suffix.
+
+### After 2022-08-08
+
+To verify the signature use [this public key](https://www.slf4j.org/public-keys/60200AC4AE761F1614D6C46766D68DAA073BE985.gpg). Here is its fingerprint:
+```
+pub nistp521 2022-08-08 [SC]
+ 60200AC4AE761F1614D6C46766D68DAA073BE985
+uid Ceki Gulcu <ceki@qos.ch>
+sub nistp521 2022-08-08 [E]
+```
+
+A copy of this key is stored on the
+[keys.openpgp.org](https://keys.openpgp.org) keyserver. To add it to
+your public key ring use the following command:
+
+```
+> FINGER_PRINT=60200AC4AE761F1614D6C46766D68DAA073BE985
+> gpg --keyserver hkps://keys.openpgp.org --recv-keys $FINGER_PRINT
+```
+
+### Before 2022-08-08
+
+To verify the signature use [this public key](https://www.slf4j.org/public-keys/ceki-public-key.pgp). Here is its fingerprint:
+
+```
+pub 2048R/A511E325 2012-04-26
+Key fingerprint = 475F 3B8E 59E6 E63A A780 6748 2C7B 12F2 A511 E325
+uid Ceki Gulcu <ceki@qos.ch>
+sub 2048R/7FBFA159 2012-04-26
+```
+
+A copy of this key is stored on the
+[keys.openpgp.org](https://keys.openpgp.org) keyserver. To add it to
+your public key ring use the following command:
+
+```
+> FINGER_PRINT=475F3B8E59E6E63AA78067482C7B12F2A511E325
+> gpg --keyserver hkps://keys.openpgp.org --recv-keys $FINGER_PRINT
+```
+
+
+## Preventing commit history overwrite
+
+In order to prevent loss of commit history, developers of the project
+are highly encouraged to deny branch deletions or history overwrites
+by invoking the following two commands on their local copy of the
+repository.
+
+
+```
+git config receive.denyDelete true
+git config receive.denyNonFastForwards true
+``` \ No newline at end of file
diff --git a/binderVersion.pl b/binderVersion.pl
deleted file mode 100644
index b5b32334..00000000
--- a/binderVersion.pl
+++ /dev/null
@@ -1,42 +0,0 @@
-
-if ($#ARGV < 1) {
- print "Usage: binderVersion.pl VER FILE {FILE, FILE}\n";
- exit;
-}
-
-$V= $ARGV[0];
-# Trim -SNAPSHOT
-$V =~ s/-SNAPSHOT//;
-
-print "VER:${V}\r\n";
-shift(@ARGV);
-
-sub replace () {
- my $filename = $_[0];
-
- if(-s $filename) {
- print "Processing [" . $filename . "]\r\n";
-
- my $original = "$filename.original";
-
- rename($filename, $original);
- open(OUT, ">$filename");
- open(IN, "$original");
-
- while(<IN>) {
- if(/VERSION\s+=\s+".*";/) {
- s/VERSION\s+=\s+".*";/VERSION = "${V}";/;
- }
- print OUT;
- }
- close(IN);
- close(OUT);
- unlink($original);
- } else {
- print "File [" . $filename . "] does not exist\r\n"
- }
-}
-
-foreach $ARG (@ARGV) {
- do replace($ARG);
-}
diff --git a/goVersion.sh b/goVersion.sh
deleted file mode 100644
index 77105f8b..00000000
--- a/goVersion.sh
+++ /dev/null
@@ -1,7 +0,0 @@
-VER=$1
-echo "Will use version '${VER}'"
-echo "Changing pom.xml files"
-find . -name "pom.xml" |xargs perl version.pl ${VER}
-echo "Changing Java files"
-find . -name "StaticLoggerBinder.java" |xargs perl binderVersion.pl ${VER}
-
diff --git a/integration/build.xml b/integration/build.xml
index d3a5d5ac..89ffc373 100644..100755
--- a/integration/build.xml
+++ b/integration/build.xml
@@ -13,13 +13,10 @@
<echo message="runtime classpath: ${runtime_classpath}" />
<echo message="test classpath: ${test_classpath}" />
<echo message="plugin classpath: ${plugin_classpath}" />
+ <echo message="basedir: ${basedir}" />
- <path id="path142Binding">
- <pathelement location="target/test-classes/" />
- <pathelement location="../slf4j-api/target/slf4j-api-${currentVersion}.jar" />
- <pathelement location="./lib/slf4j-simple-1.4.2.jar" />
- </path >
+ <!--<property name="path_to_policy" value="file:./integration/src/policy/java-under-ant.policy"/>-->
<path id="path150Binding">
<pathelement location="target/test-classes/" />
@@ -39,27 +36,12 @@
<pathelement location="./lib/slf4j-simple-1.5.11.jar" />
</path >
- <!--<path id="pathIncompatible">
- <pathelement location="target/test-classes/" />
- <pathelement location="../slf4j-api/target/slf4j-api-${currentVersion}.jar" />
- <pathelement location="./lib/slf4j-simple-INCOMPATIBLE.jar" />
- </path >
- -->
-
<path id="pathCurrent">
<pathelement location="target/test-classes/" />
<pathelement location="../slf4j-api/target/slf4j-api-${currentVersion}.jar" />
<pathelement location="../slf4j-simple/target/slf4j-simple-${currentVersion}.jar" />
</path >
-
- <path id="incompatibleMultiBinding">
- <pathelement location="target/test-classes/" />
- <pathelement location="../slf4j-api/target/slf4j-api-${currentVersion}.jar" />
- <pathelement location="./lib/slf4j-simple-1.5.0.jar" />
- <pathelement location="./lib/slf4j-nop-1.5.6.jar" />
- </path >
-
<path id="multiBinding">
<pathelement location="target/test-classes/" />
<pathelement location="../slf4j-api/target/slf4j-api-${currentVersion}.jar" />
@@ -90,54 +72,64 @@
<!-- this is really very ugly, but it's the only way to circumvent
http://jira.codehaus.org/browse/MANTRUN-95
-->
+ <!--
<taskdef name="junit" classpath="${plugin_classpath};${compile_classpath}"
classname="org.apache.tools.ant.taskdefs.optional.junit.JUnitTask" />
+ -->
<target name="init">
<mkdir dir="target/unit-reports" />
</target>
<target name="testAll" depends="init,
- testMissingSingletonMethod,
- testMismatch,
+ testNoProvider150,
+ testMismatch,
testMatch,
- testMultiBinding,
- testIncompatibleMultiBinding,
- testFuture_16Series">
+ testMultiBinding,
+ testFuture_16Series,
+ testActiveSecurityManager">
</target>
- <target name="testMissingSingletonMethod">
+ <target name="testNoProvider150">
- <junit printsummary="yes" fork="no" haltonfailure="yes">
- <classpath refid="path142Binding" />
+ <junit printsummary="yes" fork="no" haltonfailure="yes">
+ <classpath refid="path150Binding" />
<formatter type="plain" />
- <test fork="yes" todir="target/unit-reports"
- outfile="TEST-142BININDING"
- name="org.slf4j.MissingSingletonMethodAssertionTest" />
+ <test fork="yes" todir="target/unit-reports"
+ outfile="TEST-150BINDING"
+ name="org.slf4j.NoProviderAssertionTest" />
</junit>
+ </target>
+
+
+ <target name="testMixed17">
+
<junit printsummary="yes" fork="no" haltonfailure="yes">
- <classpath refid="path150Binding" />
+ <classpath refid="pathMixed17" />
<formatter type="plain" />
<test fork="yes" todir="target/unit-reports"
- outfile="TEST-150BINDING"
- name="org.slf4j.MissingSingletonMethodAssertionTest" />
+ outfile="TEST-MIXED-17"
+ name="org.slf4j.VersionMismatchAssertionTest" />
</junit>
-
</target>
+
<target name="testMismatch">
+ <!--
+
<junit printsummary="yes" fork="no" haltonfailure="yes">
<classpath refid="path1511API" />
<formatter type="plain" />
<test fork="yes" todir="target/unit-reports"
outfile="TEST-MISMATCH-1511API"
- name="org.slf4j.VersionMismatchAssertionTest" />
+ name="org.slf4j.OldAPIVersionMismatchAssertionTest" />
</junit>
+ -->
-
+ <!--
<junit printsummary="yes" fork="no" haltonfailure="yes">
<classpath refid="path1511Binding" />
<formatter type="plain" />
@@ -145,6 +137,7 @@
outfile="TEST-MISMATCH-1511Binding"
name="org.slf4j.VersionMismatchAssertionTest" />
</junit>
+ -->
</target>
@@ -156,16 +149,7 @@
outfile="TEST-Match"
name="org.slf4j.CompatibilityAssertionTest" />
</junit>
- </target>
- <target name="testIncompatibleMultiBinding">
- <junit printsummary="yes" fork="no" haltonfailure="yes">
- <classpath refid="incompatibleMultiBinding" />
- <formatter type="plain" />
- <test fork="yes" todir="target/unit-reports"
- outfile="TEST-IncompatibleMultiBinding"
- name="org.slf4j.IncompatibleMultiBindingAssertionTest" />
- </junit>
</target>
<target name="testMultiBinding">
@@ -178,13 +162,17 @@
</junit>
</target>
+
<target name="testFuture_16Series">
- <junit printsummary="yes" fork="no" haltonfailure="yes">
+
+ <!-- 1.8 uses providers and no longer supports bindings ==
+
+ <junit printsummary="yes" fork="no" haltonfailure="yes">
<classpath refid="binding166" />
<formatter type="plain" />
<test fork="yes" todir="target/unit-reports"
outfile="TEST-binding166"
- name="org.slf4j.CompatibilityAssertionTest" />
+ name="org.slf4j.NoProviderAssertionTest" />
</junit>
@@ -195,6 +183,36 @@
outfile="TEST-api166"
name="org.slf4j.CompatibilityAssertionTest" />
</junit>
+ -->
+ </target>
+
+
+ <condition property="runFromWithinIntegrationModule">
+ <contains string="${user.dir}" substring="integration" />
+ </condition>
+
+ <target name="setPathToPolicy_FromTop" unless="runFromWithinIntegrationModule">
+ <echo>setPathToPolicy_FromTop</echo>
+ <property name="path_to_policy" value="file:./integration/src/policy/java-under-ant.policy"/>
+ </target>
+
+ <target name="setPathToPolicy_FromIntegration" if="runFromWithinIntegrationModule">
+ <echo>setPathToPolicy_FromInegration </echo>
+ <property name="path_to_policy" value="file:./src/policy/java-under-ant.policy"/>
+ </target>
+
+ <target name="testActiveSecurityManager" depends="setPathToPolicy_FromTop, setPathToPolicy_FromIntegration">
+ <junit printsummary="yes" fork="no" haltonfailure="yes">
+ <jvmarg value="-Djava.security.manager"/>
+ <jvmarg value="-Djava.security.policy=${path_to_policy}"/>
+ <jvmarg value="-Dslf4j.detectLoggerNameMismatch=true"/>
+ <classpath refid="pathCurrent" />
+ <formatter type="plain" />
+ <test fork="yes" todir="target/unit-reports"
+ outfile="TEST-SecurityManager"
+ name="org.slf4j.issues.Issue324Test" />
+ </junit>
</target>
+
</project> \ No newline at end of file
diff --git a/integration/lib/slf4j-simple-1.5.4-SNAPSHOT.jar b/integration/lib/slf4j-simple-1.5.4-SNAPSHOT.jar
deleted file mode 100644
index ebae7cd0..00000000
--- a/integration/lib/slf4j-simple-1.5.4-SNAPSHOT.jar
+++ /dev/null
Binary files differ
diff --git a/integration/osgi-build.xml b/integration/osgi-build.xml
index 231c2faa..8d0c17ce 100644..100755
--- a/integration/osgi-build.xml
+++ b/integration/osgi-build.xml
@@ -13,15 +13,22 @@
<echo message="test classpath: ${test_classpath}" />
<echo message="basedir: ${basedir}" />
+ <echo message="ant.java.version: ${ant.java.version}" />
+
<property name="iBundleJar" value="target/iBundle.jar"/>
<property name="bundlesDir" value="bundle"/>
<!-- this is really very ugly, but it's the only way to circumvent
http://jira.codehaus.org/browse/MANTRUN-95
- -->
+
<taskdef name="junit" classpath="${test_classpath}"
classname="org.apache.tools.ant.taskdefs.optional.junit.JUnitTask" />
+ -->
+
+ <condition property="jdk9">
+ <matches pattern="9.*" string="${ant.java.version}" />
+ </condition>
<path id="minimal">
<pathelement location="target/test-classes/" />
@@ -59,34 +66,45 @@
<!-- for some reason if mvn is invoked from the parent directory, junit gets
- invoked from the parent dir, which messes up theses tests. Hence, the
+ invoked from the parent dir, which messes up these tests. Hence, the
fork="yes" dir="${basedir}" -->
- <target name="nop">
+<!--
+ <jvmarg line="MINUS_MINUSadd-opens java.base/java.net=ALL-UNNAMED"/>
+ <jvmarg line="MINUS_MINUSadd-opens java.base/java.security=ALL-UNNAMED"/>
+-->
+
+ <target name="nop" unless="jdk9">
<prepareOSGiHarness binding="nop"/>
<junit printsummary="yes" fork="yes" dir="${basedir}" haltonfailure="yes">
<classpath path="${test_classpath}"/>
<formatter type="plain" />
- <test fork="yes" todir="target/unit-reports" name="org.slf4j.test_osgi.BundleTest" />
+ <test todir="target/unit-reports"
+ name="org.slf4j.test_osgi.BundleTest"
+ outfile="OSGI-nop" />
</junit>
</target>
- <target name="simple">
+ <target name="simple" unless="jdk9">
<prepareOSGiHarness binding="simple"/>
<junit printsummary="yes" fork="yes" dir="${basedir}" haltonfailure="yes">
<classpath path="${test_classpath}"/>
<formatter type="plain" />
- <test fork="yes" todir="target/unit-reports" name="org.slf4j.test_osgi.BundleTest" />
+ <test fork="yes" todir="target/unit-reports"
+ name="org.slf4j.test_osgi.BundleTest"
+ outfile="OSGI-simple" />
</junit>
</target>
- <target name="jdk14">
+ <target name="jdk14" unless="jdk9">
<prepareOSGiHarness binding="jdk14"/>
<junit printsummary="yes" fork="yes" dir="${basedir}" haltonfailure="yes">
<classpath path="${test_classpath}"/>
<formatter type="plain" />
- <test fork="yes" todir="target/unit-reports" name="org.slf4j.test_osgi.BundleTest" />
+ <test fork="yes" todir="target/unit-reports"
+ name="org.slf4j.test_osgi.BundleTest"
+ outfile="OSGI-jdk14"/>
</junit>
</target>
-</project> \ No newline at end of file
+</project>
diff --git a/integration/pom.xml b/integration/pom.xml
index 3230dc2f..092d8423 100755
--- a/integration/pom.xml
+++ b/integration/pom.xml
@@ -1,17 +1,16 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
-
<artifactId>integration</artifactId>
<packaging>jar</packaging>
<name>SLF4J Integration tests</name>
@@ -19,6 +18,14 @@
<url>http://www.slf4j.org</url>
<description>SLF4J integration tests</description>
+ <properties>
+ <junit.version>4.10</junit.version>
+ <!-- 1.9.1 does not work. Do not update lightly -->
+ <ant-junit.version>1.9.0</ant-junit.version>
+ <antrun-plugin.version>1.8</antrun-plugin.version>
+ </properties>
+
+
<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
@@ -26,24 +33,28 @@
</dependency>
<!-- declaration to circumvent http://jira.codehaus.org/browse/MANTRUN-95 -->
+ <!--
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
- <version>3.8.1</version>
+ <version>${junit3.version}</version>
</dependency>
+ -->
<!-- declaration to circumvent http://jira.codehaus.org/browse/MANTRUN-95 -->
+ <!--
<dependency>
<groupId>ant</groupId>
<artifactId>ant-junit</artifactId>
- <version>1.6.5</version>
+ <version>${ant-junit.version}</version>
</dependency>
-
+ -->
<!-- some test run Felix in hosted mode -->
<dependency>
<groupId>org.apache.felix</groupId>
<artifactId>org.apache.felix.main</artifactId>
- <version>2.0.2</version>
+ <version>5.6.1</version>
+ <!--<version>2.0.2</version>-->
</dependency>
</dependencies>
@@ -51,17 +62,17 @@
<plugins>
<plugin>
<artifactId>maven-antrun-plugin</artifactId>
- <version>1.2</version>
+ <version>${antrun-plugin.version}</version>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
- <version>3.8.1</version>
+ <version>${junit.version}</version>
</dependency>
<dependency>
- <groupId>ant</groupId>
+ <groupId>org.apache.ant</groupId>
<artifactId>ant-junit</artifactId>
- <version>1.6.5</version>
+ <version>${ant-junit.version}</version>
</dependency>
</dependencies>
<executions>
@@ -82,6 +93,7 @@
<goal>run</goal>
</goals>
</execution>
+ <!-- OSGI integration with ServiceLoader mechanism fails at this stage
<execution>
<id>ant-osgi-test</id>
<phase>package</phase>
@@ -97,7 +109,7 @@
<goal>run</goal>
</goals>
</execution>
-
+ -->
</executions>
</plugin>
@@ -113,9 +125,19 @@
</excludes>
</configuration>
</plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+
+
</plugins>
</build>
-</project> \ No newline at end of file
+</project>
diff --git a/integration/src/IBUNDLE-META-INF/MANIFEST.MF b/integration/src/IBUNDLE-META-INF/MANIFEST.MF
index d518a2b6..cd0e0b21 100644
--- a/integration/src/IBUNDLE-META-INF/MANIFEST.MF
+++ b/integration/src/IBUNDLE-META-INF/MANIFEST.MF
@@ -10,6 +10,6 @@ Implementation-Title: iBundle
Bundle-ManifestVersion: 2
Bundle-SymbolicName: iBundle
Bundle-Name: abundle
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
+Bundle-RequiredExecutionEnvironment: JavaSE-1.8
Export-Package: apack
Import-Package: org.osgi.framework, org.slf4j;version=1.5 \ No newline at end of file
diff --git a/integration/src/policy/java-eclipse.policy b/integration/src/policy/java-eclipse.policy
new file mode 100644
index 00000000..9a42e4d1
--- /dev/null
+++ b/integration/src/policy/java-eclipse.policy
@@ -0,0 +1,10 @@
+
+grant {
+
+ // note that java.lang.RuntimePermission createSecurityManager is NOT granted
+
+ permission java.util.PropertyPermission "user.dir", "read";
+ permission java.util.PropertyPermission "*", "read";
+
+ permission java.net.SocketPermission "*", "connect,resolve";
+}; \ No newline at end of file
diff --git a/integration/src/policy/java-under-ant.policy b/integration/src/policy/java-under-ant.policy
new file mode 100644
index 00000000..41f7fcfb
--- /dev/null
+++ b/integration/src/policy/java-under-ant.policy
@@ -0,0 +1,13 @@
+
+grant {
+
+ // note that java.lang.RuntimePermission createSecurityManager is NOT granted
+
+ permission java.util.PropertyPermission "user.dir", "read";
+
+ // permissions required for Ant's Junit runner
+ permission java.util.PropertyPermission "*", "read, write";
+ permission java.io.FilePermission "./-", "read";
+ permission java.io.FilePermission "./-", "write";
+ permission java.lang.RuntimePermission "setIO";
+}; \ No newline at end of file
diff --git a/integration/src/test/java/org/slf4j/CompatibilityAssertionTest.java b/integration/src/test/java/org/slf4j/CompatibilityAssertionTest.java
index 021ef137..af804406 100644
--- a/integration/src/test/java/org/slf4j/CompatibilityAssertionTest.java
+++ b/integration/src/test/java/org/slf4j/CompatibilityAssertionTest.java
@@ -25,31 +25,33 @@
package org.slf4j;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
import java.io.PrintStream;
import java.util.Random;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class CompatibilityAssertionTest extends TestCase {
+public class CompatibilityAssertionTest {
StringPrintStream sps = new StringPrintStream(System.err);
PrintStream old = System.err;
int diff = 1024 + new Random().nextInt(10000);
- public CompatibilityAssertionTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
System.setErr(sps);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
System.setErr(old);
}
+ @Test
public void test() throws Exception {
Logger logger = LoggerFactory.getLogger(this.getClass());
String msg = "hello world " + diff;
@@ -57,5 +59,6 @@ public class CompatibilityAssertionTest extends TestCase {
assertEquals(1, sps.stringList.size());
String s0 = (String) sps.stringList.get(0);
assertTrue(s0.contains(msg));
+
}
}
diff --git a/integration/src/test/java/org/slf4j/IncompatibleMultiBindingAssertionTest.java b/integration/src/test/java/org/slf4j/IncompatibleMultiBindingAssertionTest.java
index 80c9b00e..c8fb4081 100644
--- a/integration/src/test/java/org/slf4j/IncompatibleMultiBindingAssertionTest.java
+++ b/integration/src/test/java/org/slf4j/IncompatibleMultiBindingAssertionTest.java
@@ -24,33 +24,35 @@
*/
package org.slf4j;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+
import java.io.PrintStream;
import java.util.List;
import java.util.Random;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class IncompatibleMultiBindingAssertionTest extends TestCase {
+public class IncompatibleMultiBindingAssertionTest {
StringPrintStream sps = new StringPrintStream(System.err);
PrintStream old = System.err;
int diff = 1024 + new Random().nextInt(10000);
- public IncompatibleMultiBindingAssertionTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
System.setErr(sps);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
System.setErr(old);
}
- public void test() throws Exception {
+ @Test
+ public void smoke() throws Exception {
try {
Logger logger = LoggerFactory.getLogger(this.getClass());
String msg = "hello world " + diff;
diff --git a/integration/src/test/java/org/slf4j/MissingSingletonMethodAssertionTest.java b/integration/src/test/java/org/slf4j/MissingSingletonMethodAssertionTest.java
deleted file mode 100644
index af678ccd..00000000
--- a/integration/src/test/java/org/slf4j/MissingSingletonMethodAssertionTest.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j;
-
-import java.io.PrintStream;
-import java.util.Random;
-
-import junit.framework.TestCase;
-
-public class MissingSingletonMethodAssertionTest extends TestCase {
-
- StringPrintStream sps = new StringPrintStream(System.err);
- PrintStream old = System.err;
- int diff = 1024 + new Random().nextInt(10000);
-
- public MissingSingletonMethodAssertionTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- System.setErr(sps);
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- System.setErr(old);
- }
-
- public void test() throws Exception {
- try {
- Logger logger = LoggerFactory.getLogger(this.getClass());
- String msg = "hello world " + diff;
- logger.info(msg);
- fail("NoSuchMethodError expected");
- } catch (NoSuchMethodError e) {
- }
-
- int lineCount = sps.stringList.size();
- assertTrue("number of lines should be 3 but was " + lineCount, lineCount == 3);
-
- // expected output:
- // SLF4J: slf4j-api 1.6.x (or later) is incompatible with this binding.
- // SLF4J: Your binding is version 1.4.x or earlier.
- // SLF4J: Upgrade your binding to version 1.6.x. or 2.0.x
-
- {
- String s = (String) sps.stringList.get(0);
- assertTrue(s.contains("SLF4J: slf4j-api 1.6.x (or later) is incompatible with this binding."));
- }
- {
- String s = (String) sps.stringList.get(1);
- assertTrue(s.contains("SLF4J: Your binding is version 1.5.5 or earlier."));
- }
- {
- String s = (String) sps.stringList.get(2);
- assertTrue(s.contains("SLF4J: Upgrade your binding to version 1.6.x."));
- }
-
- }
-}
diff --git a/integration/src/test/java/org/slf4j/MultiBindingAssertionTest.java b/integration/src/test/java/org/slf4j/MultiBindingAssertionTest.java
index 8d1cb598..052faab2 100644
--- a/integration/src/test/java/org/slf4j/MultiBindingAssertionTest.java
+++ b/integration/src/test/java/org/slf4j/MultiBindingAssertionTest.java
@@ -28,38 +28,38 @@ import java.io.PrintStream;
import java.util.List;
import java.util.Random;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import static org.junit.Assert.assertTrue;
-public class MultiBindingAssertionTest extends TestCase {
+public class MultiBindingAssertionTest {
StringPrintStream sps = new StringPrintStream(System.err);
PrintStream old = System.err;
int diff = 1024 + new Random().nextInt(10000);
- public MultiBindingAssertionTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
System.setErr(sps);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
System.setErr(old);
}
+ @Test
public void test() throws Exception {
Logger logger = LoggerFactory.getLogger(this.getClass());
String msg = "hello world " + diff;
logger.info(msg);
List<String> list = sps.stringList;
- assertMsgContains(list, 0, "Class path contains multiple SLF4J bindings.");
- assertMsgContains(list, 1, "Found binding in");
- assertMsgContains(list, 2, "Found binding in");
- assertMsgContains(list, 3, "See http://www.slf4j.org/codes.html");
- assertMsgContains(list, 4, "Actual binding is of type [");
+ assertMsgContains(list, 0, "Class path contains multiple SLF4J providers.");
+ assertMsgContains(list, 1, "Found provider");
+ assertMsgContains(list, 2, "Found provider");
+ assertMsgContains(list, 3, "See https://www.slf4j.org/codes.html#multiple_bindings for an explanation.");
+ assertMsgContains(list, 4, "Actual provider is of type [");
}
void assertMsgContains(List<String> strList, int index, String msg) {
diff --git a/slf4j-ext/src/test/java/org/slf4j/dummyExt/MDCStrLookupTest.java b/integration/src/test/java/org/slf4j/NoProviderAssertionTest.java
index 8544e7b3..7ee8baa8 100644
--- a/slf4j-ext/src/test/java/org/slf4j/dummyExt/MDCStrLookupTest.java
+++ b/integration/src/test/java/org/slf4j/NoProviderAssertionTest.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2016 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,35 +22,36 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.dummyExt;
+package org.slf4j;
-import junit.framework.TestCase;
+import java.io.PrintStream;
+import java.util.Random;
-import org.slf4j.MDC;
-import org.slf4j.ext.MDCStrLookup;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class MDCStrLookupTest extends TestCase {
+public class NoProviderAssertionTest {
- public MDCStrLookupTest(String name) {
- super(name);
- }
+ StringPrintStream sps = new StringPrintStream(System.err);
+ PrintStream old = System.err;
+ int diff = 1024 + new Random().nextInt(10000);
+ @Before
public void setUp() throws Exception {
- super.setUp();
+ System.setErr(sps);
}
+ @After
public void tearDown() throws Exception {
- super.tearDown();
+ System.setErr(old);
}
- public void testLookup() throws Exception {
- MDC.put("key", "value");
- MDC.put("number", "2");
- MDCStrLookup lookup = new MDCStrLookup();
- assertEquals("value", lookup.lookup("key"));
- assertEquals("2", lookup.lookup("number"));
- assertEquals(null, lookup.lookup(null));
- assertEquals(null, lookup.lookup(""));
- assertEquals(null, lookup.lookup("other"));
+ @Test
+ public void test() throws Exception {
+ Logger logger = LoggerFactory.getLogger(this.getClass());
+ String msg = "hello world " + diff;
+ logger.info(msg);
+ OutputVerifier.noProvider(sps);
}
}
diff --git a/integration/src/test/java/org/slf4j/VersionMismatchAssertionTest.java b/integration/src/test/java/org/slf4j/OldAPIVersionMismatchAssertionTest.java
index c6d90e03..0b67214c 100644
--- a/integration/src/test/java/org/slf4j/VersionMismatchAssertionTest.java
+++ b/integration/src/test/java/org/slf4j/OldAPIVersionMismatchAssertionTest.java
@@ -24,36 +24,39 @@
*/
package org.slf4j;
+import static org.junit.Assert.assertTrue;
+
import java.io.PrintStream;
import java.util.Random;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class VersionMismatchAssertionTest extends TestCase {
+public class OldAPIVersionMismatchAssertionTest {
StringPrintStream sps = new StringPrintStream(System.err);
PrintStream old = System.err;
int diff = 1024 + new Random().nextInt(10000);
- public VersionMismatchAssertionTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
System.setErr(sps);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
System.setErr(old);
}
+ @Test
public void test() throws Exception {
Logger logger = LoggerFactory.getLogger(this.getClass());
String msg = "hello world " + diff;
logger.info(msg);
+ OutputVerifier.dump(sps);
+
String s0 = (String) sps.stringList.get(0);
assertTrue(s0.matches("SLF4J: The requested version .* by your slf4j binding is not compatible with.*"));
diff --git a/integration/src/test/java/org/slf4j/OutputVerifier.java b/integration/src/test/java/org/slf4j/OutputVerifier.java
new file mode 100755
index 00000000..fbc71a15
--- /dev/null
+++ b/integration/src/test/java/org/slf4j/OutputVerifier.java
@@ -0,0 +1,54 @@
+package org.slf4j;
+
+import static junit.framework.Assert.assertTrue;
+
+public class OutputVerifier {
+
+ static void noProvider(StringPrintStream sps) {
+ dump(sps);
+ int lineCount = sps.stringList.size();
+ assertTrue("number of lines should be 6 but was " + lineCount, lineCount == 6);
+
+ // expected output: (version 1.8)
+ // SLF4J: No SLF4J providers were found.
+ // SLF4J: Defaulting to no-operation (NOP) logger implementation
+ // SLF4J: See http://www.slf4j.org/codes.html#noProviders for further details.
+ // SLF4J: Class path contains SLF4J bindings targeting slf4j-api versions prior to 1.8.
+ // SLF4J: Ignoring binding found at
+ // [jar:file:..../slf4j-simple-1.4.2.jar!/org/slf4j/impl/StaticLoggerBinder.class]
+ // SLF4J: See http://www.slf4j.org/codes.html#ignoredBindings for an explanation.
+
+ {
+ String s = (String) sps.stringList.get(0);
+ assertTrue(s.contains("No SLF4J providers were found."));
+ }
+ {
+ String s = (String) sps.stringList.get(1);
+ assertTrue(s.contains("Defaulting to no-operation (NOP) logger implementation"));
+ }
+ {
+ String s = (String) sps.stringList.get(2);
+ assertTrue(s.contains("See https://www.slf4j.org/codes.html#noProviders for further details."));
+ }
+
+ {
+ String s = (String) sps.stringList.get(3);
+ assertTrue(s.contains("Class path contains SLF4J bindings targeting slf4j-api versions 1.7.x or earlier."));
+ }
+
+ {
+ String s = (String) sps.stringList.get(4);
+ assertTrue(s.contains("Ignoring binding found at"));
+ }
+ {
+ String s = (String) sps.stringList.get(5);
+ assertTrue(s.contains("See https://www.slf4j.org/codes.html#ignoredBindings for an explanation"));
+ }
+ }
+
+ public static void dump(StringPrintStream sps) {
+ for (String s : sps.stringList) {
+ System.out.println(s);
+ }
+ }
+}
diff --git a/integration/src/test/java/org/slf4j/StringPrintStream.java b/integration/src/test/java/org/slf4j/StringPrintStream.java
index 200b745f..a26cb391 100644
--- a/integration/src/test/java/org/slf4j/StringPrintStream.java
+++ b/integration/src/test/java/org/slf4j/StringPrintStream.java
@@ -32,7 +32,7 @@ public class StringPrintStream extends PrintStream {
public static final String LINE_SEP = System.getProperty("line.separator");
PrintStream other;
- List<String> stringList = new ArrayList<String>();
+ List<String> stringList = new ArrayList<>();
public StringPrintStream(PrintStream ps) {
super(ps);
diff --git a/integration/src/test/java/org/slf4j/issues/Issue324Test.java b/integration/src/test/java/org/slf4j/issues/Issue324Test.java
new file mode 100644
index 00000000..9d3cf208
--- /dev/null
+++ b/integration/src/test/java/org/slf4j/issues/Issue324Test.java
@@ -0,0 +1,16 @@
+package org.slf4j.issues;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import junit.framework.TestCase;
+
+public class Issue324Test extends TestCase {
+
+ public void testLoggerCreationInPresenceOfSecurityManager() {
+ String currentDir = System.getProperty("user.dir");
+ System.out.println("currentDir:" + currentDir);
+ Logger logger = LoggerFactory.getLogger(Issue324Test.class);
+ logger.debug("hello");
+ }
+}
diff --git a/integration/src/test/java/org/slf4j/test_osgi/CheckingBundleListener.java b/integration/src/test/java/org/slf4j/test_osgi/CheckingBundleListener.java
index ef4a0349..bdbfdee8 100644
--- a/integration/src/test/java/org/slf4j/test_osgi/CheckingBundleListener.java
+++ b/integration/src/test/java/org/slf4j/test_osgi/CheckingBundleListener.java
@@ -33,7 +33,7 @@ import org.osgi.framework.BundleListener;
public class CheckingBundleListener implements BundleListener {
- List<BundleEvent> eventList = new ArrayList<BundleEvent>();
+ List<BundleEvent> eventList = new ArrayList<>();
public void bundleChanged(BundleEvent be) {
eventList.add(be);
@@ -45,16 +45,14 @@ public class CheckingBundleListener implements BundleListener {
}
public void dumpAll() {
- for (int i = 0; i < eventList.size(); i++) {
- BundleEvent fe = (BundleEvent) eventList.get(i);
+ for (BundleEvent fe : eventList) {
dump(fe);
}
}
boolean exists(String bundleName) {
- for (int i = 0; i < eventList.size(); i++) {
- BundleEvent fe = (BundleEvent) eventList.get(i);
- Bundle b = fe.getBundle();
+ for (BundleEvent bundleEvent : eventList) {
+ Bundle b = bundleEvent.getBundle();
System.out.println("===[" + b + "]");
if (bundleName.equals(b.getSymbolicName())) {
return true;
diff --git a/integration/src/test/java/org/slf4j/test_osgi/FelixHost.java b/integration/src/test/java/org/slf4j/test_osgi/FelixHost.java
index 204b8c23..10997055 100644
--- a/integration/src/test/java/org/slf4j/test_osgi/FelixHost.java
+++ b/integration/src/test/java/org/slf4j/test_osgi/FelixHost.java
@@ -41,7 +41,7 @@ import org.osgi.framework.Constants;
* Runs a hosted version of Felix for testing purposes. Any bundle errors are
* reported via the FrameworkListener passed to the constructor.
*
- * @author Ceki G&uuml;c&uuml;
+ * @author Ceki G&uuml;lc&uuml;
*/
public class FelixHost {
@@ -59,7 +59,7 @@ public class FelixHost {
public void doLaunch() {
// Create a case-insensitive configuration property map.
- StringMap configMap = new StringMap(false);
+ StringMap configMap = new StringMap();
// Configure the Felix instance to be embedded.
// configMap.put(FelixConstants.EMBEDDED_EXECUTION_PROP, "true");
// Add core OSGi packages to be exported from the class path
@@ -75,7 +75,7 @@ public class FelixHost {
try {
// Create host activator;
- List<Object> list = new ArrayList<Object>();
+ List<Object> list = new ArrayList<>();
// list.add(new HostActivator());
configMap.put(Constants.FRAMEWORK_SYSTEMPACKAGES_EXTRA, "org.xml.sax, org.xml.sax.helpers, javax.xml.parsers, javax.naming");
@@ -89,8 +89,8 @@ public class FelixHost {
// otherProps.put(Constants.FRAMEWORK_STORAGE, "bundles");
- otherProps.put(AutoProcessor.AUTO_DEPLOY_DIR_PROPERY, AutoProcessor.AUTO_DEPLOY_DIR_VALUE);
- otherProps.put(AutoProcessor.AUTO_DEPLOY_ACTION_PROPERY, AutoProcessor.AUTO_DEPLOY_START_VALUE + "," + AutoProcessor.AUTO_DEPLOY_INSTALL_VALUE);
+ otherProps.put(AutoProcessor.AUTO_DEPLOY_DIR_PROPERTY, AutoProcessor.AUTO_DEPLOY_DIR_VALUE);
+ otherProps.put(AutoProcessor.AUTO_DEPLOY_ACTION_PROPERTY, AutoProcessor.AUTO_DEPLOY_START_VALUE + "," + AutoProcessor.AUTO_DEPLOY_INSTALL_VALUE);
BundleContext felixBudleContext = felix.getBundleContext();
diff --git a/integration/src/test/java/org/slf4j/test_osgi/FrameworkErrorListener.java b/integration/src/test/java/org/slf4j/test_osgi/FrameworkErrorListener.java
index 2f9458d8..bdb13a7f 100644
--- a/integration/src/test/java/org/slf4j/test_osgi/FrameworkErrorListener.java
+++ b/integration/src/test/java/org/slf4j/test_osgi/FrameworkErrorListener.java
@@ -32,8 +32,9 @@ import org.osgi.framework.FrameworkListener;
public class FrameworkErrorListener implements FrameworkListener {
- public List<FrameworkEvent> errorList = new ArrayList<FrameworkEvent>();
+ public List<FrameworkEvent> errorList = new ArrayList<>();
+ @Override
public void frameworkEvent(FrameworkEvent fe) {
if (fe.getType() == FrameworkEvent.ERROR) {
errorList.add(fe);
@@ -54,9 +55,8 @@ public class FrameworkErrorListener implements FrameworkListener {
}
public void dumpAll() {
- for (int i = 0; i < errorList.size(); i++) {
- FrameworkEvent fe = (FrameworkEvent) errorList.get(i);
- dump(fe);
+ for (FrameworkEvent frameworkEvent : errorList) {
+ dump(frameworkEvent);
}
}
}
diff --git a/jcl-over-slf4j/pom.xml b/jcl-over-slf4j/pom.xml
index c6ff398f..80249164 100755
--- a/jcl-over-slf4j/pom.xml
+++ b/jcl-over-slf4j/pom.xml
@@ -1,65 +1,58 @@
+<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>jcl-over-slf4j</artifactId>
<packaging>jar</packaging>
- <name>JCL 1.1.1 implemented over SLF4J</name>
- <description>JCL 1.1.1 implemented over SLF4J</description>
+ <name>JCL 1.2 implemented over SLF4J</name>
+ <description>JCL 1.2 implemented over SLF4J</description>
<url>http://www.slf4j.org</url>
+ <licenses>
+ <license>
+ <name>Apache License, Version 2.0</name>
+ <url>https://www.apache.org/licenses/LICENSE-2.0.txt</url>
+ <distribution>repo</distribution>
+ </license>
+ </licenses>
- <dependencies>
- <!--
- <dependency>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-nop</artifactId>
- <version>${project.version}</version>
- <scope>provided</scope>
- </dependency>
- -->
+ <properties>
+ <module-name>org.apache.commons.logging</module-name>
+ </properties>
+ <dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</dependency>
-
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-jdk14</artifactId>
<scope>test</scope>
</dependency>
-
</dependencies>
-
<build>
<plugins>
<plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
<configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
+ <instructions>
+ <_exportcontents>org.apache.commons.logging*;version=${jcl.version};-noimport:=true</_exportcontents>
+ </instructions>
</configuration>
</plugin>
-
- </plugins>
-
+ </plugins>
</build>
-
-</project> \ No newline at end of file
+</project>
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/Log.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/Log.java
index 779c4d9d..b74c8a74 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/Log.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/Log.java
@@ -20,7 +20,7 @@ package org.apache.commons.logging;
* <p>A simple logging interface abstracting logging APIs. In order to be
* instantiated successfully by {@link LogFactory}, classes that implement
* this interface must have a constructor that takes a single String
- * parameter representing the "name" of this Log.</p>
+ * parameter representing the "name" of this Log.
*
* <p> The six logging levels used by <code>Log</code> are (in order):
* <ol>
@@ -34,27 +34,27 @@ package org.apache.commons.logging;
* The mapping of these log levels to the concepts used by the underlying
* logging system is implementation dependent.
* The implementation should ensure, though, that this ordering behaves
- * as expected.</p>
+ * as expected.
*
* <p>Performance is often a logging concern.
* By examining the appropriate property,
* a component can avoid expensive operations (producing information
- * to be logged).</p>
+ * to be logged).
*
* <p> For example,
- * <code><pre>
+ * <pre>
* if (log.isDebugEnabled()) {
* ... do something expensive ...
* log.debug(theResult);
* }
- * </pre></code>
- * </p>
+ * </pre>
+ *
*
* <p>Configuration of the underlying logging system will generally be done
* external to the Logging APIs, through whatever mechanism is supported by
- * that system.</p>
+ * that system.
*
- * <p style="color: #E40; font-weight: bold;">Please note that this interface is identical to that found in JCL 1.1.1.</p>
+ * <p style="color: #E40; font-weight: bold;">Please note that this interface is identical to that found in JCL 1.1.1.
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
@@ -65,74 +65,74 @@ public interface Log {
// ----------------------------------------------------- Logging Properties
/**
- * <p> Is debug logging currently enabled? </p>
+ * <p> Is debug logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than debug. </p>
+ * when the log level is more than debug.
*/
public boolean isDebugEnabled();
/**
- * <p> Is error logging currently enabled? </p>
+ * <p> Is error logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than error. </p>
+ * when the log level is more than error.
*/
public boolean isErrorEnabled();
/**
- * <p> Is fatal logging currently enabled? </p>
+ * <p> Is fatal logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than fatal. </p>
+ * when the log level is more than fatal.
*/
public boolean isFatalEnabled();
/**
- * <p> Is info logging currently enabled? </p>
+ * <p> Is info logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than info. </p>
+ * when the log level is more than info.
*
* @return true if info enabled, false otherwise
*/
public boolean isInfoEnabled();
/**
- * <p> Is trace logging currently enabled? </p>
+ * <p> Is trace logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than trace. </p>
+ * when the log level is more than trace.
*
* @return true if trace enabled, false otherwise
*/
public boolean isTraceEnabled();
/**
- * <p> Is warn logging currently enabled? </p>
+ * <p> Is warn logging currently enabled?
*
* <p> Call this method to prevent having to perform expensive operations
* (for example, <code>String</code> concatenation)
- * when the log level is more than warn. </p>
+ * when the log level is more than warn.
*/
public boolean isWarnEnabled();
// -------------------------------------------------------- Logging Methods
/**
- * <p> Log a message with trace log level. </p>
+ * <p> Log a message with trace log level.
*
* @param message log this message
*/
public void trace(Object message);
/**
- * <p> Log an error with trace log level. </p>
+ * <p> Log an error with trace log level.
*
* @param message log this message
* @param t log this cause
@@ -140,14 +140,14 @@ public interface Log {
public void trace(Object message, Throwable t);
/**
- * <p> Log a message with debug log level. </p>
+ * <p> Log a message with debug log level.
*
* @param message log this message
*/
public void debug(Object message);
/**
- * <p> Log an error with debug log level. </p>
+ * <p> Log an error with debug log level.
*
* @param message log this message
* @param t log this cause
@@ -155,14 +155,14 @@ public interface Log {
public void debug(Object message, Throwable t);
/**
- * <p> Log a message with info log level. </p>
+ * <p> Log a message with info log level.
*
* @param message log this message
*/
public void info(Object message);
/**
- * <p> Log an error with info log level. </p>
+ * <p> Log an error with info log level.
*
* @param message log this message
* @param t log this cause
@@ -170,14 +170,14 @@ public interface Log {
public void info(Object message, Throwable t);
/**
- * <p> Log a message with warn log level. </p>
+ * <p> Log a message with warn log level.
*
* @param message log this message
*/
public void warn(Object message);
/**
- * <p> Log an error with warn log level. </p>
+ * <p> Log an error with warn log level.
*
* @param message log this message
* @param t log this cause
@@ -185,14 +185,14 @@ public interface Log {
public void warn(Object message, Throwable t);
/**
- * <p> Log a message with error log level. </p>
+ * <p> Log a message with error log level.
*
* @param message log this message
*/
public void error(Object message);
/**
- * <p> Log an error with error log level. </p>
+ * <p> Log an error with error log level.
*
* @param message log this message
* @param t log this cause
@@ -200,14 +200,14 @@ public interface Log {
public void error(Object message, Throwable t);
/**
- * <p> Log a message with fatal log level. </p>
+ * <p> Log a message with fatal log level.
*
* @param message log this message
*/
public void fatal(Object message);
/**
- * <p> Log an error with fatal log level. </p>
+ * <p> Log an error with fatal log level.
*
* @param message log this message
* @param t log this cause
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogConfigurationException.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogConfigurationException.java
index 668f413d..c51084ef 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogConfigurationException.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogConfigurationException.java
@@ -21,7 +21,7 @@ package org.apache.commons.logging;
* An exception that is thrown only if a suitable <code>LogFactory</code> or
* <code>Log</code> instance cannot be created by the corresponding factory
* methods.
- * </p>
+ *
*
* <p>
* In this version of JCL, this exception will never be thrown in practice.
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogFactory.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogFactory.java
index 275aab30..f58c0e31 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogFactory.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/LogFactory.java
@@ -25,7 +25,7 @@ import org.apache.commons.logging.impl.SLF4JLogFactory;
* Factory for creating {@link Log} instances, which always delegates to an
* instance of {@link SLF4JLogFactory}.
*
- * </p>
+ *
*
* @author Craig R. McClanahan
* @author Costin Manolache
@@ -170,7 +170,7 @@ public abstract class LogFactory {
* <p>
* Construct (if necessary) and return a <code>Log</code> instance, using
* the factory's current set of configuration attributes.
- * </p>
+ *
*
* <p>
* <strong>NOTE </strong>- Depending upon the implementation of the
@@ -178,7 +178,7 @@ public abstract class LogFactory {
* you are returned may or may not be local to the current application, and
* may or may not be returned again on a subsequent call with the same name
* argument.
- * </p>
+ *
*
* @param name
* Logical name of the <code>Log</code> instance to be
@@ -229,7 +229,7 @@ public abstract class LogFactory {
* Construct (if necessary) and return a <code>LogFactory</code> instance,
* using the following ordered lookup procedure to determine the name of the
* implementation class to be loaded.
- * </p>
+ *
* <ul>
* <li>The <code>org.apache.commons.logging.LogFactory</code> system
* property.</li>
@@ -248,7 +248,7 @@ public abstract class LogFactory {
* <code>LogFactory</code> implementation class is utilized, all of the
* properties defined in this file will be set as configuration attributes on
* the corresponding <code>LogFactory</code> instance.
- * </p>
+ *
*
* @exception LogConfigurationException
* if the implementation class is not available or cannot
@@ -321,9 +321,9 @@ public abstract class LogFactory {
* Returns a string that uniquely identifies the specified object, including
* its class.
* <p>
- * The returned string is of form "classname@hashcode", ie is the same as the
+ * The returned string is of form "classname@hashcode", i.e. is the same as the
* return value of the Object.toString() method, but works even when the
- * specified object's class has overidden the toString method.
+ * specified object's class has overridden the toString method.
*
* @param o
* may be null.
@@ -345,64 +345,64 @@ public abstract class LogFactory {
* This method exists to ensure signature compatibility.
*/
protected static Object createFactory(String factoryClass, ClassLoader classLoader) {
- throw new UnsupportedOperationException("Operation [factoryClass] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [factoryClass] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static ClassLoader directGetContextClassLoader() {
- throw new UnsupportedOperationException("Operation [directGetContextClassLoader] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [directGetContextClassLoader] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static ClassLoader getContextClassLoader() throws LogConfigurationException {
- throw new UnsupportedOperationException("Operation [getContextClassLoader] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [getContextClassLoader] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static ClassLoader getClassLoader(Class clazz) {
- throw new UnsupportedOperationException("Operation [getClassLoader] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [getClassLoader] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static boolean isDiagnosticsEnabled() {
- throw new UnsupportedOperationException("Operation [isDiagnosticsEnabled] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [isDiagnosticsEnabled] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static void logRawDiagnostic(String msg) {
- throw new UnsupportedOperationException("Operation [logRawDiagnostic] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [logRawDiagnostic] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static LogFactory newFactory(final String factoryClass, final ClassLoader classLoader, final ClassLoader contextClassLoader) {
- throw new UnsupportedOperationException("Operation [logRawDiagnostic] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [logRawDiagnostic] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
/**
* This method exists to ensure signature compatibility.
*/
protected static LogFactory newFactory(final String factoryClass, final ClassLoader classLoader) {
- throw new UnsupportedOperationException("Operation [newFactory] is not supported in jcl-over-slf4j. See also "
- + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
+ throw new UnsupportedOperationException(
+ "Operation [newFactory] is not supported in jcl-over-slf4j. See also " + UNSUPPORTED_OPERATION_IN_JCL_OVER_SLF4J);
}
} \ No newline at end of file
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/NoOpLog.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/NoOpLog.java
index 45e99a4a..49f72528 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/NoOpLog.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/NoOpLog.java
@@ -23,7 +23,7 @@ import org.apache.commons.logging.Log;
* <p>
* Trivial implementation of Log that throws away all messages. No configurable
* system properties are supported.
- * </p>
+ *
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLocationAwareLog.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLocationAwareLog.java
index ef48be67..755c2f59 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLocationAwareLog.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLocationAwareLog.java
@@ -43,11 +43,11 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
// in both Log4jLogger and Jdk14Logger classes in the original JCL, the
// logger instance is transient
- private transient LocationAwareLogger logger;
+ private final transient LocationAwareLogger logger;
private static final String FQCN = SLF4JLocationAwareLog.class.getName();
- SLF4JLocationAwareLog(LocationAwareLogger logger) {
+ public SLF4JLocationAwareLog(LocationAwareLogger logger) {
this.logger = logger;
this.name = logger.getName();
}
@@ -104,7 +104,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void trace(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.TRACE_INT, String.valueOf(message), null, null);
+ if (isTraceEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.TRACE_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -117,7 +119,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void trace(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.TRACE_INT, String.valueOf(message), null, t);
+ if (isTraceEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.TRACE_INT, String.valueOf(message), null, t);
+ }
}
/**
@@ -128,7 +132,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void debug(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.DEBUG_INT, String.valueOf(message), null, null);
+ if (isDebugEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.DEBUG_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -141,7 +147,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void debug(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.DEBUG_INT, String.valueOf(message), null, t);
+ if (isDebugEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.DEBUG_INT, String.valueOf(message), null, t);
+ }
}
/**
@@ -152,7 +160,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void info(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.INFO_INT, String.valueOf(message), null, null);
+ if (isInfoEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.INFO_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -165,7 +175,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void info(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.INFO_INT, String.valueOf(message), null, t);
+ if (isInfoEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.INFO_INT, String.valueOf(message), null, t);
+ }
}
/**
@@ -176,7 +188,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void warn(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.WARN_INT, String.valueOf(message), null, null);
+ if (isWarnEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.WARN_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -189,7 +203,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void warn(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.WARN_INT, String.valueOf(message), null, t);
+ if (isWarnEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.WARN_INT, String.valueOf(message), null, t);
+ }
}
/**
@@ -200,7 +216,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void error(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, null);
+ if (isErrorEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -213,7 +231,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void error(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, t);
+ if (isErrorEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, t);
+ }
}
/**
@@ -224,7 +244,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the message to log. Converted to {@link String}
*/
public void fatal(Object message) {
- logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, null);
+ if (isErrorEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, null);
+ }
}
/**
@@ -237,7 +259,9 @@ public class SLF4JLocationAwareLog implements Log, Serializable {
* the exception to log
*/
public void fatal(Object message, Throwable t) {
- logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, t);
+ if (isErrorEnabled()) {
+ logger.log(null, FQCN, LocationAwareLogger.ERROR_INT, String.valueOf(message), null, t);
+ }
}
/**
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLog.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLog.java
index 5ee59f7b..2e796c2b 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLog.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLog.java
@@ -42,9 +42,9 @@ public class SLF4JLog implements Log, Serializable {
// in both Log4jLogger and Jdk14Logger classes in the original JCL, the
// logger instance is transient
- private transient Logger logger;
+ private final transient Logger logger;
- SLF4JLog(Logger logger) {
+ public SLF4JLog(Logger logger) {
this.logger = logger;
this.name = logger.getName();
}
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLogFactory.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLogFactory.java
index d715c59f..2050adb2 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLogFactory.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SLF4JLogFactory.java
@@ -42,7 +42,7 @@ import java.util.concurrent.ConcurrentMap;
*
* <p>
* This implementation ignores any configured attributes.
- * </p>
+ *
*
* @author Rod Waldhoff
* @author Craig R. McClanahan
@@ -64,7 +64,7 @@ public class SLF4JLogFactory extends LogFactory {
* Public no-arguments constructor required by the lookup mechanism.
*/
public SLF4JLogFactory() {
- loggerMap = new ConcurrentHashMap<String, Log>();
+ loggerMap = new ConcurrentHashMap<>();
}
// ----------------------------------------------------- Manifest Constants
@@ -105,12 +105,12 @@ public class SLF4JLogFactory extends LogFactory {
@SuppressWarnings("unchecked")
public String[] getAttributeNames() {
- List<String> names = new ArrayList<String>();
+ List<String> names = new ArrayList<>();
Enumeration<String> keys = attributes.keys();
while (keys.hasMoreElements()) {
names.add((String) keys.nextElement());
}
- String results[] = new String[names.size()];
+ String[] results = new String[names.size()];
for (int i = 0; i < results.length; i++) {
results[i] = (String) names.get(i);
}
@@ -136,7 +136,7 @@ public class SLF4JLogFactory extends LogFactory {
* <p>
* Construct (if necessary) and return a <code>Log</code> instance, using
* the factory's current set of configuration attributes.
- * </p>
+ *
*
* @param name
* Logical name of the <code>Log</code> instance to be returned
@@ -173,12 +173,10 @@ public class SLF4JLogFactory extends LogFactory {
public void release() {
// This method is never called by jcl-over-slf4j classes. However,
// in certain deployment scenarios, in particular if jcl-over-slf4j.jar
- // is
- // in the the web-app class loader and the official commons-logging.jar is
- // deployed in some parent class loader (e.g. commons/lib), then it is
- // possible
- // for the parent class loader to mask the classes shipping in
- // jcl-over-slf4j.jar.
+ // is in the web-app class loader and the official commons-logging.jar
+ // is deployed in some parent class loader (e.g. commons/lib), then it
+ // is possible for the parent class loader to mask the classes shipping
+ // in jcl-over-slf4j.jar.
System.out.println("WARN: The method " + SLF4JLogFactory.class + "#release() was invoked.");
System.out.println("WARN: Please see http://www.slf4j.org/codes.html#release for an explanation.");
System.out.flush();
@@ -216,4 +214,4 @@ public class SLF4JLogFactory extends LogFactory {
}
}
-} \ No newline at end of file
+}
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SimpleLog.java b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SimpleLog.java
index 46b5d70e..e8223af6 100644
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SimpleLog.java
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/impl/SimpleLog.java
@@ -35,7 +35,7 @@ import org.apache.commons.logging.LogConfigurationException;
* Simple implementation of Log that sends all enabled log messages, for all
* defined loggers, to System.err. The following system properties are supported
* to configure the behavior of this logger:
- * </p>
+ *
* <ul>
* <li><code>org.apache.commons.logging.simplelog.defaultlog</code> - Default
* logging detail level for all instances of SimpleLog. Must be one of ("trace",
@@ -67,7 +67,7 @@ import org.apache.commons.logging.LogConfigurationException;
* this implementation also checks for a class loader resource named
* <code>"simplelog.properties"</code>, and includes any matching definitions
* from this resource (if it exists).
- * </p>
+ *
*
* @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
* @author Rod Waldhoff
@@ -87,7 +87,7 @@ public class SimpleLog implements Log, Serializable {
/** Properties loaded from simplelog.properties */
static protected final Properties simpleLogProps = new Properties();
- /** The default format to use when formating dates */
+ /** The default format to use when formatting dates */
static protected final String DEFAULT_DATE_TIME_FORMAT = "yyyy/MM/dd HH:mm:ss:SSS zzz";
/** Include the instance name in the log message? */
@@ -157,9 +157,14 @@ public class SimpleLog implements Log, Serializable {
if (null != in) {
try {
simpleLogProps.load(in);
- in.close();
} catch (java.io.IOException e) {
// ignored
+ } finally {
+ try {
+ in.close();
+ } catch (java.io.IOException e) {
+ // ignored
+ }
}
}
@@ -243,7 +248,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Set logging level.
- * </p>
+ *
*
* @param currentLogLevel
* new logging level
@@ -257,7 +262,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Get logging level.
- * </p>
+ *
*/
public int getLevel() {
@@ -270,7 +275,7 @@ public class SimpleLog implements Log, Serializable {
* <p>
* Do the actual logging. This method assembles the message and then calls
* <code>write()</code> to cause it to be written.
- * </p>
+ *
*
* @param type
* One of the LOG_LEVEL_XXX constants defining the log level
@@ -349,7 +354,7 @@ public class SimpleLog implements Log, Serializable {
* Write the content of the message accumulated in the specified
* <code>StringBuffer</code> to the appropriate output destination. The
* default implementation writes to <code>System.err</code>.
- * </p>
+ *
*
* @param buffer
* A <code>StringBuffer</code> containing the accumulated text to be
@@ -378,7 +383,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with debug log level.
- * </p>
+ *
*/
public final void debug(Object message) {
@@ -390,7 +395,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with debug log level.
- * </p>
+ *
*/
public final void debug(Object message, Throwable t) {
@@ -402,7 +407,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with trace log level.
- * </p>
+ *
*/
public final void trace(Object message) {
@@ -414,7 +419,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with trace log level.
- * </p>
+ *
*/
public final void trace(Object message, Throwable t) {
@@ -426,7 +431,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with info log level.
- * </p>
+ *
*/
public final void info(Object message) {
@@ -438,7 +443,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with info log level.
- * </p>
+ *
*/
public final void info(Object message, Throwable t) {
@@ -450,7 +455,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with warn log level.
- * </p>
+ *
*/
public final void warn(Object message) {
@@ -462,7 +467,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with warn log level.
- * </p>
+ *
*/
public final void warn(Object message, Throwable t) {
@@ -474,7 +479,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with error log level.
- * </p>
+ *
*/
public final void error(Object message) {
@@ -486,7 +491,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with error log level.
- * </p>
+ *
*/
public final void error(Object message, Throwable t) {
@@ -498,7 +503,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log a message with fatal log level.
- * </p>
+ *
*/
public final void fatal(Object message) {
@@ -510,7 +515,7 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Log an error with fatal log level.
- * </p>
+ *
*/
public final void fatal(Object message, Throwable t) {
@@ -522,12 +527,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are debug messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isDebugEnabled() {
@@ -537,12 +542,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are error messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isErrorEnabled() {
@@ -552,12 +557,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are fatal messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isFatalEnabled() {
@@ -567,12 +572,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are info messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isInfoEnabled() {
@@ -582,12 +587,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are trace messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isTraceEnabled() {
@@ -597,12 +602,12 @@ public class SimpleLog implements Log, Serializable {
/**
* <p>
* Are warn messages currently enabled?
- * </p>
+ *
*
* <p>
* This allows expensive operations such as <code>String</code> concatenation
* to be avoided when the message will be ignored by the logger.
- * </p>
+ *
*/
public final boolean isWarnEnabled() {
@@ -668,15 +673,13 @@ public class SimpleLog implements Log, Serializable {
}
private static InputStream getResourceAsStream(final String name) {
- return AccessController.doPrivileged(new PrivilegedAction<InputStream>() {
- public InputStream run() {
- ClassLoader threadCL = getContextClassLoader();
-
- if (threadCL != null) {
- return threadCL.getResourceAsStream(name);
- } else {
- return ClassLoader.getSystemResourceAsStream(name);
- }
+ return AccessController.doPrivileged((PrivilegedAction<InputStream>) () -> {
+ ClassLoader threadCL = getContextClassLoader();
+
+ if (threadCL != null) {
+ return threadCL.getResourceAsStream(name);
+ } else {
+ return ClassLoader.getSystemResourceAsStream(name);
}
});
}
diff --git a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/package.html b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/package.html
index 014e85a6..26f3fe6c 100755
--- a/jcl-over-slf4j/src/main/java/org/apache/commons/logging/package.html
+++ b/jcl-over-slf4j/src/main/java/org/apache/commons/logging/package.html
@@ -31,7 +31,7 @@ replacement for the original JCL version 1.0.4.
<p>As the original JCL version 1.0.4, the present version supports
various logging APIs. It differs from the original in implementation
but not the public API. This implementation uses SLF4J under the
-covers. As as such, all the logging systems that SLF4J supports,
+covers. As such, all the logging systems that SLF4J supports,
e.g. NOP, Simple, JDK14, nlog4j are supported by this version of JCL.
</p>
diff --git a/jcl-over-slf4j/src/main/java9/module-info.java b/jcl-over-slf4j/src/main/java9/module-info.java
new file mode 100755
index 00000000..8c33c164
--- /dev/null
+++ b/jcl-over-slf4j/src/main/java9/module-info.java
@@ -0,0 +1,4 @@
+module org.apache.commons.logging {
+ requires org.slf4j;
+ exports org.apache.commons.logging;
+}
diff --git a/jcl-over-slf4j/src/main/resources/META-INF/MANIFEST.MF b/jcl-over-slf4j/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index d5233ea3..00000000
--- a/jcl-over-slf4j/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,9 +0,0 @@
-Implementation-Title: jcl-over-slf4j
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: jcl.over.slf4j
-Bundle-Name: jcl-over-slf4j
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.apache.commons.logging;version=1.1.1,
- org.apache.commons.logging.impl;version=1.1.1
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}
diff --git a/jcl-over-slf4j/src/test/java/org/apache/commons/logging/InvokeJCLTest.java b/jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/InvokeJCLTest.java
index ef5d23cb..931ed8ba 100644
--- a/jcl-over-slf4j/src/test/java/org/apache/commons/logging/InvokeJCLTest.java
+++ b/jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/InvokeJCLTest.java
@@ -23,12 +23,20 @@
*
*/
-package org.apache.commons.logging;
+package org.apache.commons.logging.test;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.assertEquals;
-public class InvokeJCLTest extends TestCase {
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.junit.Test;
+
+public class InvokeJCLTest {
+
+ @Test
public void testIsEnabledAPI() {
// assume that we are running over slf4j-jdk14
Log log = LogFactory.getLog(InvokeJCLTest.class);
@@ -40,6 +48,7 @@ public class InvokeJCLTest extends TestCase {
assertTrue(log.isFatalEnabled());
}
+ @Test
public void testPrintAPI() {
Log log = LogFactory.getLog(InvokeJCLTest.class);
Exception e = new Exception("just testing");
@@ -80,4 +89,58 @@ public class InvokeJCLTest extends TestCase {
log.fatal(null, e);
log.fatal("fatal message", e);
}
+
+ @Test
+ public void testAvoidConvertingObjectToString() {
+ Log log = LogFactory.getLog(InvokeJCLTest.class);
+ Exception e = new Exception("just testing");
+
+ TestMessage fatalMsg = new TestMessage("fatal msg");
+ TestMessage errorMsg = new TestMessage("error msg");
+ TestMessage warnMsg = new TestMessage("warn msg");
+ TestMessage infoMsg = new TestMessage("info msg");
+ TestMessage debugMsg = new TestMessage("debug msg");
+ TestMessage traceMsg = new TestMessage("trace msg");
+
+ log.fatal(fatalMsg);
+ log.fatal(fatalMsg, e);
+ assertEquals(2, fatalMsg.invokedCount);
+
+ log.error(errorMsg);
+ log.error(errorMsg, e);
+ assertEquals(2, errorMsg.invokedCount);
+
+ log.warn(warnMsg);
+ log.warn(warnMsg, e);
+ assertEquals(2, warnMsg.invokedCount);
+
+ log.info(infoMsg);
+ log.info(infoMsg, e);
+ assertEquals(2, infoMsg.invokedCount);
+
+ log.debug(debugMsg);
+ log.debug(debugMsg, e);
+ assertEquals(0, debugMsg.invokedCount);
+
+ log.trace(traceMsg);
+ log.trace(traceMsg, e);
+ assertEquals(0, traceMsg.invokedCount);
+ }
+
+ static class TestMessage {
+
+ private final String msg;
+ int invokedCount = 0;
+
+ TestMessage(String msg) {
+ this.msg = msg;
+ }
+
+ @Override
+ public String toString() {
+ invokedCount++;
+ return msg;
+ }
+ }
+
}
diff --git a/jcl-over-slf4j/src/test/java/org/apache/commons/logging/impl/SerializationTest.java b/jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/SerializationTest.java
index 017d6b84..3ca0b9ac 100644
--- a/jcl-over-slf4j/src/test/java/org/apache/commons/logging/impl/SerializationTest.java
+++ b/jcl-over-slf4j/src/test/java/org/apache/commons/logging/test/SerializationTest.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.apache.commons.logging.impl;
+package org.apache.commons.logging.test;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
@@ -30,30 +30,29 @@ import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
-import junit.framework.TestCase;
-
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
-import org.slf4j.impl.JDK14LoggerFactory;
+import org.apache.commons.logging.impl.SLF4JLocationAwareLog;
+import org.apache.commons.logging.impl.SLF4JLog;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.jul.JDK14LoggerFactory;
import org.slf4j.spi.LocationAwareLogger;
-public class SerializationTest extends TestCase {
+public class SerializationTest {
ObjectInputStream ois;
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos;
- public SerializationTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
+ @Before
+ public void setUp() throws Exception {
oos = new ObjectOutputStream(baos);
- super.setUp();
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
oos.close();
}
@@ -67,6 +66,7 @@ public class SerializationTest extends TestCase {
resuscitatedLog.isDebugEnabled();
}
+ @Test
public void testSLF4JLog() throws Exception {
JDK14LoggerFactory factory = new JDK14LoggerFactory();
SLF4JLog log = new SLF4JLog(factory.getLogger("x"));
@@ -74,12 +74,14 @@ public class SerializationTest extends TestCase {
verify();
}
+ @Test
public void testSmoke() throws Exception {
Log log = LogFactory.getLog("testing");
oos.writeObject(log);
verify();
}
+ @Test
public void testLocationAware() throws Exception {
JDK14LoggerFactory factory = new JDK14LoggerFactory();
SLF4JLocationAwareLog log = new SLF4JLocationAwareLog((LocationAwareLogger) factory.getLogger("x"));
diff --git a/slf4j-android/LICENSE.txt b/jul-to-slf4j/LICENSE.txt
index 361d2ce0..1a3d0532 100644
--- a/slf4j-android/LICENSE.txt
+++ b/jul-to-slf4j/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2013 QOS.ch
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/jul-to-slf4j/pom.xml b/jul-to-slf4j/pom.xml
index 4c5476c5..89640acb 100755
--- a/jul-to-slf4j/pom.xml
+++ b/jul-to-slf4j/pom.xml
@@ -1,14 +1,14 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>jul-to-slf4j</artifactId>
@@ -26,7 +26,7 @@
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
- <artifactId>slf4j-log4j12</artifactId>
+ <artifactId>slf4j-reload4j</artifactId>
<version>${project.version}</version>
<scope>test</scope>
</dependency>
@@ -34,31 +34,7 @@
<build>
<plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-compiler-plugin</artifactId>
- <configuration>
- <source>${required.jdk.version}</source>
- <target>${required.jdk.version}</target>
- </configuration>
- </plugin>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}
- </Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
-
</plugins>
</build>
-</project> \ No newline at end of file
+</project>
diff --git a/jul-to-slf4j/src/main/java/org/slf4j/bridge/SLF4JBridgeHandler.java b/jul-to-slf4j/src/main/java/org/slf4j/bridge/SLF4JBridgeHandler.java
index 72576a03..74adedcf 100755
--- a/jul-to-slf4j/src/main/java/org/slf4j/bridge/SLF4JBridgeHandler.java
+++ b/jul-to-slf4j/src/main/java/org/slf4j/bridge/SLF4JBridgeHandler.java
@@ -36,15 +36,15 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.spi.LocationAwareLogger;
-// Based on http://bugzilla.slf4j.org/show_bug.cgi?id=38
+// Based on http://jira.qos.ch/browse/SLF4J-30
/**
- * <p>Bridge/route all JUL log records to the SLF4J API.</p>
+ * <p>Bridge/route all JUL log records to the SLF4J API.
* <p>Essentially, the idea is to install on the root logger an instance of
* <code>SLF4JBridgeHandler</code> as the sole JUL handler in the system. Subsequently, the
* SLF4JBridgeHandler instance will redirect all JUL log records are redirected
* to the SLF4J API based on the following mapping of levels:
- * </p>
+ *
* <pre>
* FINEST -&gt; TRACE
* FINER -&gt; DEBUG
@@ -52,7 +52,7 @@ import org.slf4j.spi.LocationAwareLogger;
* INFO -&gt; INFO
* WARNING -&gt; WARN
* SEVERE -&gt; ERROR</pre>
- * <p><b>Programmatic installation:</b></p>
+ * <p><b>Programmatic installation:</b>
* <pre>
* // Optionally remove existing handlers attached to j.u.l root logger
* SLF4JBridgeHandler.removeHandlersForRootLogger(); // (since SLF4J 1.6.5)
@@ -60,12 +60,12 @@ import org.slf4j.spi.LocationAwareLogger;
* // add SLF4JBridgeHandler to j.u.l's root logger, should be done once during
* // the initialization phase of your application
* SLF4JBridgeHandler.install();</pre>
- * <p><b>Installation via <em>logging.properties</em> configuration file:</b></p>
+ * <p><b>Installation via <em>logging.properties</em> configuration file:</b>
* <pre>
* // register SLF4JBridgeHandler as handler for the j.u.l. root logger
* handlers = org.slf4j.bridge.SLF4JBridgeHandler</pre>
* <p>Once SLF4JBridgeHandler is installed, logging by j.u.l. loggers will be directed to
- * SLF4J. Example: </p>
+ * SLF4J. Example:
* <pre>
* import java.util.logging.Logger;
* ...
@@ -79,17 +79,26 @@ import org.slf4j.spi.LocationAwareLogger;
* SLF4J translation can seriously increase the cost of disabled logging
* statements (60 fold or 6000% increase) and measurably impact the performance of enabled log
* statements (20% overall increase).</b> Please note that as of logback-version 0.9.25,
- * it is possible to completely eliminate the 60 fold translation overhead for disabled
+ * it is possible to completely eliminate the 60-fold translation overhead for disabled
* log statements with the help of <a href="http://logback.qos.ch/manual/configuration.html#LevelChangePropagator">LevelChangePropagator</a>.
- * </p>
+ *
*
* <p>If you are concerned about application performance, then use of <code>SLF4JBridgeHandler</code>
- * is appropriate only if any one the following two conditions is true:</p>
+ * is appropriate only if any of the following conditions is true:
* <ol>
* <li>few j.u.l. logging statements are in play</li>
* <li>LevelChangePropagator has been installed</li>
* </ol>
*
+ * <h2>As a Java 9/Jigsaw module</h2>
+ *
+ * <p>Given that <b>to</b> is a reserved keyword under Java 9 within module productions,
+ * the MANIFEST.MF file in <em>jul-to-slf4j.jar</em> declares <b>jul_to_slf4j</b> as
+ * its Automatic Module Name. Thus, if your application is Jigsaw modularized, the requires
+ * statement in your <em>module-info.java</em> needs to be <b>jul_to_slf4j</b>
+ * (note the two underscores).
+ *
+ *
* @author Christian Stein
* @author Joern Huxhorn
* @author Ceki G&uuml;lc&uuml;
@@ -109,9 +118,8 @@ public class SLF4JBridgeHandler extends Handler {
/**
* Adds a SLF4JBridgeHandler instance to jul's root logger.
- * <p/>
- * <p/>
- * This handler will redirect j.u.l. logging to SLF4J. However, only logs enabled
+ *
+ * <p>This handler will redirect j.u.l. logging to SLF4J. However, only logs enabled
* in j.u.l. will be redirected. For example, if a log statement invoking a
* j.u.l. logger is disabled, then the corresponding non-event will <em>not</em>
* reach SLF4JBridgeHandler and cannot be redirected.
@@ -135,9 +143,9 @@ public class SLF4JBridgeHandler extends Handler {
public static void uninstall() throws SecurityException {
java.util.logging.Logger rootLogger = getRootLogger();
Handler[] handlers = rootLogger.getHandlers();
- for (int i = 0; i < handlers.length; i++) {
- if (handlers[i] instanceof SLF4JBridgeHandler) {
- rootLogger.removeHandler(handlers[i]);
+ for (Handler handler : handlers) {
+ if (handler instanceof SLF4JBridgeHandler) {
+ rootLogger.removeHandler(handler);
}
}
}
@@ -145,14 +153,14 @@ public class SLF4JBridgeHandler extends Handler {
/**
* Returns true if SLF4JBridgeHandler has been previously installed, returns false otherwise.
*
- * @return true if SLF4JBridgeHandler is already installed, false other wise
- * @throws SecurityException
+ * @return true if SLF4JBridgeHandler is already installed, false otherwise
+ *
*/
- public static boolean isInstalled() throws SecurityException {
+ public static boolean isInstalled() {
java.util.logging.Logger rootLogger = getRootLogger();
Handler[] handlers = rootLogger.getHandlers();
- for (int i = 0; i < handlers.length; i++) {
- if (handlers[i] instanceof SLF4JBridgeHandler) {
+ for (Handler handler : handlers) {
+ if (handler instanceof SLF4JBridgeHandler) {
return true;
}
}
@@ -166,8 +174,8 @@ public class SLF4JBridgeHandler extends Handler {
public static void removeHandlersForRootLogger() {
java.util.logging.Logger rootLogger = getRootLogger();
java.util.logging.Handler[] handlers = rootLogger.getHandlers();
- for (int i = 0; i < handlers.length; i++) {
- rootLogger.removeHandler(handlers[i]);
+ for (Handler handler : handlers) {
+ rootLogger.removeHandler(handler);
}
}
@@ -193,6 +201,9 @@ public class SLF4JBridgeHandler extends Handler {
/**
* Return the Logger instance that will be used for logging.
+ *
+ * @param record a LogRecord
+ * @return an SLF4J logger corresponding to the record parameter's logger name
*/
protected Logger getSLF4JLogger(LogRecord record) {
String name = record.getLoggerName();
@@ -259,19 +270,25 @@ public class SLF4JBridgeHandler extends Handler {
}
Object[] params = record.getParameters();
// avoid formatting when there are no or 0 parameters. see also
- // http://bugzilla.slf4j.org/show_bug.cgi?id=212
+ // http://jira.qos.ch/browse/SLF4J-203
if (params != null && params.length > 0) {
- message = MessageFormat.format(message, params);
+ try {
+ message = MessageFormat.format(message, params);
+ } catch (IllegalArgumentException e) {
+ // default to the same behavior as in java.util.logging.Formatter.formatMessage(LogRecord)
+ // see also http://jira.qos.ch/browse/SLF4J-337
+ return message;
+ }
}
return message;
}
/**
* Publish a LogRecord.
- * <p/>
+ * <p>
* The logging request was made initially to a Logger object, which
* initialized the LogRecord and forwarded it here.
- * <p/>
+ * <p>
* This handler ignores the Level attached to the LogRecord, as SLF4J cares
* about discarding log statements.
*
@@ -285,13 +302,12 @@ public class SLF4JBridgeHandler extends Handler {
}
Logger slf4jLogger = getSLF4JLogger(record);
- String message = record.getMessage(); // can be null!
// this is a check to avoid calling the underlying logging system
// with a null message. While it is legitimate to invoke j.u.l. with
// a null message, other logging frameworks do not support this.
- // see also http://bugzilla.slf4j.org/show_bug.cgi?id=108
- if (message == null) {
- message = "";
+ // see also http://jira.qos.ch/browse/SLF4J-99
+ if (record.getMessage() == null) {
+ record.setMessage("");
}
if (slf4jLogger instanceof LocationAwareLogger) {
callLocationAwareLogger((LocationAwareLogger) slf4jLogger, record);
diff --git a/jul-to-slf4j/src/main/java/org/slf4j/bridge/package.html b/jul-to-slf4j/src/main/java/org/slf4j/bridge/package.html
index 2b643c31..30628238 100644
--- a/jul-to-slf4j/src/main/java/org/slf4j/bridge/package.html
+++ b/jul-to-slf4j/src/main/java/org/slf4j/bridge/package.html
@@ -10,6 +10,6 @@
<p>Bridge/route all JUL log records to the SLF4J API.</p>
- <hr/>
+ <hr>
</body>
</html>
diff --git a/jul-to-slf4j/src/main/java9/module-info.java b/jul-to-slf4j/src/main/java9/module-info.java
new file mode 100644
index 00000000..10d4f540
--- /dev/null
+++ b/jul-to-slf4j/src/main/java9/module-info.java
@@ -0,0 +1,7 @@
+module jul.to.slf4j {
+
+ requires org.slf4j;
+ requires java.logging;
+
+ exports org.slf4j.bridge;
+} \ No newline at end of file
diff --git a/jul-to-slf4j/src/main/resources/META-INF/MANIFEST.MF b/jul-to-slf4j/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index e1ab4c0d..00000000
--- a/jul-to-slf4j/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,7 +0,0 @@
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: jul.to.slf4j
-Bundle-Name: jul-to-slf4j
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.bridge;version=${parsedVersion.osgiVersion};uses:="org.slf4j,org.slf4j.spi"
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion},org.slf4j.spi;version=${parsedVersion.osgiVersion}
diff --git a/jul-to-slf4j/src/test/java/org/slf4j/bridge/ListAppender.java b/jul-to-slf4j/src/test/java/org/slf4j/bridge/ListAppender.java
index e5fb5f3b..41cc5d81 100644
--- a/jul-to-slf4j/src/test/java/org/slf4j/bridge/ListAppender.java
+++ b/jul-to-slf4j/src/test/java/org/slf4j/bridge/ListAppender.java
@@ -32,7 +32,7 @@ import org.apache.log4j.spi.LoggingEvent;
public class ListAppender extends AppenderSkeleton {
- public List<LoggingEvent> list = new ArrayList<LoggingEvent>();
+ public List<LoggingEvent> list = new ArrayList<>();
public boolean extractLocationInfo = false;
diff --git a/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerPerfTest.java b/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerPerfTest.java
index 17e2329e..2860aa70 100644
--- a/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerPerfTest.java
+++ b/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerPerfTest.java
@@ -27,13 +27,14 @@ package org.slf4j.bridge;
import java.util.logging.Handler;
import java.util.logging.LogManager;
-import junit.framework.TestCase;
-
import org.apache.log4j.FileAppender;
import org.apache.log4j.PatternLayout;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
import org.slf4j.LoggerFactory;
-public class SLF4JBridgeHandlerPerfTest extends TestCase {
+public class SLF4JBridgeHandlerPerfTest {
static String LOGGER_NAME = "yay";
static int RUN_LENGTH = 100 * 1000;
@@ -50,29 +51,25 @@ public class SLF4JBridgeHandlerPerfTest extends TestCase {
Handler[] existingHandlers;
- public SLF4JBridgeHandlerPerfTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
fileAppender = new FileAppender(new PatternLayout("%r [%t] %p %c %x - %m%n"), "target/test-output/toto.log");
existingHandlers = julRootLogger.getHandlers();
- for (int i = 0; i < existingHandlers.length; i++) {
- julRootLogger.removeHandler(existingHandlers[i]);
+ for (Handler existingHandler : existingHandlers) {
+ julRootLogger.removeHandler(existingHandler);
}
log4jRoot = org.apache.log4j.Logger.getRootLogger();
log4jRoot.addAppender(fileAppender);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
SLF4JBridgeHandler.uninstall();
fileAppender.close();
log4jRoot.getLoggerRepository().resetConfiguration();
- for (int i = 0; i < existingHandlers.length; i++) {
- julRootLogger.addHandler(existingHandlers[i]);
+ for (Handler existingHandler : existingHandlers) {
+ julRootLogger.addHandler(existingHandler);
}
}
@@ -94,6 +91,7 @@ public class SLF4JBridgeHandlerPerfTest extends TestCase {
return (end - start) * 1.0 / RUN_LENGTH;
}
+ @Test
public void testPerf() {
SLF4JBridgeHandler.install();
diff --git a/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerTest.java b/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerTest.java
index a413cdbe..79ca53e0 100755
--- a/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerTest.java
+++ b/jul-to-slf4j/src/test/java/org/slf4j/bridge/SLF4JBridgeHandlerTest.java
@@ -24,43 +24,46 @@
*/
package org.slf4j.bridge;
+import static org.junit.Assert.assertEquals;
+
import java.text.MessageFormat;
import java.util.ResourceBundle;
import java.util.logging.Level;
-import junit.framework.TestCase;
-
import org.apache.log4j.spi.LocationInfo;
import org.apache.log4j.spi.LoggingEvent;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class SLF4JBridgeHandlerTest extends TestCase {
+public class SLF4JBridgeHandlerTest {
static String LOGGER_NAME = "yay";
ListAppender listAppender = new ListAppender();
org.apache.log4j.Logger log4jRoot;
- java.util.logging.Logger julLogger = java.util.logging.Logger.getLogger("yay");
-
- public SLF4JBridgeHandlerTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ java.util.logging.Logger julLogger = java.util.logging.Logger.getLogger(LOGGER_NAME);
+ java.util.logging.Logger julRootLogger = java.util.logging.Logger.getLogger("");
+
+ @Before
+ public void setUp() throws Exception {
listAppender.extractLocationInfo = true;
log4jRoot = org.apache.log4j.Logger.getRootLogger();
log4jRoot.addAppender(listAppender);
log4jRoot.setLevel(org.apache.log4j.Level.TRACE);
+ julRootLogger.setLevel(Level.FINEST);
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
SLF4JBridgeHandler.uninstall();
log4jRoot.getLoggerRepository().resetConfiguration();
}
+ @Test
public void testSmoke() {
SLF4JBridgeHandler.install();
+
String msg = "msg";
julLogger.info(msg);
assertEquals(1, listAppender.list.size());
@@ -77,7 +80,21 @@ public class SLF4JBridgeHandlerTest extends TestCase {
assertEquals("SLF4JBridgeHandlerTest.java", li.getFileName());
assertEquals("testSmoke", li.getMethodName());
}
+
+ @Test
+ public void LOGBACK_1612() {
+ SLF4JBridgeHandler.install();
+
+ String msg = "LOGBACK_1612";
+ julLogger.finer(msg);
+ assertEquals(1, listAppender.list.size());
+ LoggingEvent le = (LoggingEvent) listAppender.list.get(0);
+ assertEquals(LOGGER_NAME, le.getLoggerName());
+ assertEquals(msg, le.getMessage());
+
+ }
+ @Test
public void testLevels() {
SLF4JBridgeHandler.install();
String msg = "msg";
@@ -100,6 +117,9 @@ public class SLF4JBridgeHandlerTest extends TestCase {
assertLevel(i++, org.apache.log4j.Level.ERROR);
}
+
+
+ @Test
public void testLogWithResourceBundle() {
SLF4JBridgeHandler.install();
@@ -113,11 +133,12 @@ public class SLF4JBridgeHandlerTest extends TestCase {
julResourceBundleLogger.info(msg);
assertEquals(1, listAppender.list.size());
- LoggingEvent le = (LoggingEvent) listAppender.list.get(0);
+ LoggingEvent le = listAppender.list.get(0);
assertEquals(LOGGER_NAME, le.getLoggerName());
assertEquals(expectedMsg, le.getMessage());
}
+ @Test
public void testLogWithResourceBundleWithParameters() {
SLF4JBridgeHandler.install();
@@ -146,36 +167,60 @@ public class SLF4JBridgeHandlerTest extends TestCase {
LoggingEvent le = null;
- le = (LoggingEvent) listAppender.list.get(0);
+ le = listAppender.list.get(0);
assertEquals("foo", le.getLoggerName());
assertEquals(expectedMsg1, le.getMessage());
- le = (LoggingEvent) listAppender.list.get(1);
+ le = listAppender.list.get(1);
assertEquals("foo", le.getLoggerName());
assertEquals(expectedMsg2, le.getMessage());
- le = (LoggingEvent) listAppender.list.get(2);
+ le = listAppender.list.get(2);
assertEquals("foo", le.getLoggerName());
assertEquals(expectedMsg3, le.getMessage());
- le = (LoggingEvent) listAppender.list.get(3);
+ le = listAppender.list.get(3);
assertEquals("yay", le.getLoggerName());
assertEquals(expectedMsg3, le.getMessage());
}
+ @Test
public void testLogWithPlaceholderNoParameters() {
SLF4JBridgeHandler.install();
String msg = "msg {non-number-string}";
julLogger.logp(Level.INFO, "SLF4JBridgeHandlerTest", "testLogWithPlaceholderNoParameters", msg, new Object[0]);
assertEquals(1, listAppender.list.size());
- LoggingEvent le = (LoggingEvent) listAppender.list.get(0);
+ LoggingEvent le = listAppender.list.get(0);
assertEquals(LOGGER_NAME, le.getLoggerName());
assertEquals(msg, le.getMessage());
}
+ // See http://jira.qos.ch/browse/SLF4J-337
+
+ @Test
+ public void illFormattedInputShouldBeReturnedAsIs() {
+ SLF4JBridgeHandler.install();
+ String msg = "foo {18=bad} {0}";
+
+ julLogger.log(Level.INFO, msg, "ignored parameter due to IllegalArgumentException");
+ assertEquals(1, listAppender.list.size());
+ LoggingEvent le = listAppender.list.get(0);
+ assertEquals(msg, le.getMessage());
+ }
+
+ @Test
+ public void withNullMessage() {
+ SLF4JBridgeHandler.install();
+ String msg = null;
+ julLogger.log(Level.INFO, msg);
+ assertEquals(1, listAppender.list.size());
+ LoggingEvent le = listAppender.list.get(0);
+ assertEquals("", le.getMessage());
+ }
+
void assertLevel(int index, org.apache.log4j.Level expectedLevel) {
- LoggingEvent le = (LoggingEvent) listAppender.list.get(index);
+ LoggingEvent le = listAppender.list.get(index);
assertEquals(expectedLevel, le.getLevel());
}
}
diff --git a/log4j-over-slf4j/LICENSE.txt b/log4j-over-slf4j/LICENSE.txt
new file mode 100644
index 00000000..2bb9ad24
--- /dev/null
+++ b/log4j-over-slf4j/LICENSE.txt
@@ -0,0 +1,176 @@
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS \ No newline at end of file
diff --git a/log4j-over-slf4j/compatibility/build.xml b/log4j-over-slf4j/compatibility/build.xml
index 5115a42a..b8136313 100644
--- a/log4j-over-slf4j/compatibility/build.xml
+++ b/log4j-over-slf4j/compatibility/build.xml
@@ -39,7 +39,7 @@
<!-- ================================================================= -->
<target name="usage">
<echo>
- These are some of the targets supported by this ANT build scpript:
+ These are some of the targets supported by this ANT build script:
all - run all available tests
refresh - copy required jar files to the lib directory
diff --git a/log4j-over-slf4j/compatibility/readme.txt b/log4j-over-slf4j/compatibility/readme.txt
index 6554cc63..86bbc820 100644
--- a/log4j-over-slf4j/compatibility/readme.txt
+++ b/log4j-over-slf4j/compatibility/readme.txt
@@ -5,7 +5,7 @@ that uses either log4j 1.2.x, or log4j 1.3.x.
In the same directory is a build.xml file that uses ant to
compile the test cases with the corresponding log4j version,
-and to runs these tests without log4j in the classpath but with
+and to run these tests without log4j in the classpath but with
logback jars instead.
To run the tests, one must have ant installed. Issuing the following command,
@@ -14,4 +14,4 @@ once in the compatibility directory will launch the tests:
ant all
To obtain more information about the use of the log4j-over-slf4j module,
-please visit http://www..slf4j.org/log4j-over-slf4j.html \ No newline at end of file
+please visit http://www.slf4j.org/log4j-over-slf4j.html
diff --git a/log4j-over-slf4j/pom.xml b/log4j-over-slf4j/pom.xml
index 6f6c0266..7823734f 100755
--- a/log4j-over-slf4j/pom.xml
+++ b/log4j-over-slf4j/pom.xml
@@ -1,5 +1,5 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
@@ -7,16 +7,17 @@
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
- <artifactId>log4j-over-slf4j</artifactId>
- <packaging>jar</packaging>
- <name>Log4j Implemented Over SLF4J</name>
+ <artifactId>log4j-over-slf4j</artifactId>
+ <packaging>jar</packaging>
+ <name>Log4j Implemented Over SLF4J</name>
<description>Log4j implemented over SLF4J</description>
- <url>http://www.slf4j.org</url>
+ <url>http://www.slf4j.org</url>
<licenses>
<license>
@@ -25,39 +26,34 @@
</license>
</licenses>
+
+
<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
- </dependency>
-
+ </dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-jdk14</artifactId>
<scope>test</scope>
- </dependency>
+ </dependency>
</dependencies>
-
<build>
<plugins>
<plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
<configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
+ <instructions>
+ <_exportcontents>org.apache.log4j*;version=${reload4j.version};-noimport:=true</_exportcontents>
+ </instructions>
+ </configuration>
</plugin>
-
+
</plugins>
</build>
-</project> \ No newline at end of file
+</project>
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Appender.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Appender.java
index 3df673fb..fcc09994 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Appender.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Appender.java
@@ -18,7 +18,6 @@ package org.apache.log4j;
import org.apache.log4j.spi.Filter;
import org.apache.log4j.spi.ErrorHandler;
-import org.apache.log4j.spi.Layout;
import org.apache.log4j.spi.LoggingEvent;
/**
@@ -55,7 +54,7 @@ public interface Appender {
/**
* Release any resources allocated within the appender such as file
* handles, network connections, etc.
- * <p/>
+ *
* <p>It is a programming error to append to a closed appender.
*
* @since 0.8.4
@@ -115,12 +114,12 @@ public interface Appender {
* Configurators call this method to determine if the appender
* requires a layout. If this method returns <code>true</code>,
* meaning that layout is required, then the configurator will
- * configure an layout using the configuration information at its
+ * configure a layout using the configuration information at its
* disposal. If this method returns <code>false</code>, meaning that
* a layout is not required, then layout configuration will be
* skipped even if there is available layout configuration
- * information at the disposal of the configurator..
- * <p/>
+ * information at the disposal of the configurator.
+ *
* <p>In the rather exceptional case, where the appender
* implementation admits a layout but can also work without it, then
* the appender should return <code>true</code>.
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Category.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Category.java
index 0d29fbe9..ee4d7893 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Category.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Category.java
@@ -29,7 +29,7 @@ import java.util.Enumeration;
* This class is a minimal implementation of the original
* <code>org.apache.log4j.Category</code> class (as found in log4j 1.2) by
* delegation of all calls to a {@link org.slf4j.Logger} instance.
- * </p>
+ *
*
* <p>
* Log4j's <code>trace</code>, <code>debug()</code>, <code>info()</code>,
@@ -45,12 +45,12 @@ public class Category {
private static final String CATEGORY_FQCN = Category.class.getName();
- private String name;
+ private final String name;
protected org.slf4j.Logger slf4jLogger;
private org.slf4j.spi.LocationAwareLogger locationAwareLogger;
- private static Marker FATAL_MARKER = MarkerFactory.getMarker("FATAL");
+ private static final Marker FATAL_MARKER = MarkerFactory.getMarker("FATAL");
Category(String name) {
this.name = name;
@@ -125,6 +125,7 @@ public class Category {
/**
* @deprecated Please use {@link #getLevel} instead.
+ * @return a Level
*/
final public Level getPriority() {
return null;
@@ -132,6 +133,9 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#isDebugEnabled} method in SLF4J
+ *
+ * @return true if this logger is enabled for the level DEBUG
+ *
*/
public boolean isDebugEnabled() {
return slf4jLogger.isDebugEnabled();
@@ -139,13 +143,17 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#isInfoEnabled} method in SLF4J
+ *
+ * @return true if this logger is enabled for the level INFO
*/
public boolean isInfoEnabled() {
return slf4jLogger.isInfoEnabled();
}
/**
- * Delegates tob {@link org.slf4j.Logger#isWarnEnabled} method in SLF4J
+ * Delegates to {@link org.slf4j.Logger#isWarnEnabled} method in SLF4J
+ *
+ * @return true if this logger is enabled for the level WARN
*/
public boolean isWarnEnabled() {
return slf4jLogger.isWarnEnabled();
@@ -153,6 +161,8 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#isErrorEnabled} method in SLF4J
+ *
+ * @return true if this logger is enabled for the level ERROR
*/
public boolean isErrorEnabled() {
return slf4jLogger.isErrorEnabled();
@@ -160,13 +170,11 @@ public class Category {
/**
* Determines whether the priority passed as parameter is enabled in the
- * underlying SLF4J logger. Each log4j priority is mapped directly to its
- * SLF4J equivalent, except for FATAL which is mapped as ERROR.
+ * underlying SLF4J logger. Each log4j priority is mapped directly to its SLF4J
+ * equivalent, except for FATAL which is mapped as ERROR.
*
- * @param p
- * the priority to check against
- * @return true if this logger is enabled for the given level, false
- * otherwise.
+ * @param p the priority to check against
+ * @return true if this logger is enabled for the given level, false otherwise.
*/
public boolean isEnabledFor(Priority p) {
switch (p.level) {
@@ -194,19 +202,19 @@ public class Category {
} else {
switch (level) {
case LocationAwareLogger.TRACE_INT:
- slf4jLogger.trace(marker, m);
+ slf4jLogger.trace(marker, m, (Throwable) t);
break;
case LocationAwareLogger.DEBUG_INT:
- slf4jLogger.debug(marker, m);
+ slf4jLogger.debug(marker, m, (Throwable) t);
break;
case LocationAwareLogger.INFO_INT:
- slf4jLogger.info(marker, m);
+ slf4jLogger.info(marker, m, (Throwable) t);
break;
case LocationAwareLogger.WARN_INT:
- slf4jLogger.warn(marker, m);
+ slf4jLogger.warn(marker, m, (Throwable) t);
break;
case LocationAwareLogger.ERROR_INT:
- slf4jLogger.error(marker, m);
+ slf4jLogger.error(marker, m, (Throwable) t);
break;
}
}
@@ -214,6 +222,8 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#debug(String)} method of SLF4J.
+ *
+ * @param message a message to log
*/
public void debug(Object message) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.DEBUG_INT, message, null);
@@ -222,6 +232,9 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#debug(String,Throwable)} method in
* SLF4J.
+ *
+ * @param message a message to log
+ * @param t a throwable to log
*/
public void debug(Object message, Throwable t) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.DEBUG_INT, message, t);
@@ -229,14 +242,18 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#info(String)} method in SLF4J.
+ *
+ * @param message a message to log
*/
public void info(Object message) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.INFO_INT, message, null);
}
/**
- * Delegates to {@link org.slf4j.Logger#info(String,Throwable)} method in
- * SLF4J.
+ * Delegates to {@link org.slf4j.Logger#info(String,Throwable)} method in SLF4J.
+ *
+ * @param message a message to log
+ * @param t a throwable to log
*/
public void info(Object message, Throwable t) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.INFO_INT, message, t);
@@ -244,14 +261,20 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#warn(String)} method in SLF4J.
+ *
+ * @param message a message to log
+ *
*/
public void warn(Object message) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.WARN_INT, message, null);
}
/**
- * Delegates to {@link org.slf4j.Logger#warn(String,Throwable)} method in
- * SLF4J.
+ * Delegates to {@link org.slf4j.Logger#warn(String,Throwable)} method in SLF4J.
+ *
+ * @param message a message to log
+ * @param t a throwable to log
+ *
*/
public void warn(Object message, Throwable t) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.WARN_INT, message, t);
@@ -259,6 +282,9 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#error(String)} method in SLF4J.
+ *
+ * @param message a message to log
+ *
*/
public void error(Object message) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.ERROR_INT, message, null);
@@ -267,6 +293,10 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#error(String,Throwable)} method in
* SLF4J.
+ *
+ * @param message a message to log
+ * @param t a throwable to log
+ *
*/
public void error(Object message, Throwable t) {
differentiatedLog(null, CATEGORY_FQCN, LocationAwareLogger.ERROR_INT, message, t);
@@ -274,6 +304,9 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#error(String)} method in SLF4J.
+ *
+ * @param message a message to log
+ *
*/
public void fatal(Object message) {
differentiatedLog(FATAL_MARKER, CATEGORY_FQCN, LocationAwareLogger.ERROR_INT, message, null);
@@ -282,6 +315,10 @@ public class Category {
/**
* Delegates to {@link org.slf4j.Logger#error(String,Throwable)} method in
* SLF4J. In addition, the call is marked with a marker named "FATAL".
+ *
+ * @param message a message to log
+ * @param t a throwable to log
+ *
*/
public void fatal(Object message, Throwable t) {
differentiatedLog(FATAL_MARKER, CATEGORY_FQCN, LocationAwareLogger.ERROR_INT, message, t);
@@ -291,7 +328,7 @@ public class Category {
log(FQCN, p, msg, t);
}
- // See also http://bugzilla.slf4j.org/show_bug.cgi?id=168
+ // See also http://jira.qos.ch/browse/SLF4J-159
public void log(String FQCN, Priority p, Object msg, Throwable t) {
int levelInt = priorityToLevelInt(p);
differentiatedLog(null, FQCN, levelInt, msg, t);
@@ -347,4 +384,13 @@ public class Category {
// nothing to do
}
+ public boolean getAdditivity() {
+ return false;
+ }
+
+ public void assertLog(boolean assertion, String msg) {
+ if (!assertion)
+ error(msg);
+ }
+
}
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/ConsoleAppender.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/ConsoleAppender.java
index 40e8f800..c1935074 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/ConsoleAppender.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/ConsoleAppender.java
@@ -15,6 +15,18 @@
*/
package org.apache.log4j;
+/**
+ * Skeleton implementation of ConsoleAppender
+ */
public class ConsoleAppender extends WriterAppender {
+ public ConsoleAppender() {
+ }
+
+ public ConsoleAppender(Layout layout) {
+ }
+
+ public ConsoleAppender(Layout layout, String target) {
+ }
+
}
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Layout.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Layout.java
index 4ea3d990..1f4ef945 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Layout.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Layout.java
@@ -20,7 +20,7 @@ package org.apache.log4j;
/**
* This class is a minimal implementation of the original Log4J class.
*
- * @author Christian Trutz <christian.trutz@belaso.de>
+ * @author Christian Trutz
* */
public class Layout {
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Level.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Level.java
index 62ef578e..ddadbea0 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Level.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Level.java
@@ -26,21 +26,21 @@ import java.io.ObjectStreamException;
import java.io.Serializable;
/**
- Defines the minimum set of levels recognized by the system, that is
- <code>OFF</code>, <code>FATAL</code>, <code>ERROR</code>,
- <code>WARN</code>, <code>INFO</code>, <code>DEBUG</code> and
- <code>ALL</code>.
-
- <p>The <code>Level</code> class may be subclassed to define a larger
- level set.
-
- @author Ceki G&uuml;lc&uuml;
-
+ * Defines the minimum set of levels recognized by the system, that is
+ * <code>OFF</code>, <code>FATAL</code>, <code>ERROR</code>, <code>WARN</code>,
+ * <code>INFO</code>, <code>DEBUG</code> and <code>ALL</code>.
+ *
+ * <p>
+ * The <code>Level</code> class may be subclassed to define a larger level set.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ *
*/
public class Level extends Priority implements Serializable {
/**
* TRACE level integer value.
+ *
* @since 1.2.12
*/
public static final int TRACE_INT = 5000;
@@ -49,48 +49,52 @@ public class Level extends Priority implements Serializable {
public static final int X_TRACE_INT = DEBUG_INT - 100;
/**
- The <code>OFF</code> has the highest possible rank and is
- intended to turn off logging. */
+ * The <code>OFF</code> has the highest possible rank and is intended to turn
+ * off logging.
+ */
final static public Level OFF = new Level(OFF_INT, "OFF", 0);
/**
- The <code>FATAL</code> level designates very severe error
- events that will presumably lead the application to abort.
+ * The <code>FATAL</code> level designates very severe error events that will
+ * presumably lead the application to abort.
*/
final static public Level FATAL = new Level(FATAL_INT, "FATAL", 0);
/**
- The <code>ERROR</code> level designates error events that
- might still allow the application to continue running. */
+ * The <code>ERROR</code> level designates error events that might still allow
+ * the application to continue running.
+ */
final static public Level ERROR = new Level(ERROR_INT, "ERROR", 3);
/**
- The <code>WARN</code> level designates potentially harmful situations.
- */
+ * The <code>WARN</code> level designates potentially harmful situations.
+ */
final static public Level WARN = new Level(WARN_INT, "WARN", 4);
/**
- The <code>INFO</code> level designates informational messages
- that highlight the progress of the application at coarse-grained
- level. */
+ * The <code>INFO</code> level designates informational messages that highlight
+ * the progress of the application at coarse-grained level.
+ */
final static public Level INFO = new Level(INFO_INT, "INFO", 6);
/**
- The <code>DEBUG</code> Level designates fine-grained
- informational events that are most useful to debug an
- application. */
+ * The <code>DEBUG</code> Level designates fine-grained informational events
+ * that are most useful to debug an application.
+ */
final static public Level DEBUG = new Level(DEBUG_INT, "DEBUG", 7);
/**
- * The <code>TRACE</code> Level designates finer-grained
- * informational events than the <code>DEBUG</code level.
- * @since 1.2.12
- */
+ * The <code>TRACE</code> Level designates finer-grained informational events
+ * than the <code>DEBUG</code> level.
+ *
+ * @since 1.2.12
+ */
public static final Level TRACE = new Level(TRACE_INT, "TRACE", 7);
/**
- The <code>ALL</code> has the lowest possible rank and is intended to
- turn on all logging. */
+ * The <code>ALL</code> has the lowest possible rank and is intended to turn on
+ * all logging.
+ */
final static public Level ALL = new Level(ALL_INT, "ALL", 7);
/**
@@ -99,33 +103,47 @@ public class Level extends Priority implements Serializable {
static final long serialVersionUID = 3491141966387921974L;
/**
- Instantiate a Level object.
+ * Instantiate a Level object.
+ *
+ * @param level a level
+ * @param levelStr a level string
+ * @param syslogEquivalent the Syslog equivalent
*/
protected Level(int level, String levelStr, int syslogEquivalent) {
super(level, levelStr, syslogEquivalent);
}
/**
- Convert the string passed as argument to a level. If the
- conversion fails, then this method returns {@link #DEBUG}.
- */
+ * Convert the string passed as argument to a level. If the conversion fails,
+ * then this method returns {@link #DEBUG}.
+ *
+ * @param sArg a string
+ * @return corresponding Level
+ *
+ */
public static Level toLevel(String sArg) {
return (Level) toLevel(sArg, Level.DEBUG);
}
/**
- Convert an integer passed as argument to a level. If the
- conversion fails, then this method returns {@link #DEBUG}.
-
- */
+ * Convert an integer passed as argument to a level. If the conversion fails,
+ * then this method returns {@link #DEBUG}.
+ *
+ * @param val an int
+ * @return a level
+ */
public static Level toLevel(int val) {
return (Level) toLevel(val, Level.DEBUG);
}
/**
- Convert an integer passed as argument to a level. If the
- conversion fails, then this method returns the specified default.
- */
+ * Convert an integer passed as argument to a level. If the conversion fails,
+ * then this method returns the specified default.
+ *
+ * @param val a value
+ * @param defaultLevel a defaultLevel
+ * @return corresponding Level
+ */
public static Level toLevel(int val, Level defaultLevel) {
switch (val) {
case ALL_INT:
@@ -150,10 +168,13 @@ public class Level extends Priority implements Serializable {
}
/**
- Convert the string passed as argument to a level. If the
- conversion fails, then this method returns the value of
- <code>defaultLevel</code>.
- */
+ * Convert the string passed as argument to a level. If the conversion fails,
+ * then this method returns the value of <code>defaultLevel</code>.
+ *
+ * @param sArg a string
+ * @param defaultLevel a default level
+ * @return corresponding level
+ */
public static Level toLevel(String sArg, Level defaultLevel) {
if (sArg == null)
return defaultLevel;
@@ -181,8 +202,9 @@ public class Level extends Priority implements Serializable {
/**
* Custom deserialization of Level.
+ *
* @param s serialization stream.
- * @throws IOException if IO exception.
+ * @throws IOException if IO exception.
* @throws ClassNotFoundException if class not found.
*/
private void readObject(final ObjectInputStream s) throws IOException, ClassNotFoundException {
@@ -197,6 +219,7 @@ public class Level extends Priority implements Serializable {
/**
* Serialize level.
+ *
* @param s serialization stream.
* @throws IOException if exception during serialization.
*/
@@ -208,14 +231,15 @@ public class Level extends Priority implements Serializable {
}
/**
- * Resolved deserialized level to one of the stock instances.
- * May be overriden in classes derived from Level.
+ * Resolved deserialized level to one of the stock instances. May be overridden
+ * in classes derived from Level.
+ *
* @return resolved object.
* @throws ObjectStreamException if exception during resolution.
*/
private Object readResolve() throws ObjectStreamException {
//
- // if the deserizalized object is exactly an instance of Level
+ // if the deserialized object is exactly an instance of Level
//
if (getClass() == Level.class) {
return toLevel(level);
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Log4jLoggerFactory.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Log4jLoggerFactory.java
index 738b6a6c..eea3c97d 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Log4jLoggerFactory.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Log4jLoggerFactory.java
@@ -17,7 +17,6 @@
package org.apache.log4j;
import org.apache.log4j.spi.LoggerFactory;
-import org.slf4j.helpers.Util;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
@@ -34,24 +33,7 @@ import java.util.concurrent.ConcurrentMap;
class Log4jLoggerFactory {
// String, Logger
- private static ConcurrentMap<String, Logger> log4jLoggers = new ConcurrentHashMap<String, Logger>();
-
- private static final String LOG4J_DELEGATION_LOOP_URL = "http://www.slf4j.org/codes.html#log4jDelegationLoop";
-
- // check for delegation loops
- static {
- try {
- Class.forName("org.slf4j.impl.Log4jLoggerFactory");
- String part1 = "Detected both log4j-over-slf4j.jar AND slf4j-log4j12.jar on the class path, preempting StackOverflowError. ";
- String part2 = "See also " + LOG4J_DELEGATION_LOOP_URL + " for more details.";
-
- Util.report(part1);
- Util.report(part2);
- throw new IllegalStateException(part1 + part2);
- } catch (ClassNotFoundException e) {
- // this is the good case
- }
- }
+ private static final ConcurrentMap<String, Logger> log4jLoggers = new ConcurrentHashMap<>();
public static Logger getLogger(String name) {
org.apache.log4j.Logger instance = log4jLoggers.get(name);
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/LogManager.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/LogManager.java
index 51c9c85d..42619190 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/LogManager.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/LogManager.java
@@ -22,12 +22,11 @@ import java.util.Enumeration;
import java.util.Vector;
/**
- * <p/>
+ * <p>
* This class is a minimal implementation of the original
* <code>org.apache.log4j.LogManager</code> class (as found in log4j 1.2)
* delegating all calls to SLF4J.
- * <p/>
- * <p/>
+ * <p>
* This implementation does <b>NOT</b> implement the setRepositorySelector(),
* getLoggerRepository(), exists(), getCurrentLoggers(), shutdown() and
* resetConfiguration() methods which do not have SLF4J equivalents.
@@ -51,7 +50,7 @@ public class LogManager {
/**
* Returns a logger instance created by loggerFactory. This method was requested in
- * <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=234">bug #234</a>. Note that
+ * <a href="http://jira.qos.ch/browse/SLF4J-225">SLF4J-225</a>. Note that
* log4j-over-slf4j does not ship with a LoggerFactory implementation. If this
* method is called, the caller must provide his/her own implementation.
*
@@ -67,7 +66,7 @@ public class LogManager {
/**
* This bogus implementation returns an empty enumeration.
*
- * @return
+ * @return an Enumeration of current loggers
*/
public static Enumeration getCurrentLoggers() {
return new Vector().elements();
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Logger.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Logger.java
index 12ec1761..198b4e9e 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Logger.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Logger.java
@@ -24,7 +24,7 @@ import org.slf4j.spi.LocationAwareLogger;
* This class is a minimal implementation of the original
* <code>org.apache.log4j.Logger</code> class (as found in log4j 1.2)
* delegating all calls to a {@link org.slf4j.Logger} instance.
- * </p>
+ *
*
* @author Ceki G&uuml;lc&uuml;
* */
@@ -52,7 +52,7 @@ public class Logger extends Category {
/**
* Does the obvious.
*
- * @return
+ * @return the root logger
*/
public static Logger getRootLogger() {
return Log4jLoggerFactory.getLogger(org.slf4j.Logger.ROOT_LOGGER_NAME);
@@ -61,6 +61,8 @@ public class Logger extends Category {
/**
* Delegates to {@link org.slf4j.Logger#isTraceEnabled}
* method of SLF4J.
+ *
+ * @return whether this logger is enabled for the level TRACE
*/
public boolean isTraceEnabled() {
return slf4jLogger.isTraceEnabled();
@@ -68,6 +70,9 @@ public class Logger extends Category {
/**
* Delegates to {@link org.slf4j.Logger#trace(String)} method in SLF4J.
+ *
+ * @param message the message to log
+ *
*/
public void trace(Object message) {
differentiatedLog(null, LOGGER_FQCN, LocationAwareLogger.TRACE_INT, message, null);
@@ -76,9 +81,12 @@ public class Logger extends Category {
/**
* Delegates to {@link org.slf4j.Logger#trace(String,Throwable)}
* method in SLF4J.
+ *
+ * @param message the message to log
+ * @param t a Throwable to log
*/
public void trace(Object message, Throwable t) {
- differentiatedLog(null, LOGGER_FQCN, LocationAwareLogger.TRACE_INT, message, null);
+ differentiatedLog(null, LOGGER_FQCN, LocationAwareLogger.TRACE_INT, message, t);
}
}
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/MDC.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/MDC.java
index c4a8eff4..32118d4d 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/MDC.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/MDC.java
@@ -49,6 +49,8 @@ public class MDC {
* This method is not part of the Log4J public API. However it
* has been called by other projects. This method is here temporarily
* until projects who are depending on this method release fixes.
+ *
+ * @return a copy of the underlying map returned as a Hashtable
*/
@SuppressWarnings({ "rawtypes", "unchecked" })
@Deprecated
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/PatternLayout.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/PatternLayout.java
index a38df63b..a65fa2b9 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/PatternLayout.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/PatternLayout.java
@@ -20,7 +20,7 @@ package org.apache.log4j;
/**
* This class is a minimal implementation of the original Log4J class.
*
- * @author Christian Trutz <christian.trutz@belaso.de>
+ * @author Christian Trutz
* */
public class PatternLayout extends Layout {
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/Priority.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/Priority.java
index bb4f8d4a..08eebca9 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/Priority.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/Priority.java
@@ -21,8 +21,8 @@ package org.apache.log4j;
// Contributors: Kitching Simon <Simon.Kitching@OOOrange.ch>
/**
- <font color="#AA4444">Refrain from using this class directly, use
- the {@link Level} class instead</font>.
+ <b>Refrain from using this class directly, use
+ the {@link Level} class instead</b>.
@author Ceki G&uuml;lc&uuml; */
public class Priority {
@@ -48,21 +48,25 @@ public class Priority {
/**
* @deprecated Use {@link Level#ERROR} instead.
*/
+ @Deprecated
final static public Priority ERROR = new Level(ERROR_INT, "ERROR", 3);
/**
* @deprecated Use {@link Level#WARN} instead.
*/
+ @Deprecated
final static public Priority WARN = new Level(WARN_INT, "WARN", 4);
/**
* @deprecated Use {@link Level#INFO} instead.
*/
+ @Deprecated
final static public Priority INFO = new Level(INFO_INT, "INFO", 6);
/**
* @deprecated Use {@link Level#DEBUG} instead.
*/
+ @Deprecated
final static public Priority DEBUG = new Level(DEBUG_INT, "DEBUG", 7);
/**
@@ -76,6 +80,15 @@ public class Priority {
/**
Instantiate a level object.
+ @param
+ */
+
+ /**
+ * Instantiate a level object.
+ *
+ * @param level a level as in int
+ * @param levelStr a levelStr
+ * @param syslogEquivalent the syslog equivalent level integer
*/
protected Priority(int level, String levelStr, int syslogEquivalent) {
this.level = level;
@@ -98,20 +111,23 @@ public class Priority {
/**
Return the syslog equivalent of this priority as an integer.
+ @return the Syslog Equivalent of this Priority
*/
public final int getSyslogEquivalent() {
return syslogEquivalent;
}
/**
- Returns <code>true</code> if this level has a higher or equal
- level than the level passed as argument, <code>false</code>
- otherwise.
-
- <p>You should think twice before overriding the default
- implementation of <code>isGreaterOrEqual</code> method.
-
- */
+ * Returns <code>true</code> if this level has a higher or equal
+ * level than the level passed as argument, <code>false</code>
+ * otherwise.
+ *
+ * <p>You should think twice before overriding the default
+ * implementation of <code>isGreaterOrEqual</code> method.
+ *
+ * @param r a priority
+ * @return a boolean
+ */
public boolean isGreaterOrEqual(Priority r) {
return level >= r.level;
}
@@ -119,9 +135,11 @@ public class Priority {
/**
Return all possible priorities as an array of Level objects in
descending order.
-
+
@deprecated This method will be removed with no replacement.
+ @return array of all possible priorities
*/
+ @Deprecated
public static Priority[] getAllPossiblePriorities() {
return new Priority[] { Priority.FATAL, Priority.ERROR, Level.WARN, Priority.INFO, Priority.DEBUG };
}
@@ -134,7 +152,9 @@ public class Priority {
}
/**
- Returns the integer representation of this level.
+ * Returns the integer representation of this level.
+ *
+ * @return integer representation of this level
*/
public final int toInt() {
return level;
@@ -142,29 +162,46 @@ public class Priority {
/**
* @deprecated Please use the {@link Level#toLevel(String)} method instead.
+ *
+ * @param sArg a string to convert to a Priority
+ * @return the corresponding Priority
*/
+ @Deprecated
public static Priority toPriority(String sArg) {
return Level.toLevel(sArg);
}
/**
* @deprecated Please use the {@link Level#toLevel(int)} method instead.
+ *
+ * @param val an integer to convert to a Priority
+ * @return the corresponding Priority
*/
+ @Deprecated
public static Priority toPriority(int val) {
return toPriority(val, Priority.DEBUG);
}
/**
* @deprecated Please use the {@link Level#toLevel(int, Level)} method instead.
- */
+ *
+ * @param val an integer value
+ * @param defaultPriority a default priority value
+ * @return corresponding Priority value
+ */
+ @Deprecated
public static Priority toPriority(int val, Priority defaultPriority) {
return Level.toLevel(val, (Level) defaultPriority);
}
/**
* @deprecated Please use the {@link Level#toLevel(String, Level)} method instead.
+ * @param sArg string value
+ * @param defaultPriority a default Priority
+ * @return a Priority
*/
+ @Deprecated
public static Priority toPriority(String sArg, Priority defaultPriority) {
return Level.toLevel(sArg, (Level) defaultPriority);
}
-} \ No newline at end of file
+}
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/PropertyConfigurator.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/PropertyConfigurator.java
index baf4c136..6af30d06 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/PropertyConfigurator.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/PropertyConfigurator.java
@@ -23,7 +23,7 @@ import org.apache.log4j.spi.Configurator;
import org.apache.log4j.spi.LoggerRepository;
/**
- * An nop implementation of PropertyConfigurator.
+ * A no-op implementation of PropertyConfigurator.
*/
public class PropertyConfigurator implements Configurator {
public static void configure(Properties properties) {
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/RollingFileAppender.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/RollingFileAppender.java
index b3295974..7cecc550 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/RollingFileAppender.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/RollingFileAppender.java
@@ -22,7 +22,7 @@ import java.io.IOException;
/**
* This class is a minimal implementation of the original Log4J class.
*
- * @author Christian Trutz <christian.trutz@belaso.de>
+ * @author Christian Trutz
* */
public class RollingFileAppender {
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/helpers/LogLog.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/helpers/LogLog.java
index 01157ab7..0270e418 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/helpers/LogLog.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/helpers/LogLog.java
@@ -25,7 +25,7 @@ package org.apache.log4j.helpers;
<b>log4j.configDebug</b> variable.
<p>All log4j internal debug calls go to <code>System.out</code>
- where as internal error messages are sent to
+ whereas internal error messages are sent to
<code>System.err</code>. All internal messages are prepended with
the string "log4j: ".
@@ -37,20 +37,20 @@ public class LogLog {
/**
Defining this value makes log4j print log4j-internal debug
statements to <code>System.out</code>.
-
+
<p> The value of this string is <b>log4j.debug</b>.
-
- <p>Note that the search for all option names is case sensitive. */
+
+ <p>Note that the search for all option names is case-sensitive. */
public static final String DEBUG_KEY = "log4j.debug";
/**
Defining this value makes log4j components print log4j-internal
debug statements to <code>System.out</code>.
-
+
<p> The value of this string is <b>log4j.configDebug</b>.
-
- <p>Note that the search for all option names is case sensitive.
-
+
+ <p>Note that the search for all option names is case-sensitive.
+
@deprecated Use {@link #DEBUG_KEY} instead.
*/
public static final String CONFIG_DEBUG_KEY = "log4j.configDebug";
@@ -127,7 +127,7 @@ public class LogLog {
/**
In quite mode no LogLog generates strictly no output, not even
for errors.
-
+
@param quietMode A true for not
*/
public static void setQuietMode(boolean quietMode) {
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Configurator.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Configurator.java
index abf75609..f15cbf07 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Configurator.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Configurator.java
@@ -16,7 +16,6 @@
package org.apache.log4j.spi;
-import org.apache.log4j.spi.LoggerRepository;
import java.net.URL;
/**
@@ -41,10 +40,10 @@ public interface Configurator {
/**
Interpret a resource pointed by a URL and set up log4j accordingly.
-
+
The configuration is done relative to the <code>hierarchy</code>
parameter.
-
+
@param url The URL to parse
@param repository The hierarchy to operation upon.
*/
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/HierarchyEventListener.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/HierarchyEventListener.java
index a774949e..9271b70b 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/HierarchyEventListener.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/HierarchyEventListener.java
@@ -19,7 +19,7 @@ package org.apache.log4j.spi;
import org.apache.log4j.*;
/**
- Listen to events occuring within a {@link
+ Listen to events occurring within a {@link
org.apache.log4j.Hierarchy Hierarchy}.
@author Ceki G&uuml;lc&uuml;
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Layout.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Layout.java
deleted file mode 100644
index 32d49074..00000000
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/Layout.java
+++ /dev/null
@@ -1,20 +0,0 @@
-/*
- * Copyright 2001-2004 The Apache Software Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.log4j.spi;
-
-public class Layout {
-}
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerFactory.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerFactory.java
index c3e756d7..0f008bfa 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerFactory.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerFactory.java
@@ -21,7 +21,7 @@ import org.apache.log4j.Logger;
/**
Implement this interface to create new instances of Logger or
- a sub-class of Logger.
+ a subclass of Logger.
<p>See <code>examples/subclass/MyLogger.java</code> for an example.
diff --git a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerRepository.java b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerRepository.java
index 4decdb78..87a3b61d 100644
--- a/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerRepository.java
+++ b/log4j-over-slf4j/src/main/java/org/apache/log4j/spi/LoggerRepository.java
@@ -25,7 +25,7 @@ import java.util.Enumeration;
* <code>Loggers</code>. The relation between loggers in a repository
* depends on the repository but typically loggers are arranged in a
* named hierarchy.
- * <p/>
+ *
* <p>In addition to the creational methods, a
* <code>LoggerRepository</code> can be queried for existing loggers,
* can act as a point of registry for events related to loggers.
@@ -37,6 +37,8 @@ public interface LoggerRepository {
/**
* Add a {@link HierarchyEventListener} event to the repository.
+ *
+ * @param listener a listener
*/
public void addHierarchyEventListener(HierarchyEventListener listener);
diff --git a/log4j-over-slf4j/src/main/java9/module-info.java b/log4j-over-slf4j/src/main/java9/module-info.java
new file mode 100755
index 00000000..35017bea
--- /dev/null
+++ b/log4j-over-slf4j/src/main/java9/module-info.java
@@ -0,0 +1,8 @@
+module log4j {
+ requires org.slf4j;
+ requires java.xml;
+ exports org.apache.log4j;
+ exports org.apache.log4j.helpers;
+ exports org.apache.log4j.spi;
+ exports org.apache.log4j.xml;
+} \ No newline at end of file
diff --git a/log4j-over-slf4j/src/main/resources/META-INF/MANIFEST.MF b/log4j-over-slf4j/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 531f5842..00000000
--- a/log4j-over-slf4j/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,8 +0,0 @@
-Implementation-Title: log4j-over-slf4j
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: log4j.over.slf4j
-Bundle-Name: log4j-over-slf4j
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.apache.log4j;version=${log4j.version},org.apache.log4j.helpers;version=${log4j.version},org.apache.log4j.spi;version=${log4j.version},org.apache.log4j.xml;version=${log4j.version}
-Import-Package: org.slf4j;version=${slf4j.api.minimum.compatible.version}, org.slf4j.helpers;version=${slf4j.api.minimum.compatible.version}, org.slf4j.spi;version=${slf4j.api.minimum.compatible.version}
diff --git a/log4j-over-slf4j/src/test/java/org/apache/log4j/NDCTest.java b/log4j-over-slf4j/src/test/java/org/apache/log4j/test/NDCTest.java
index 74c2cd3b..ff87cff4 100644
--- a/log4j-over-slf4j/src/test/java/org/apache/log4j/NDCTest.java
+++ b/log4j-over-slf4j/src/test/java/org/apache/log4j/test/NDCTest.java
@@ -22,35 +22,46 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.apache.log4j;
+package org.apache.log4j.test;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+import org.apache.log4j.NDC;
/**
- * @author Ceki G&uuml;c&uuml;
+ * @author Ceki G&uuml;lc&uuml;
*/
-public class NDCTest extends TestCase {
+public class NDCTest {
+ @Before
public void setUp() {
assertEquals(0, NDC.getDepth());
}
+ @After
public void tearDown() {
NDC.clear();
}
+ @Test
public void testSmoke() {
NDC.push("a");
String back = NDC.pop();
assertEquals("a", back);
}
+ @Test
public void testPop() {
NDC.push("peek");
String back = NDC.peek();
assertEquals("peek", back);
}
+ @Test
public void testClear() {
NDC.push("clear");
NDC.clear();
diff --git a/log4j-over-slf4j/src/test/java/org/apache/log4j/Trivial.java b/log4j-over-slf4j/src/test/java/org/apache/log4j/test/Trivial.java
index 50edf2d3..6a8fbcc5 100644
--- a/log4j-over-slf4j/src/test/java/org/apache/log4j/Trivial.java
+++ b/log4j-over-slf4j/src/test/java/org/apache/log4j/test/Trivial.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.apache.log4j;
+package org.apache.log4j.test;
import org.apache.log4j.Logger;
diff --git a/log4j-over-slf4j/src/test/java/org/dummy/Bug131.java b/log4j-over-slf4j/src/test/java/org/dummy/Bug131.java
index c97d5666..4453ac22 100644
--- a/log4j-over-slf4j/src/test/java/org/dummy/Bug131.java
+++ b/log4j-over-slf4j/src/test/java/org/dummy/Bug131.java
@@ -24,16 +24,18 @@
*/
package org.dummy;
+import static org.junit.Assert.assertEquals;
+
import java.util.logging.Level;
import java.util.logging.LogRecord;
-import junit.framework.TestCase;
-
import org.apache.log4j.Category;
import org.apache.log4j.Logger;
+import org.junit.Test;
-public class Bug131 extends TestCase {
+public class Bug131 {
+ @Test
public void testBug131() {
ListHandler listHandler = new ListHandler();
diff --git a/log4j-over-slf4j/src/test/java/org/dummy/Bug139.java b/log4j-over-slf4j/src/test/java/org/dummy/Bug139.java
index f6cfe63f..1bb280ce 100644
--- a/log4j-over-slf4j/src/test/java/org/dummy/Bug139.java
+++ b/log4j-over-slf4j/src/test/java/org/dummy/Bug139.java
@@ -24,16 +24,18 @@
*/
package org.dummy;
+import static org.junit.Assert.assertEquals;
+
import java.util.logging.Level;
import java.util.logging.LogRecord;
-import junit.framework.TestCase;
-
import org.apache.log4j.Category;
import org.apache.log4j.Logger;
+import org.junit.Test;
-public class Bug139 extends TestCase {
+public class Bug139 {
+ @Test
public void test() {
ListHandler listHandler = new ListHandler();
java.util.logging.Logger root = java.util.logging.Logger.getLogger("");
diff --git a/log4j-over-slf4j/src/test/java/org/dummy/ListHandler.java b/log4j-over-slf4j/src/test/java/org/dummy/ListHandler.java
index c29ebfa1..2a237239 100644
--- a/log4j-over-slf4j/src/test/java/org/dummy/ListHandler.java
+++ b/log4j-over-slf4j/src/test/java/org/dummy/ListHandler.java
@@ -31,7 +31,7 @@ import java.util.logging.LogRecord;
public class ListHandler extends Handler {
- List<LogRecord> list = new ArrayList<LogRecord>();
+ List<LogRecord> list = new ArrayList<>();
public void close() throws SecurityException {
diff --git a/slf4j-jcl/LICENSE.txt b/osgi-over-slf4j/LICENSE.txt
index 508a2728..1a3d0532 100644
--- a/slf4j-jcl/LICENSE.txt
+++ b/osgi-over-slf4j/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/osgi-over-slf4j/pom.xml b/osgi-over-slf4j/pom.xml
index 1962dd6b..71c69929 100755
--- a/osgi-over-slf4j/pom.xml
+++ b/osgi-over-slf4j/pom.xml
@@ -1,3 +1,4 @@
+<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
@@ -6,12 +7,13 @@
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>osgi-over-slf4j</artifactId>
- <packaging>bundle</packaging>
+ <packaging>jar</packaging>
<name>OSGi LogService implemented over SLF4J</name>
<url>http://www.slf4j.org</url>
@@ -36,24 +38,27 @@
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
- <version>${project.version}</version>
<scope>provided</scope>
</dependency>
</dependencies>
+
<build>
<plugins>
+
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
- <version>2.3.7</version>
- <extensions>true</extensions>
<configuration>
<instructions>
- <Export-Package>org.osgi.service.log</Export-Package>
+ <Bundle-SymbolicName>org.slf4j.osgi-over-slf4j</Bundle-SymbolicName>
<Bundle-Activator>org.slf4j.osgi.logservice.impl.Activator</Bundle-Activator>
+ <Bundle-Category>osgi</Bundle-Category>
+ <_exportcontents combine.self="override" />
</instructions>
</configuration>
</plugin>
+
</plugins>
</build>
+
</project>
diff --git a/parent/pom.xml b/parent/pom.xml
new file mode 100644
index 00000000..b702b5ff
--- /dev/null
+++ b/parent/pom.xml
@@ -0,0 +1,397 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-bom</artifactId>
+ <version>2.0.12</version>
+ <relativePath>../pom.xml</relativePath>
+ </parent>
+
+ <artifactId>slf4j-parent</artifactId>
+ <packaging>pom</packaging>
+ <name>SLF4J Parent POM</name>
+ <description>SLF4J project parent pom.xml file</description>
+
+
+ <organization>
+ <name>QOS.ch</name>
+ <url>http://www.qos.ch</url>
+ </organization>
+ <inceptionYear>2005</inceptionYear>
+
+
+ <properties>
+ <!-- yyyy-MM-dd'T'HH:mm:ss'Z' -->
+ <project.build.outputTimestamp>2024-02-05T21:21:00Z</project.build.outputTimestamp>
+ <latest.1.version>1.7.36</latest.1.version>
+ <!-- java.util.ServiceLoader requires Java 6 -->
+ <jdk.version>8</jdk.version>
+ <maven.compiler.source>${jdk.version}</maven.compiler.source>
+ <maven.compiler.target>${jdk.version}</maven.compiler.target>
+ <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
+ <project.build.resourceEncoding>UTF-8</project.build.resourceEncoding>
+ <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
+ <!-- used in integration testing -->
+ <cal10n.version>0.8.1</cal10n.version>
+ <reload4j.version>1.2.22</reload4j.version>
+ <logback.version>1.2.10</logback.version>
+ <jcl.version>1.2</jcl.version>
+ <junit.version>4.13.1</junit.version>
+ <maven-site-plugin.version>3.7.1</maven-site-plugin.version>
+ <maven-compiler-plugin.version>3.10.1</maven-compiler-plugin.version>
+ <maven-surefire-plugin.version>3.0.0-M7</maven-surefire-plugin.version>
+ <maven-javadoc-plugin.version>3.6.3</maven-javadoc-plugin.version>
+ <maven-source-plugin.version>3.2.1</maven-source-plugin.version>
+ <maven-deploy-plugin.version>3.0.0-M1</maven-deploy-plugin.version>
+ <maven-jar-plugin.version>3.2.0</maven-jar-plugin.version>
+ <maven-jxr-plugin.version>3.1.1</maven-jxr-plugin.version>
+ <maven-bundle-plugin.version>5.1.9</maven-bundle-plugin.version>
+ </properties>
+
+
+ <dependencies>
+ <dependency>
+ <groupId>junit</groupId>
+ <artifactId>junit</artifactId>
+ <version>${junit.version}</version>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
+
+ <dependencyManagement>
+ <dependencies>
+
+ <dependency>
+ <groupId>ch.qos.reload4j</groupId>
+ <artifactId>reload4j</artifactId>
+ <version>${reload4j.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>ch.qos.cal10n</groupId>
+ <artifactId>cal10n-api</artifactId>
+ <version>${cal10n.version}</version>
+ </dependency>
+
+ </dependencies>
+ </dependencyManagement>
+
+ <build>
+ <extensions>
+ <extension>
+ <groupId>org.apache.maven.wagon</groupId>
+ <artifactId>wagon-ssh</artifactId>
+ <version>2.10</version>
+ </extension>
+ </extensions>
+
+ <resources>
+ <resource>
+ <directory>${project.basedir}/src/main/resources</directory>
+ <filtering>true</filtering>
+ </resource>
+
+ <resource>
+ <directory>..</directory>
+ <targetPath>META-INF</targetPath>
+ <includes>
+ <include>LICENSE.txt</include>
+ </includes>
+ </resource>
+ </resources>
+
+ <pluginManagement>
+ <plugins>
+
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>animal-sniffer-maven-plugin</artifactId>
+ <version>1.14</version>
+ <configuration>
+ <signature>
+ <groupId>org.codehaus.mojo.signature</groupId>
+ <artifactId>java16</artifactId>
+ <version>1.0</version>
+ </signature>
+ </configuration>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <version>${maven-deploy-plugin.version}</version>
+ </plugin>
+
+ </plugins>
+ </pluginManagement>
+
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <version>${maven-compiler-plugin.version}</version>
+ <executions>
+
+ <execution>
+ <id>default-compile</id>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ <configuration>
+ <source>${jdk.version}</source>
+ <target>${jdk.version}</target>
+ </configuration>
+ </execution>
+
+ <execution>
+ <id>module-compile</id>
+ <phase>compile</phase>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ <configuration>
+ <release>9</release>
+ <compileSourceRoots>
+ <compileSourceRoot>${project.basedir}/src/main/java9</compileSourceRoot>
+ </compileSourceRoots>
+ <multiReleaseOutput>true</multiReleaseOutput>
+ </configuration>
+ </execution>
+
+
+ </executions>
+
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-jar-plugin</artifactId>
+ <version>${maven-jar-plugin.version}</version>
+ <executions>
+ <!-- Repeated in slf4j-api/pom.xml -->
+ <execution>
+ <id>default-jar</id>
+ <phase>package</phase>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ <skipIfEmpty>true</skipIfEmpty>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <version>${maven-bundle-plugin.version}</version>
+ <configuration>
+ <supportIncrementalBuild>true</supportIncrementalBuild>
+ <!-- populated by the plugin itself -->
+ <instructions>
+ <Bundle-SymbolicName>${replacestring;${project.artifactId};-;.}</Bundle-SymbolicName>
+ <Bundle-Vendor>SLF4J.ORG</Bundle-Vendor>
+ <_snapshot/>
+ <_exportcontents>!META-INF.versions.9,*;-noimport:=true</_exportcontents>
+ <Bundle-Description>${project.description}</Bundle-Description>
+ <Bundle-DocURL>${project.url}</Bundle-DocURL>
+ <X-Compile-Source-JDK>${maven.compiler.source}</X-Compile-Source-JDK>
+ <X-Compile-Target-JDK>${maven.compiler.target}</X-Compile-Target-JDK>
+ <Implementation-Version>${project.version}</Implementation-Version>
+ <Implementation-Title>${project.artifactId}</Implementation-Title>
+ <Multi-Release>true</Multi-Release>
+ <_removeheaders>Private-Package,Bundle-SCM, Bundle-Developers, Include-Resource</_removeheaders>
+ </instructions>
+ </configuration>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <version>${maven-surefire-plugin.version}</version>
+ <configuration>
+ <forkCount>1</forkCount>
+ <reuseForks>false</reuseForks>
+ <reportFormat>plain</reportFormat>
+ <trimStackTrace>false</trimStackTrace>
+ <excludes>
+ <exclude>**/AllTest.java</exclude>
+ <exclude>**/PackageTest.java</exclude>
+ </excludes>
+ </configuration>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-source-plugin</artifactId>
+ <version>${maven-source-plugin.version}</version>
+ <executions>
+ <execution>
+ <phase>package</phase>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-site-plugin</artifactId>
+ <version>${maven-site-plugin.version}</version>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-project-info-reports-plugin</artifactId>
+ <version>3.0.0</version>
+ </plugin>
+ </plugins>
+
+ </build>
+
+ <profiles>
+ <profile>
+ <id>skipTests</id>
+ <properties>
+ <maven.test.skip>true</maven.test.skip>
+ </properties>
+ </profile>
+
+ <profile>
+ <id>javadocjar</id>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ <version>${maven-javadoc-plugin.version}</version>
+ <executions>
+ <execution>
+ <id>attach-javadocs</id>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <additionalparam>-Xdoclint:none</additionalparam>
+ <failOnError>false</failOnError>
+ <sourceFileExcludes>
+ <sourceFileExclude>**/module-info.java</sourceFileExclude>
+ </sourceFileExcludes>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+ </profile>
+
+ <profile>
+ <id>license</id>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>com.google.code.maven-license-plugin</groupId>
+ <artifactId>maven-license-plugin</artifactId>
+ <configuration>
+ <header>src/main/licenseHeader.txt</header>
+ <quiet>false</quiet>
+ <failIfMissing>true</failIfMissing>
+ <aggregate>true</aggregate>
+ <includes>
+ <include>src/**/*.java</include>
+ </includes>
+ <useDefaultExcludes>true</useDefaultExcludes>
+ <useDefaultMapping>true</useDefaultMapping>
+ <properties>
+ <year>1999</year>
+ </properties>
+ <headerDefinitions>
+ <headerDefinition>src/main/javadocHeaders.xml</headerDefinition>
+ </headerDefinitions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+
+ <pluginRepositories>
+ </pluginRepositories>
+ </profile>
+
+
+ <profile>
+ <id>generate-osgi-service-loader-mediator-entries</id>
+ <activation>
+ <file>
+ <exists>src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider</exists>
+ </file>
+ </activation>
+ <build>
+ <!-- Add the OSGi Service Loader Mediator Specification Manifest entries for each module that has a SLF4JServiceProvider Service-Loader file.-->
+ <plugins>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <configuration>
+ <instructions>
+ <Provide-Capability><![CDATA[
+ osgi.service;objectClass:List<String>="org.slf4j.spi.SLF4JServiceProvider";type=${slf4j.provider.type};effective:=active,
+ osgi.serviceloader;osgi.serviceloader="org.slf4j.spi.SLF4JServiceProvider";register:="${slf4j.provider.implementation}";type=${slf4j.provider.type}
+ ]]></Provide-Capability>
+ <Require-Capability><![CDATA[
+ osgi.extender;filter:="(&(osgi.extender=osgi.serviceloader.registrar)(version>=1.0.0)(!(version>=2.0.0)))"
+ ]]></Require-Capability>
+ </instructions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+ </profile>
+
+ <!--
+ <profile>
+ <id>travis</id>
+ <activation>
+ <property>
+ <name>env.TRAVIS</name>
+ <value>true</value>
+ </property>
+ </activation>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-toolchains-plugin</artifactId>
+ <version>1.1</version>
+ <executions>
+ <execution>
+ <id>toolchain</id>
+ <phase>none</phase>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+ </profile>
+ -->
+ </profiles>
+
+
+</project>
diff --git a/pom.xml b/pom.xml
index b2fb3e2c..bbebde28 100755
--- a/pom.xml
+++ b/pom.xml
@@ -1,24 +1,18 @@
<?xml version="1.0" encoding="UTF-8"?>
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.slf4j</groupId>
- <artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
-
+ <artifactId>slf4j-bom</artifactId>
+ <version>2.0.12</version>
<packaging>pom</packaging>
- <name>SLF4J</name>
- <description>Top SLF4J project pom.xml file</description>
+
<url>http://www.slf4j.org</url>
- <organization>
- <name>QOS.ch</name>
- <url>http://www.qos.ch</url>
- </organization>
- <inceptionYear>2005</inceptionYear>
+ <name>SLF4J BOM</name>
+ <description>SLF4J project BOM</description>
<licenses>
<license>
@@ -29,59 +23,31 @@
</licenses>
<scm>
- <url>https://github.com/ceki/slf4j</url>
- <connection>git@github.com:qos-ch/slf4j.git</connection>
+ <url>https://github.com/qos-ch/slf4j</url>
+ <connection>scm:git:https://github.com/qos-ch/slf4j.git</connection>
</scm>
- <properties>
- <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
- <required.jdk.version>1.5</required.jdk.version>
- <slf4j.api.minimum.compatible.version>1.6.0</slf4j.api.minimum.compatible.version>
- <cal10n.version>0.8.1</cal10n.version>
- <log4j.version>1.2.17</log4j.version>
- <logback.version>1.0.13</logback.version>
- <junit.version>4.10</junit.version>
- <maven-site-plugin.version>3.3</maven-site-plugin.version>
- <javadoc.plugin.version>2.10.2</javadoc.plugin.version>
- </properties>
-
- <developers>
- <developer>
- <id>ceki</id>
- <name>Ceki Gulcu</name>
- <email>ceki@qos.ch</email>
- </developer>
- </developers>
+ <!-- Inspired by Improving the Maven Bill of Materials (BOM) Pattern -->
+ <!-- https://www.garretwilson.com/blog/2023/06/14/improve-maven-bom-pattern -->
<modules>
+ <module>parent</module>
<module>slf4j-api</module>
- <!--<module>slf4j-scala-api</module>-->
<module>slf4j-simple</module>
<module>slf4j-nop</module>
<module>slf4j-jdk14</module>
+ <module>slf4j-jdk-platform-logging</module>
<module>slf4j-log4j12</module>
- <module>slf4j-jcl</module>
- <module>slf4j-android</module>
+ <module>slf4j-reload4j</module>
<module>slf4j-ext</module>
<module>jcl-over-slf4j</module>
<module>log4j-over-slf4j</module>
<module>jul-to-slf4j</module>
<module>osgi-over-slf4j</module>
<module>integration</module>
- <module>slf4j-site</module>
<module>slf4j-migrator</module>
</modules>
- <dependencies>
- <dependency>
- <groupId>junit</groupId>
- <artifactId>junit</artifactId>
- <version>${junit.version}</version>
- <scope>test</scope>
- </dependency>
- </dependencies>
-
-
<dependencyManagement>
<dependencies>
@@ -93,257 +59,169 @@
<dependency>
<groupId>org.slf4j</groupId>
+ <artifactId>slf4j-simple</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-nop</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+
+ <dependency>
+ <groupId>org.slf4j</groupId>
<artifactId>slf4j-jdk14</artifactId>
<version>${project.version}</version>
</dependency>
+
<dependency>
- <groupId>log4j</groupId>
- <artifactId>log4j</artifactId>
- <version>${log4j.version}</version>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-jdk-platform-logging</artifactId>
+ <version>${project.version}</version>
</dependency>
<dependency>
- <groupId>ch.qos.cal10n</groupId>
- <artifactId>cal10n-api</artifactId>
- <version>${cal10n.version}</version>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-log4j12</artifactId>
+ <version>${project.version}</version>
</dependency>
- </dependencies>
- </dependencyManagement>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-reload4j</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-ext</artifactId>
+ <version>${project.version}</version>
+ </dependency>
- <build>
- <extensions>
- <extension>
- <groupId>org.apache.maven.wagon</groupId>
- <artifactId>wagon-ssh</artifactId>
- <version>2.0</version>
- </extension>
- </extensions>
-
- <resources>
- <resource>
- <directory>src/main/resources</directory>
- <filtering>true</filtering>
- </resource>
- </resources>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>jcl-over-slf4j</artifactId>
+ <version>${project.version}</version>
+ </dependency>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-compiler-plugin</artifactId>
- <version>2.3.2</version>
- <configuration>
- <source>1.5</source>
- <target>1.5</target>
- </configuration>
- </plugin>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>log4j-over-slf4j</artifactId>
+ <version>${project.version}</version>
+ </dependency>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <version>2.3.1</version>
- </plugin>
-
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-surefire-plugin</artifactId>
- <version>2.10</version>
- <configuration>
- <forkMode>once</forkMode>
- <reportFormat>plain</reportFormat>
- <trimStackTrace>false</trimStackTrace>
- <excludes>
- <exclude>**/AllTest.java</exclude>
- <exclude>**/PackageTest.java</exclude>
- </excludes>
- </configuration>
- </plugin>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>jul-to-slf4j</artifactId>
+ <version>${project.version}</version>
+ </dependency>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-source-plugin</artifactId>
- <version>2.1.2</version>
- <executions>
- <execution>
- <phase>package</phase>
- <goals>
- <goal>jar</goal>
- </goals>
- </execution>
- </executions>
- </plugin>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>osgi-over-slf4j</artifactId>
+ <version>${project.version}</version>
+ </dependency>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-assembly-plugin</artifactId>
- <version>2.2</version>
- <configuration>
- <descriptors>
- <descriptor>src/main/assembly/source.xml</descriptor>
- </descriptors>
- <finalName>slf4j-${project.version}</finalName>
- <appendAssemblyId>false</appendAssemblyId>
- <outputDirectory>target/site/dist/</outputDirectory>
- </configuration>
- </plugin>
- <!-- as suggested in http://bugzilla.slf4j.org/show_bug.cgi?id=152 -->
- <plugin>
- <groupId>org.codehaus.mojo</groupId>
- <artifactId>build-helper-maven-plugin</artifactId>
- <version>1.7</version>
- <executions>
- <execution>
- <id>parse-version</id>
- <goals>
- <goal>parse-version</goal>
- </goals>
- </execution>
- </executions>
- </plugin>
+ </dependencies>
+ </dependencyManagement>
+
+ <distributionManagement>
- <!-- ====== site plugin ===== -->
+ <repository>
+ <id>sonatype-nexus-staging</id>
+ <url>https://oss.sonatype.org/service/local/staging/deploy/maven2/</url>
+ </repository>
+
+ </distributionManagement>
+
+ <developers>
+ <developer>
+ <id>ceki</id>
+ <name>Ceki Gulcu</name>
+ <email>ceki@qos.ch</email>
+ </developer>
+ </developers>
+
+ <build>
+ <plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-site-plugin</artifactId>
- <version>${maven-site-plugin.version}</version>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ <version>3.6.3</version>
<configuration>
- <reportPlugins>
-
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jxr-plugin</artifactId>
- <version>2.3</version>
- <configuration>
- <aggregate>true</aggregate>
- <javadocDir>target/site/apidocs/</javadocDir>
- <linkJavadoc>true</linkJavadoc>
- </configuration>
- </plugin>
-
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-javadoc-plugin</artifactId>
- <version>${javadoc.plugin.version}</version>
- <configuration>
- <!--<aggregate>true</aggregate>-->
- <excludePackageNames>org.slf4j.migrator:org.slf4j.migrator.*</excludePackageNames>
- <links>
- <link>
- http://java.sun.com/j2se/1.5.0/docs/api
- </link>
- </links>
- <groups>
- <group>
- <title>SLF4J packages</title>
- <packages>org.slf4j:org.slf4j.*</packages>
- </group>
-
- <group>
- <title>SLF4J extensions</title>
- <packages>
- org.slf4j.cal10n:org.slf4j.profiler:org.slf4j.ext:org.slf4j.instrumentation:org.slf4j.agent
- </packages>
- </group>
-
- <group>
- <title>Jakarta Commons Logging packages</title>
- <packages>org.apache.commons.*</packages>
- </group>
-
- <group>
- <title>java.util.logging (JUL) to SLF4J bridge</title>
- <packages>org.slf4j.bridge</packages>
- </group>
-
- <group>
- <title>Apache log4j</title>
- <packages>org.apache.log4j:org.apache.log4j.*</packages>
- </group>
- </groups>
- </configuration>
- </plugin>
-
- </reportPlugins>
+ <verbose>true</verbose>
+ <skippedModules>
+ slf4j-jdk-platform-logging,slf4j-migrator,osgi-over-slf4j
+ </skippedModules>
+ <detectLinks>true</detectLinks>
+ <doctitle>SLF4J project modules ${project.version}</doctitle>
+ <windowtitle>SLF4J javadoc</windowtitle>
+ <bottom><![CDATA[Copyright &copy; 2005-{currentYear} QOS.CH Sarl. All rights reserved]]></bottom>
+ <linksource>true</linksource>
+ <additionalOptions>
+ <additionalOption>-Xdoclint:none</additionalOption>
+ </additionalOptions>
+ <groups>
+ <group>
+ <title>SLF4J API packages</title>
+ <packages>org.slf4j:org.slf4j.spi:org.slf4j.event:org.slf4j.helpers</packages>
+ </group>
+
+ <group>
+ <title>slf4j-simple package</title>
+ <packages>org.slf4j.simple</packages>
+ </group>
+
+ <group>
+ <title>slf4j-nop package</title>
+ <packages>org.slf4j.nop</packages>
+ </group>
+
+
+ <group>
+ <title>slf4j-jdk14 package</title>
+ <packages>org.slf4j.jul</packages>
+ </group>
+
+
+ <group>
+ <title>slf4j-reload4j package</title>
+ <packages>org.slf4j.reload4j</packages>
+ </group>
+
+
+ <group>
+ <title>SLF4J extensions</title>
+ <packages>
+ org.slf4j.cal10n:org.slf4j.profiler:org.slf4j.ext:org.slf4j.instrumentation:org.slf4j.agent
+ </packages>
+ </group>
+
+ <group>
+ <title>Jakarta Commons Logging packages</title>
+ <packages>org.apache.commons.*</packages>
+ </group>
+
+ <group>
+ <title>java.util.logging (JUL) to SLF4J bridge</title>
+ <packages>org.slf4j.bridge</packages>
+ </group>
+
+ <group>
+ <title>log4j-over-slf4j redirection</title>
+ <packages>org.apache.log4j:org.apache.log4j.*</packages>
+ </group>
+ </groups>
+
</configuration>
</plugin>
</plugins>
-
</build>
<profiles>
- <profile>
- <id>skipTests</id>
- <properties>
- <maven.test.skip>true</maven.test.skip>
- </properties>
- </profile>
-
- <profile>
- <id>javadocjar</id>
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-javadoc-plugin</artifactId>
- <version>${javadoc.plugin.version}</version>
- <executions>
- <execution>
- <id>attach-javadocs</id>
- <goals>
- <goal>jar</goal>
- </goals>
- </execution>
- </executions>
- </plugin>
- </plugins>
- </build>
- </profile>
-
- <profile>
- <id>license</id>
- <build>
- <plugins>
- <plugin>
- <groupId>com.google.code.maven-license-plugin</groupId>
- <artifactId>maven-license-plugin</artifactId>
- <configuration>
- <header>src/main/licenseHeader.txt</header>
- <quiet>false</quiet>
- <failIfMissing>true</failIfMissing>
- <aggregate>true</aggregate>
- <includes>
- <include>src/**/*.java</include>
- </includes>
- <useDefaultExcludes>true</useDefaultExcludes>
- <useDefaultMapping>true</useDefaultMapping>
- <properties>
- <year>1999</year>
- </properties>
- <headerDefinitions>
- <headerDefinition>src/main/javadocHeaders.xml</headerDefinition>
- </headerDefinitions>
- </configuration>
- </plugin>
- </plugins>
- </build>
-
- <pluginRepositories>
- <pluginRepository>
- <id>mc-release</id>
- <name>Local Maven repository of releases</name>
- <url>http://mc-repo.googlecode.com/svn/maven2/releases</url>
- <snapshots>
- <enabled>false</enabled>
- </snapshots>
- <releases>
- <enabled>true</enabled>
- </releases>
- </pluginRepository>
- </pluginRepositories>
- </profile>
<profile>
<id>sign-artifacts</id>
@@ -366,25 +244,6 @@
</plugins>
</build>
</profile>
-
</profiles>
- <pluginRepositories>
- </pluginRepositories>
-
- <distributionManagement>
- <site>
- <id>pixie</id>
- <url>scp://pixie.qos.ch/var/www/www.slf4j.org/htdocs/</url>
- </site>
-
- <repository>
- <!--<id>pixie</id>-->
- <!--<url>scp://pixie.qos.ch/var/mvnrepo/</url>-->
- <id>sonatype-nexus-staging</id>
- <url>https://oss.sonatype.org/service/local/staging/deploy/maven2/</url>
- </repository>
-
- </distributionManagement>
-
</project>
diff --git a/release.sh b/release.sh
new file mode 100755
index 00000000..30daedec
--- /dev/null
+++ b/release.sh
@@ -0,0 +1,61 @@
+
+# Javadoc
+
+#JDK8 - mvn site:site
+#rscpSLF4J apidocs/
+
+# JDK 11+
+# adding the following
+#mvn -Ddoclint=none -Dadditionalparam=-Xdoclint:none javadoc:aggregate
+
+
+#mvn versions:set -DgenerateBackupPoms=false -DnewVersion=${VERSION_NUMBER}
+
+MVN='/java/maven-3.5.2//bin/mvn'
+
+function checkExit(){
+ if test "$?" != "0"; then
+ echo Command $1 exited with abnormal status
+ exit 1;
+ else echo $?
+ fi
+}
+
+function echoRunAndCheck () { # echo and then run the command
+ echo $1
+ $1
+ ret=$?
+ if test "$ret" != "0";
+ then
+ echo Failed command: $1
+ exit 1;
+ else echo Successful run: $1
+ fi
+}
+
+echoRunAndCheck "$MVN clean"
+
+echoRunAndCheck "$MVN install"
+
+#echoRunAndCheck "$MVN site:site"
+
+#echoRunAndCheck "$MVN javadoc:aggregate"
+
+#echoRunAndCheck "$MVN jxr:aggregate"
+
+
+if [ ! -z "$PASS" ]
+then
+ export GPG_TTY=$(tty)
+ echoRunAndCheck "$MVN deploy -P javadocjar,sign-artifacts"
+fi
+
+
+git tag -m "tagging" -a v_${VERSION_NUMBER}
+git push --tags
+
+#Update release version and add next version on jira
+
+
+
+echo Full Success
diff --git a/slf4j-android/.gitignore b/slf4j-android/.gitignore
deleted file mode 100755
index 7792e06b..00000000
--- a/slf4j-android/.gitignore
+++ /dev/null
@@ -1,2 +0,0 @@
-bin/
-gen/
diff --git a/slf4j-android/AndroidManifest.xml b/slf4j-android/AndroidManifest.xml
deleted file mode 100755
index a2b9e40c..00000000
--- a/slf4j-android/AndroidManifest.xml
+++ /dev/null
@@ -1,7 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
- package="org.slf4j"
- android:versionCode="176"
- android:versionName="1.7.6">
- <uses-sdk android:minSdkVersion="3" />
-</manifest> \ No newline at end of file
diff --git a/slf4j-android/pom.xml b/slf4j-android/pom.xml
deleted file mode 100644
index 28a3b41a..00000000
--- a/slf4j-android/pom.xml
+++ /dev/null
@@ -1,63 +0,0 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-
- <parent>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
- </parent>
-
- <modelVersion>4.0.0</modelVersion>
-
- <artifactId>slf4j-android</artifactId>
- <packaging>jar</packaging>
- <name>SLF4J Android Binding</name>
- <description>SLF4J Android Binding</description>
- <url>http://www.slf4j.org</url>
-
- <dependencies>
- <dependency>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-api</artifactId>
- <version>${project.version}</version>
- </dependency>
-
- <dependency>
- <groupId>com.google.android</groupId>
- <artifactId>android</artifactId>
- <version>1.5_r4</version>
- <scope>provided</scope>
- </dependency>
- </dependencies>
-
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
-
- <plugin>
- <!-- Google Android requires class compatibility set to 5.0 -->
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-compiler-plugin</artifactId>
- <configuration>
- <source>${required.jdk.version}</source>
- <target>${required.jdk.version}</target>
- </configuration>
- </plugin>
- </plugins>
- </build>
-
-</project> \ No newline at end of file
diff --git a/slf4j-android/project.properties b/slf4j-android/project.properties
deleted file mode 100755
index 0d4e7607..00000000
--- a/slf4j-android/project.properties
+++ /dev/null
@@ -1,14 +0,0 @@
-# This file is automatically generated by Android Tools.
-# Do not modify this file -- YOUR CHANGES WILL BE ERASED!
-#
-# This file must be checked in Version Control Systems.
-#
-# To customize properties used by the Ant build system use,
-# "ant.properties", and override values to adapt the script to your
-# project structure.
-
-android.library=true
-# Indicates whether an apk should be generated for each density.
-split.density=false
-# Project target.
-target=android-3
diff --git a/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerAdapter.java b/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerAdapter.java
deleted file mode 100755
index c13a7ce8..00000000
--- a/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerAdapter.java
+++ /dev/null
@@ -1,553 +0,0 @@
-/*
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import android.util.Log;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MarkerIgnoringBase;
-import org.slf4j.helpers.MessageFormatter;
-
-/**
- * <p>A simple implementation that delegates all log requests to the Google Android
- * logging facilities. Note that this logger does not support {@link org.slf4j.Marker}.
- * Methods taking marker data as parameter simply invoke the eponymous method
- * without the Marker argument, discarding any marker data in the process.</p>
- *
- * <p>The logging levels specified for SLF4J can be almost directly mapped to
- * the levels that exist in the Google Android platform. The following table
- * shows the mapping implemented by this logger.</p>
- *
- * <table border="1">
- * <tr><th><b>SLF4J<b></th><th><b>Android</b></th></tr>
- * <tr><td>TRACE</td><td>{@link android.util.Log#VERBOSE}</td></tr>
- * <tr><td>DEBUG</td><td>{@link android.util.Log#DEBUG}</td></tr>
- * <tr><td>INFO</td><td>{@link android.util.Log#INFO}</td></tr>
- * <tr><td>WARN</td><td>{@link android.util.Log#WARN}</td></tr>
- * <tr><td>ERROR</td><td>{@link android.util.Log#ERROR}</td></tr>
- * </table>
- *
- * <p>Use loggers as usual:
- * <ul>
- * <li>
- * Declare a logger<br/>
- * <code>private static final Logger logger = LoggerFactory.getLogger(MyClass.class);</code>
- * </li>
- * <li>
- * Invoke logging methods, e.g.,<br/>
- * <code>logger.debug("Some log message. Details: {}", someObject);</code><br/>
- * <code>logger.debug("Some log message with varargs. Details: {}, {}, {}", someObject1, someObject2, someObject3);</code>
- * </li>
- * </ul>
- * </p>
- *
- * <p>Logger instances created using the LoggerFactory are named either according to the name
- * or the fully qualified class name of the class given as a parameter.
- * Each logger name will be used as the log message tag on the Android platform.
- * However, tag names cannot be longer than 23 characters so if logger name exceeds this limit then
- * it will be truncated by the LoggerFactory. The following examples illustrate this.
- * <table border="1">
- * <tr><th><b>Original Name<b></th><th><b>Truncated Name</b></th></tr>
- * <tr><td>org.example.myproject.mypackage.MyClass</td><td>o*.e*.m*.m*.MyClass</td></tr>
- * <tr><td>o.e.myproject.mypackage.MyClass</td><td>o.e.m*.m*.MyClass</td></tr>
- * <tr><td>org.example.ThisNameIsWayTooLongAndWillBeTruncated</td><td>*LongAndWillBeTruncated</td></tr>
- * <tr><td>ThisNameIsWayTooLongAndWillBeTruncated</td><td>*LongAndWillBeTruncated</td></tr>
- * </table>
- * </p>
- *
- * @author Andrey Korzhevskiy <a.korzhevskiy@gmail.com>
- */
-class AndroidLoggerAdapter extends MarkerIgnoringBase {
- private static final long serialVersionUID = -1227274521521287937L;
-
-
- /**
- * Package access allows only {@link AndroidLoggerFactory} to instantiate
- * SimpleLogger instances.
- */
- AndroidLoggerAdapter(String tag) {
- this.name = tag;
- }
-
- /**
- * Is this logger instance enabled for the VERBOSE level?
- *
- * @return True if this Logger is enabled for level VERBOSE, false otherwise.
- */
- public boolean isTraceEnabled() {
- return isLoggable(Log.VERBOSE);
- }
-
- /**
- * Log a message object at level VERBOSE.
- *
- * @param msg
- * - the message object to be logged
- */
- public void trace(String msg) {
- log(Log.VERBOSE, msg, null);
- }
-
- /**
- * Log a message at level VERBOSE according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level VERBOSE.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void trace(String format, Object arg) {
- formatAndLog(Log.VERBOSE, format, arg);
- }
-
- /**
- * Log a message at level VERBOSE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the VERBOSE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void trace(String format, Object arg1, Object arg2) {
- formatAndLog(Log.VERBOSE, format, arg1, arg2);
- }
-
- /**
- * Log a message at level VERBOSE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the VERBOSE level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void trace(String format, Object... argArray) {
- formatAndLog(Log.VERBOSE, format, argArray);
- }
-
- /**
- * Log an exception (throwable) at level VERBOSE with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void trace(String msg, Throwable t) {
- log(Log.VERBOSE, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the DEBUG level?
- *
- * @return True if this Logger is enabled for level DEBUG, false otherwise.
- */
- public boolean isDebugEnabled() {
- return isLoggable(Log.DEBUG);
- }
-
- /**
- * Log a message object at level DEBUG.
- *
- * @param msg
- * - the message object to be logged
- */
- public void debug(String msg) {
- log(Log.DEBUG, msg, null);
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level DEBUG.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void debug(String format, Object arg) {
- formatAndLog(Log.DEBUG, format, arg);
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the DEBUG level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void debug(String format, Object arg1, Object arg2) {
- formatAndLog(Log.DEBUG, format, arg1, arg2);
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the DEBUG level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void debug(String format, Object... argArray) {
- formatAndLog(Log.DEBUG, format, argArray);
- }
-
- /**
- * Log an exception (throwable) at level DEBUG with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void debug(String msg, Throwable t) {
- log(Log.VERBOSE, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the INFO level?
- *
- * @return True if this Logger is enabled for the INFO level, false otherwise.
- */
- public boolean isInfoEnabled() {
- return isLoggable(Log.INFO);
- }
-
- /**
- * Log a message object at the INFO level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void info(String msg) {
- log(Log.INFO, msg, null);
- }
-
- /**
- * Log a message at level INFO according to the specified format and argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void info(String format, Object arg) {
- formatAndLog(Log.INFO, format, arg);
- }
-
- /**
- * Log a message at the INFO level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void info(String format, Object arg1, Object arg2) {
- formatAndLog(Log.INFO, format, arg1, arg2);
- }
-
- /**
- * Log a message at level INFO according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void info(String format, Object... argArray) {
- formatAndLog(Log.INFO, format, argArray);
- }
-
- /**
- * Log an exception (throwable) at the INFO level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void info(String msg, Throwable t) {
- log(Log.INFO, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the WARN level?
- *
- * @return True if this Logger is enabled for the WARN level, false
- * otherwise.
- */
- public boolean isWarnEnabled() {
- return isLoggable(Log.WARN);
- }
-
- /**
- * Log a message object at the WARN level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void warn(String msg) {
- log(Log.WARN, msg, null);
- }
-
- /**
- * Log a message at the WARN level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void warn(String format, Object arg) {
- formatAndLog(Log.WARN, format, arg);
- }
-
- /**
- * Log a message at the WARN level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void warn(String format, Object arg1, Object arg2) {
- formatAndLog(Log.WARN, format, arg1, arg2);
- }
-
- /**
- * Log a message at level WARN according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void warn(String format, Object... argArray) {
- formatAndLog(Log.WARN, format, argArray);
- }
-
- /**
- * Log an exception (throwable) at the WARN level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void warn(String msg, Throwable t) {
- log(Log.WARN, msg, t);
- }
-
- /**
- * Is this logger instance enabled for level ERROR?
- *
- * @return True if this Logger is enabled for level ERROR, false otherwise.
- */
- public boolean isErrorEnabled() {
- return isLoggable(Log.ERROR);
- }
-
- /**
- * Log a message object at the ERROR level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void error(String msg) {
- log(Log.ERROR, msg, null);
- }
-
- /**
- * Log a message at the ERROR level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void error(String format, Object arg) {
- formatAndLog(Log.ERROR, format, arg);
- }
-
- /**
- * Log a message at the ERROR level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void error(String format, Object arg1, Object arg2) {
- formatAndLog(Log.ERROR, format, arg1, arg2);
- }
-
- /**
- * Log a message at level ERROR according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void error(String format, Object... argArray) {
- formatAndLog(Log.ERROR, format, argArray);
- }
-
- /**
- * Log an exception (throwable) at the ERROR level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void error(String msg, Throwable t) {
- log(Log.ERROR, msg, t);
- }
-
- private void formatAndLog(int priority, String format, Object... argArray) {
- if (isLoggable(priority)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- _log(priority, ft.getMessage(), ft.getThrowable());
- }
- }
-
- private void log(int priority, String message, Throwable throwable) {
- if (isLoggable(priority)) {
- _log(priority, message, throwable);
- }
- }
-
- private boolean isLoggable(int priority) {
- return Log.isLoggable(name, priority);
- }
-
- private void _log(int priority, String message, Throwable throwable) {
- if (throwable != null) {
- message += '\n' + Log.getStackTraceString(throwable);
- }
- Log.println(priority, name, message);
- }
-} \ No newline at end of file
diff --git a/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerFactory.java b/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerFactory.java
deleted file mode 100755
index f27ff551..00000000
--- a/slf4j-android/src/main/java/org/slf4j/impl/AndroidLoggerFactory.java
+++ /dev/null
@@ -1,124 +0,0 @@
-/*
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.Logger;
-
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
-
-/**
- * AndroidLoggerFactory is an implementation of {@link ILoggerFactory} returning
- * the appropriately named {@link AndroidLoggerFactory} instance.
- *
- * @author Andrey Korzhevskiy <a.korzhevskiy@gmail.com>
- */
-class AndroidLoggerFactory implements ILoggerFactory {
- static final String ANONYMOUS_TAG = "null";
- static final int TAG_MAX_LENGTH = 23;
-
- private final ConcurrentMap<String, Logger> loggerMap = new ConcurrentHashMap<String, Logger>();
-
- /**
- * Return an appropriate {@link AndroidLoggerAdapter} instance by name.
- */
- public Logger getLogger(String name) {
- String tag = loggerNameToTag(name);
- Logger logger = loggerMap.get(tag);
- if (logger == null) {
- Logger newInstance = new AndroidLoggerAdapter(tag);
- Logger oldInstance = loggerMap.putIfAbsent(tag, newInstance);
- logger = oldInstance == null ? newInstance : oldInstance;
- }
- return logger;
- }
-
- /**
- * Tag names cannot be longer than {@value #TAG_MAX_LENGTH} characters on Android platform.
- *
- * Returns the short logger tag (up to {@value #TAG_MAX_LENGTH} characters) for the given logger name.
- * Traditionally loggers are named by fully-qualified Java classes; this
- * method attempts to return a concise identifying part of such names.
- *
- * See also:
- * android/system/core/include/cutils/property.h
- * android/frameworks/base/core/jni/android_util_Log.cpp
- * dalvik.system.DalvikLogging
- *
- */
- static String loggerNameToTag(String loggerName) {
- // Anonymous logger
- if (loggerName == null) {
- return ANONYMOUS_TAG;
- }
-
- int length = loggerName.length();
- if (length <= TAG_MAX_LENGTH) {
- return loggerName;
- }
-
- int tagLength = 0;
- int lastTokenIndex = 0;
- int lastPeriodIndex;
- StringBuilder tagName = new StringBuilder(TAG_MAX_LENGTH + 3);
- while ((lastPeriodIndex = loggerName.indexOf('.', lastTokenIndex)) != -1) {
- tagName.append(loggerName.charAt(lastTokenIndex));
- // token of one character appended as is otherwise truncate it to one character
- int tokenLength = lastPeriodIndex - lastTokenIndex;
- if (tokenLength > 1) {
- tagName.append('*');
- }
- tagName.append('.');
- lastTokenIndex = lastPeriodIndex + 1;
-
- // check if name is already too long
- tagLength = tagName.length();
- if (tagLength > TAG_MAX_LENGTH) {
- return getSimpleName(loggerName);
- }
- }
-
- // Either we had no useful dot location at all
- // or last token would exceed TAG_MAX_LENGTH
- int tokenLength = length - lastTokenIndex;
- if (tagLength == 0 || (tagLength + tokenLength) > TAG_MAX_LENGTH) {
- return getSimpleName(loggerName);
- }
-
- // last token (usually class name) appended as is
- tagName.append(loggerName, lastTokenIndex, length);
- return tagName.toString();
- }
-
- private static String getSimpleName(String loggerName) {
- // Take leading part and append '*' to indicate that it was truncated
- int length = loggerName.length();
- int lastPeriodIndex = loggerName.lastIndexOf('.');
- return lastPeriodIndex != -1 && length - (lastPeriodIndex + 1) <= TAG_MAX_LENGTH
- ? loggerName.substring(lastPeriodIndex + 1)
- : '*' + loggerName.substring(length - TAG_MAX_LENGTH + 1);
- }
-} \ No newline at end of file
diff --git a/slf4j-android/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-android/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index 7817d9bf..00000000
--- a/slf4j-android/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/**
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- * @author Andrey Korzhevskiy <a.korzhevskiy@gmail.com>
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled against.
- * The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
-
- private static final String loggerFactoryClassStr = AndroidLoggerFactory.class.getName();
-
- /**
- * The ILoggerFactory instance returned by the {@link #getLoggerFactory} method
- * should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- loggerFactory = new AndroidLoggerFactory();
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-android/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-android/src/main/java/org/slf4j/impl/StaticMDCBinder.java
deleted file mode 100644
index a484c525..00000000
--- a/slf4j-android/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/**
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.helpers.NOPMDCAdapter;
-import org.slf4j.spi.MDCAdapter;
-
-
-/**
- * This implementation is bound to {@link NOPMDCAdapter}.
- *
- * @author Ceki G&uuml;lc&uuml;
- * @author Andrey Korzhevskiy <a.korzhevskiy@gmail.com>
- */
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link NOPMDCAdapter}.
- */
- public MDCAdapter getMDCA() {
- return new NOPMDCAdapter();
- }
-
- public String getMDCAdapterClassStr() {
- return NOPMDCAdapter.class.getName();
- }
-}
diff --git a/slf4j-android/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-android/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 52b05bac..00000000
--- a/slf4j-android/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- * @author Andrey Korzhevskiy <a.korzhevskiy@gmail.com>
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-}
diff --git a/slf4j-android/src/main/resources/META-INF/MANIFEST.MF b/slf4j-android/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index d71f94cb..00000000
--- a/slf4j-android/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,9 +0,0 @@
-Implementation-Title: slf4j-android
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.android
-Bundle-Name: slf4j-android
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-android/src/test/java/org/slf4j/impl/AndroidLoggerFactoryTest.java b/slf4j-android/src/test/java/org/slf4j/impl/AndroidLoggerFactoryTest.java
deleted file mode 100644
index 5c854892..00000000
--- a/slf4j-android/src/test/java/org/slf4j/impl/AndroidLoggerFactoryTest.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (c) 2004-2013 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.junit.Test;
-
-import static junit.framework.Assert.assertEquals;
-
-public class AndroidLoggerFactoryTest {
- @Test
- public void shortLoggerNames() {
- assertEquals("o.test.p.TestClass", AndroidLoggerFactory.loggerNameToTag("o.test.p.TestClass"));
- assertEquals("ex.test.TestClass", AndroidLoggerFactory.loggerNameToTag("ex.test.TestClass"));
- assertEquals("MyClass", AndroidLoggerFactory.loggerNameToTag("MyClass"));
- }
-
- @Test
- public void emptyLoggerNames() {
- assertEquals(AndroidLoggerFactory.ANONYMOUS_TAG, AndroidLoggerFactory.loggerNameToTag(null));
- assertEquals("", AndroidLoggerFactory.loggerNameToTag(""));
- }
-
- @Test
- public void simpleLoggerName() {
- assertEquals("o*.t*.p*.TestClass", AndroidLoggerFactory.loggerNameToTag("org.test.package.TestClass"));
- }
-
- @Test
- public void loggerNameWithOneCharPackage() {
- assertEquals("o.t*.p*.p*.TestClass", AndroidLoggerFactory.loggerNameToTag("o.test.project.package.TestClass"));
- assertEquals("o.t*.p*.p.TestClass", AndroidLoggerFactory.loggerNameToTag("o.test.project.p.TestClass"));
- }
-
- @Test
- public void longLoggerName() {
- assertEquals("AndroidLoggerFactory", AndroidLoggerFactory.loggerNameToTag("org.slf4j.impl.AndroidLoggerFactory"));
- }
-
- @Test
- public void veryLongLoggerName() {
- assertEquals("*meAndShouldBeTruncated", AndroidLoggerFactory.loggerNameToTag("IAmAVeryLongLoggerNameAndShouldBeTruncated"));
- }
-
- @Test
- public void oneWordLoggerName() {
- assertEquals("TestClass", AndroidLoggerFactory.loggerNameToTag("TestClass"));
- }
-
- @Test
- public void weirdLoggerNames() {
- assertEquals("WeirdLoggerName.", AndroidLoggerFactory.loggerNameToTag("WeirdLoggerName."));
- assertEquals(".WeirdLoggerName", AndroidLoggerFactory.loggerNameToTag(".WeirdLoggerName"));
- assertEquals(".WeirdLoggerName.", AndroidLoggerFactory.loggerNameToTag(".WeirdLoggerName."));
- assertEquals(".", AndroidLoggerFactory.loggerNameToTag("."));
- assertEquals("..", AndroidLoggerFactory.loggerNameToTag(".."));
- }
-}
diff --git a/slf4j-api/LICENSE.txt b/slf4j-api/LICENSE.txt
index 508a2728..e4079f54 100644
--- a/slf4j-api/LICENSE.txt
+++ b/slf4j-api/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2023 QOS.ch
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-api/pom.xml b/slf4j-api/pom.xml
index 6d1f6ba7..e8460b21 100755
--- a/slf4j-api/pom.xml
+++ b/slf4j-api/pom.xml
@@ -1,5 +1,5 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
@@ -7,7 +7,8 @@
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-api</artifactId>
@@ -18,8 +19,9 @@
<url>http://www.slf4j.org</url>
- <dependencies>
- </dependencies>
+ <properties>
+ <module-name>org.slf4j</module-name>
+ </properties>
<build>
<plugins>
@@ -40,22 +42,12 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
+ <version>${maven-jar-plugin.version}</version>
<executions>
<execution>
<id>bundle-test-jar</id>
<phase>package</phase>
<goals>
- <goal>jar</goal>
<goal>test-jar</goal>
</goals>
</execution>
@@ -63,21 +55,22 @@
</plugin>
<plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-antrun-plugin</artifactId>
- <executions>
- <execution>
- <phase>process-classes</phase>
- <goals>
- <goal>run</goal>
- </goals>
- </execution>
- </executions>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
<configuration>
- <tasks>
- <echo>Removing slf4j-api's dummy StaticLoggerBinder and StaticMarkerBinder</echo>
- <delete dir="target/classes/org/slf4j/impl"/>
- </tasks>
+ <instructions>
+ <Import-Package>org.slf4j.spi;version="${range;[===,+);${version_cleanup;${project.version}}}"</Import-Package>
+ <!-- Export the client/user package of slf4j-api version 1 to make the slf4j-api bundle in version 2 usable for bundles that only import slf4j-1.x -->
+ <_exportcontents><![CDATA[
+ *,\
+ org.slf4j;version="${latest.1.version}",\
+ org.slf4j.helpers;version="${latest.1.version}"
+ ]]></_exportcontents>
+ <Require-Capability><![CDATA[
+ osgi.extender;filter:="(&(osgi.extender=osgi.serviceloader.processor)(version>=1.0.0)(!(version>=2.0.0)))",
+ osgi.serviceloader;filter:="(osgi.serviceloader=org.slf4j.spi.SLF4JServiceProvider)";osgi.serviceloader="org.slf4j.spi.SLF4JServiceProvider"
+ ]]></Require-Capability>
+ </instructions>
</configuration>
</plugin>
@@ -85,4 +78,4 @@
</build>
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-api/src/main/java/org/slf4j/ILoggerFactory.java b/slf4j-api/src/main/java/org/slf4j/ILoggerFactory.java
index 8ed82f3c..6fec242c 100644
--- a/slf4j-api/src/main/java/org/slf4j/ILoggerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/ILoggerFactory.java
@@ -29,7 +29,7 @@ package org.slf4j;
* instances by name.
*
* <p>Most users retrieve {@link Logger} instances through the static
- * {@link LoggerFactory#getLogger(String)} method. An instance of of this
+ * {@link LoggerFactory#getLogger(String)} method. An instance of this
* interface is bound internally with {@link LoggerFactory} class at
* compile time.
*
diff --git a/slf4j-api/src/main/java/org/slf4j/Logger.java b/slf4j-api/src/main/java/org/slf4j/Logger.java
index 93dd9945..2803f782 100644
--- a/slf4j-api/src/main/java/org/slf4j/Logger.java
+++ b/slf4j-api/src/main/java/org/slf4j/Logger.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2022 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -25,12 +25,29 @@
package org.slf4j;
+import static org.slf4j.event.EventConstants.DEBUG_INT;
+import static org.slf4j.event.EventConstants.ERROR_INT;
+import static org.slf4j.event.EventConstants.INFO_INT;
+import static org.slf4j.event.EventConstants.TRACE_INT;
+import static org.slf4j.event.EventConstants.WARN_INT;
+import static org.slf4j.event.Level.DEBUG;
+import static org.slf4j.event.Level.ERROR;
+import static org.slf4j.event.Level.INFO;
+import static org.slf4j.event.Level.TRACE;
+import static org.slf4j.event.Level.WARN;
+
+import org.slf4j.event.Level;
+import org.slf4j.helpers.CheckReturnValue;
+import org.slf4j.spi.DefaultLoggingEventBuilder;
+import org.slf4j.spi.LoggingEventBuilder;
+import org.slf4j.spi.NOPLoggingEventBuilder;
+
/**
* The org.slf4j.Logger interface is the main user entry point of SLF4J API.
* It is expected that logging takes place through concrete implementations
* of this interface.
- * <p/>
- * <h3>Typical usage pattern:</h3>
+ *
+ * <H3>Typical usage pattern:</H3>
* <pre>
* import org.slf4j.Logger;
* import org.slf4j.LoggerFactory;
@@ -45,26 +62,29 @@ package org.slf4j;
* oldT = t;
* t = temperature;
* <span style="color:green">logger.debug("Temperature set to {}. Old temperature was {}.", t, oldT);</span>
- * if(temperature.intValue() > 50) {
+ * if (temperature.intValue() &gt; 50) {
* <span style="color:green">logger.info("Temperature has risen above 50 degrees.");</span>
* }
* }
* }
* </pre>
*
- * Be sure to read the FAQ entry relating to <a href="../../../faq.html#logging_performance">parameterized
+ * <p>Note that version 2.0 of the SLF4J API introduces a <a href="../../../manual.html#fluent">fluent api</a>,
+ * the most significant API change to occur in the last 20 years.
+ *
+ * <p>Be sure to read the FAQ entry relating to <a href="../../../faq.html#logging_performance">parameterized
* logging</a>. Note that logging statements can be parameterized in
* <a href="../../../faq.html#paramException">presence of an exception/throwable</a>.
*
* <p>Once you are comfortable using loggers, i.e. instances of this interface, consider using
- * <a href="MDC.html">MDC</a> as well as <a href="Marker.html">Markers</a>.</p>
+ * <a href="MDC.html">MDC</a> as well as <a href="Marker.html">Markers</a>.
*
* @author Ceki G&uuml;lc&uuml;
*/
public interface Logger {
/**
- * Case insensitive String constant used to retrieve the name of the root logger.
+ * Case-insensitive String constant used to retrieve the name of the root logger.
*
* @since 1.3
*/
@@ -77,6 +97,70 @@ public interface Logger {
public String getName();
/**
+ * <p>Make a new {@link LoggingEventBuilder} instance as appropriate for this logger implementation.
+ * This default implementation always returns a new instance of {@link DefaultLoggingEventBuilder}.</p>
+ * <p></p>
+ * <p>This method is intended to be used by logging systems implementing the SLF4J API and <b>not</b>
+ * by end users.</p>
+ * <p></p>
+ * <p>Also note that a {@link LoggingEventBuilder} instance should be built for all levels,
+ * independently of the level argument. In other words, this method is an <b>unconditional</b>
+ * constructor for the {@link LoggingEventBuilder} appropriate for this logger implementation.</p>
+ * <p></p>
+ * @param level desired level for the event builder
+ * @return a new {@link LoggingEventBuilder} instance as appropriate for <b>this</b> logger
+ * @since 2.0
+ */
+ default public LoggingEventBuilder makeLoggingEventBuilder(Level level) {
+ return new DefaultLoggingEventBuilder(this, level);
+ }
+
+ /**
+ * Make a new {@link LoggingEventBuilder} instance as appropriate for this logger and the
+ * desired {@link Level} passed as parameter. If this Logger is disabled for the given Level, then
+ * a {@link NOPLoggingEventBuilder} is returned.
+ *
+ *
+ * @param level desired level for the event builder
+ * @return a new {@link LoggingEventBuilder} instance as appropriate for this logger
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atLevel(Level level) {
+ if (isEnabledForLevel(level)) {
+ return makeLoggingEventBuilder(level);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
+
+
+ /**
+ * Returns whether this Logger is enabled for a given {@link Level}.
+ *
+ * @param level
+ * @return true if enabled, false otherwise.
+ */
+ default public boolean isEnabledForLevel(Level level) {
+ int levelInt = level.toInt();
+ switch (levelInt) {
+ case (TRACE_INT):
+ return isTraceEnabled();
+ case (DEBUG_INT):
+ return isDebugEnabled();
+ case (INFO_INT):
+ return isInfoEnabled();
+ case (WARN_INT):
+ return isWarnEnabled();
+ case (ERROR_INT):
+ return isErrorEnabled();
+ default:
+ throw new IllegalArgumentException("Level [" + level + "] not recognized.");
+ }
+ }
+
+ /**
* Is the logger instance enabled for the TRACE level?
*
* @return True if this Logger is enabled for the TRACE level,
@@ -96,9 +180,9 @@ public interface Logger {
/**
* Log a message at the TRACE level according to the specified format
* and argument.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the TRACE level. </p>
+ * is disabled for the TRACE level.
*
* @param format the format string
* @param arg the argument
@@ -109,9 +193,9 @@ public interface Logger {
/**
* Log a message at the TRACE level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the TRACE level. </p>
+ * is disabled for the TRACE level.
*
* @param format the format string
* @param arg1 the first argument
@@ -123,12 +207,12 @@ public interface Logger {
/**
* Log a message at the TRACE level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous string concatenation when the logger
* is disabled for the TRACE level. However, this variant incurs the hidden
* (and relatively small) cost of creating an <code>Object[]</code> before invoking the method,
* even if this logger is disabled for TRACE. The variants taking {@link #trace(String, Object) one} and
- * {@link #trace(String, Object, Object) two} arguments exist solely in order to avoid this hidden cost.</p>
+ * {@link #trace(String, Object, Object) two} arguments exist solely in order to avoid this hidden cost.
*
* @param format the format string
* @param arguments a list of 3 or more arguments
@@ -159,6 +243,21 @@ public interface Logger {
public boolean isTraceEnabled(Marker marker);
/**
+ * Entry point for fluent-logging for {@link org.slf4j.event.Level#TRACE} level.
+ *
+ * @return LoggingEventBuilder instance as appropriate for level TRACE
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atTrace() {
+ if (isTraceEnabled()) {
+ return makeLoggingEventBuilder(TRACE);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
+ /**
* Log a message with the specific Marker at the TRACE level.
*
* @param marker the marker data specific to this log statement
@@ -232,9 +331,9 @@ public interface Logger {
/**
* Log a message at the DEBUG level according to the specified format
* and argument.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the DEBUG level. </p>
+ * is disabled for the DEBUG level.
*
* @param format the format string
* @param arg the argument
@@ -244,9 +343,9 @@ public interface Logger {
/**
* Log a message at the DEBUG level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the DEBUG level. </p>
+ * is disabled for the DEBUG level.
*
* @param format the format string
* @param arg1 the first argument
@@ -257,13 +356,13 @@ public interface Logger {
/**
* Log a message at the DEBUG level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous string concatenation when the logger
* is disabled for the DEBUG level. However, this variant incurs the hidden
* (and relatively small) cost of creating an <code>Object[]</code> before invoking the method,
* even if this logger is disabled for DEBUG. The variants taking
* {@link #debug(String, Object) one} and {@link #debug(String, Object, Object) two}
- * arguments exist solely in order to avoid this hidden cost.</p>
+ * arguments exist solely in order to avoid this hidden cost.
*
* @param format the format string
* @param arguments a list of 3 or more arguments
@@ -341,6 +440,21 @@ public interface Logger {
public void debug(Marker marker, String msg, Throwable t);
/**
+ * Entry point for fluent-logging for {@link org.slf4j.event.Level#DEBUG} level.
+ *
+ * @return LoggingEventBuilder instance as appropriate for level DEBUG
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atDebug() {
+ if (isDebugEnabled()) {
+ return makeLoggingEventBuilder(DEBUG);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
+ /**
* Is the logger instance enabled for the INFO level?
*
* @return True if this Logger is enabled for the INFO level,
@@ -358,9 +472,9 @@ public interface Logger {
/**
* Log a message at the INFO level according to the specified format
* and argument.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the INFO level. </p>
+ * is disabled for the INFO level.
*
* @param format the format string
* @param arg the argument
@@ -370,9 +484,9 @@ public interface Logger {
/**
* Log a message at the INFO level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the INFO level. </p>
+ * is disabled for the INFO level.
*
* @param format the format string
* @param arg1 the first argument
@@ -383,13 +497,13 @@ public interface Logger {
/**
* Log a message at the INFO level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous string concatenation when the logger
* is disabled for the INFO level. However, this variant incurs the hidden
* (and relatively small) cost of creating an <code>Object[]</code> before invoking the method,
* even if this logger is disabled for INFO. The variants taking
* {@link #info(String, Object) one} and {@link #info(String, Object, Object) two}
- * arguments exist solely in order to avoid this hidden cost.</p>
+ * arguments exist solely in order to avoid this hidden cost.
*
* @param format the format string
* @param arguments a list of 3 or more arguments
@@ -410,7 +524,8 @@ public interface Logger {
* data is also taken into consideration.
*
* @param marker The marker data to take into consideration
- * @return true if this logger is warn enabled, false otherwise
+ * @return true if this Logger is enabled for the INFO level,
+ * false otherwise.
*/
public boolean isInfoEnabled(Marker marker);
@@ -466,6 +581,21 @@ public interface Logger {
public void info(Marker marker, String msg, Throwable t);
/**
+ * Entry point for fluent-logging for {@link org.slf4j.event.Level#INFO} level.
+ *
+ * @return LoggingEventBuilder instance as appropriate for level INFO
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atInfo() {
+ if (isInfoEnabled()) {
+ return makeLoggingEventBuilder(INFO);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
+ /**
* Is the logger instance enabled for the WARN level?
*
* @return True if this Logger is enabled for the WARN level,
@@ -483,9 +613,9 @@ public interface Logger {
/**
* Log a message at the WARN level according to the specified format
* and argument.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the WARN level. </p>
+ * is disabled for the WARN level.
*
* @param format the format string
* @param arg the argument
@@ -495,13 +625,13 @@ public interface Logger {
/**
* Log a message at the WARN level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous string concatenation when the logger
* is disabled for the WARN level. However, this variant incurs the hidden
* (and relatively small) cost of creating an <code>Object[]</code> before invoking the method,
* even if this logger is disabled for WARN. The variants taking
* {@link #warn(String, Object) one} and {@link #warn(String, Object, Object) two}
- * arguments exist solely in order to avoid this hidden cost.</p>
+ * arguments exist solely in order to avoid this hidden cost.
*
* @param format the format string
* @param arguments a list of 3 or more arguments
@@ -511,9 +641,9 @@ public interface Logger {
/**
* Log a message at the WARN level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the WARN level. </p>
+ * is disabled for the WARN level.
*
* @param format the format string
* @param arg1 the first argument
@@ -592,6 +722,21 @@ public interface Logger {
public void warn(Marker marker, String msg, Throwable t);
/**
+ * Entry point for fluent-logging for {@link org.slf4j.event.Level#WARN} level.
+ *
+ * @return LoggingEventBuilder instance as appropriate for level WARN
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atWarn() {
+ if (isWarnEnabled()) {
+ return makeLoggingEventBuilder(WARN);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
+ /**
* Is the logger instance enabled for the ERROR level?
*
* @return True if this Logger is enabled for the ERROR level,
@@ -609,9 +754,9 @@ public interface Logger {
/**
* Log a message at the ERROR level according to the specified format
* and argument.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the ERROR level. </p>
+ * is disabled for the ERROR level.
*
* @param format the format string
* @param arg the argument
@@ -621,9 +766,9 @@ public interface Logger {
/**
* Log a message at the ERROR level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous object creation when the logger
- * is disabled for the ERROR level. </p>
+ * is disabled for the ERROR level.
*
* @param format the format string
* @param arg1 the first argument
@@ -634,13 +779,13 @@ public interface Logger {
/**
* Log a message at the ERROR level according to the specified format
* and arguments.
- * <p/>
+ *
* <p>This form avoids superfluous string concatenation when the logger
* is disabled for the ERROR level. However, this variant incurs the hidden
* (and relatively small) cost of creating an <code>Object[]</code> before invoking the method,
* even if this logger is disabled for ERROR. The variants taking
* {@link #error(String, Object) one} and {@link #error(String, Object, Object) two}
- * arguments exist solely in order to avoid this hidden cost.</p>
+ * arguments exist solely in order to avoid this hidden cost.
*
* @param format the format string
* @param arguments a list of 3 or more arguments
@@ -718,4 +863,19 @@ public interface Logger {
*/
public void error(Marker marker, String msg, Throwable t);
+ /**
+ * Entry point for fluent-logging for {@link org.slf4j.event.Level#ERROR} level.
+ *
+ * @return LoggingEventBuilder instance as appropriate for level ERROR
+ * @since 2.0
+ */
+ @CheckReturnValue
+ default public LoggingEventBuilder atError() {
+ if (isErrorEnabled()) {
+ return makeLoggingEventBuilder(ERROR);
+ } else {
+ return NOPLoggingEventBuilder.singleton();
+ }
+ }
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/LoggerFactory.java b/slf4j-api/src/main/java/org/slf4j/LoggerFactory.java
index 2f74c18b..4e1f0b0d 100755
--- a/slf4j-api/src/main/java/org/slf4j/LoggerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/LoggerFactory.java
@@ -25,34 +25,41 @@
package org.slf4j;
import java.io.IOException;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
import java.net.URL;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.util.ArrayList;
import java.util.Arrays;
import java.util.Enumeration;
import java.util.Iterator;
import java.util.LinkedHashSet;
import java.util.List;
+import java.util.ServiceConfigurationError;
+import java.util.ServiceLoader;
import java.util.Set;
+import java.util.concurrent.LinkedBlockingQueue;
-import org.slf4j.helpers.NOPLoggerFactory;
+import org.slf4j.event.SubstituteLoggingEvent;
+import org.slf4j.helpers.NOP_FallbackServiceProvider;
+import org.slf4j.helpers.Reporter;
import org.slf4j.helpers.SubstituteLogger;
-import org.slf4j.helpers.SubstituteLoggerFactory;
+import org.slf4j.helpers.SubstituteServiceProvider;
import org.slf4j.helpers.Util;
-import org.slf4j.impl.StaticLoggerBinder;
+import org.slf4j.spi.SLF4JServiceProvider;
/**
* The <code>LoggerFactory</code> is a utility class producing Loggers for
- * various logging APIs, most notably for log4j, logback and JDK 1.4 logging.
- * Other implementations such as {@link org.slf4j.impl.NOPLogger NOPLogger} and
- * {@link org.slf4j.impl.SimpleLogger SimpleLogger} are also supported.
- * <p/>
- * <p/>
- * <code>LoggerFactory</code> is essentially a wrapper around an
- * {@link ILoggerFactory} instance bound with <code>LoggerFactory</code> at
- * compile time.
- * <p/>
- * <p/>
- * Please note that all methods in <code>LoggerFactory</code> are static.
+ * various logging APIs, e.g. logback, reload4j, log4j and JDK 1.4 logging.
+ * Other implementations such as {@link org.slf4j.helpers.NOPLogger NOPLogger} and
+ * SimpleLogger are also supported.
+ *
+ * <p><code>LoggerFactory</code> is essentially a wrapper around an
+ * {@link ILoggerFactory} instance provided by a {@link SLF4JServiceProvider}.
*
+ * <p>
+ * Please note that all methods in <code>LoggerFactory</code> are static.
*
* @author Alexander Dorokhine
* @author Robert Elliot
@@ -61,17 +68,27 @@ import org.slf4j.impl.StaticLoggerBinder;
*/
public final class LoggerFactory {
- static final String CODES_PREFIX = "http://www.slf4j.org/codes.html";
+ static final String CODES_PREFIX = "https://www.slf4j.org/codes.html";
+
+ static final String NO_PROVIDERS_URL = CODES_PREFIX + "#noProviders";
+ static final String IGNORED_BINDINGS_URL = CODES_PREFIX + "#ignoredBindings";
- static final String NO_STATICLOGGERBINDER_URL = CODES_PREFIX + "#StaticLoggerBinder";
static final String MULTIPLE_BINDINGS_URL = CODES_PREFIX + "#multiple_bindings";
- static final String NULL_LF_URL = CODES_PREFIX + "#null_LF";
static final String VERSION_MISMATCH = CODES_PREFIX + "#version_mismatch";
static final String SUBSTITUTE_LOGGER_URL = CODES_PREFIX + "#substituteLogger";
static final String LOGGER_NAME_MISMATCH_URL = CODES_PREFIX + "#loggerNameMismatch";
+ static final String REPLAY_URL = CODES_PREFIX + "#replay";
static final String UNSUCCESSFUL_INIT_URL = CODES_PREFIX + "#unsuccessfulInit";
- static final String UNSUCCESSFUL_INIT_MSG = "org.slf4j.LoggerFactory could not be successfully initialized. See also " + UNSUCCESSFUL_INIT_URL;
+ static final String UNSUCCESSFUL_INIT_MSG = "org.slf4j.LoggerFactory in failed state. Original exception was thrown EARLIER. See also "
+ + UNSUCCESSFUL_INIT_URL;
+ /**
+ * System property for explicitly setting the provider class. If set and the provider could be instantiated,
+ * then the service loading mechanism will be bypassed.
+ *
+ * @since 2.0.9
+ */
+ static final public String PROVIDER_PROPERTY_KEY = "slf4j.provider";
static final int UNINITIALIZED = 0;
static final int ONGOING_INITIALIZATION = 1;
@@ -79,22 +96,69 @@ public final class LoggerFactory {
static final int SUCCESSFUL_INITIALIZATION = 3;
static final int NOP_FALLBACK_INITIALIZATION = 4;
- static int INITIALIZATION_STATE = UNINITIALIZED;
- static SubstituteLoggerFactory TEMP_FACTORY = new SubstituteLoggerFactory();
- static NOPLoggerFactory NOP_FALLBACK_FACTORY = new NOPLoggerFactory();
+ static volatile int INITIALIZATION_STATE = UNINITIALIZED;
+ static final SubstituteServiceProvider SUBST_PROVIDER = new SubstituteServiceProvider();
+ static final NOP_FallbackServiceProvider NOP_FALLBACK_SERVICE_PROVIDER = new NOP_FallbackServiceProvider();
// Support for detecting mismatched logger names.
static final String DETECT_LOGGER_NAME_MISMATCH_PROPERTY = "slf4j.detectLoggerNameMismatch";
- static boolean DETECT_LOGGER_NAME_MISMATCH = Boolean.getBoolean(DETECT_LOGGER_NAME_MISMATCH_PROPERTY);
+ static final String JAVA_VENDOR_PROPERTY = "java.vendor.url";
+
+ static boolean DETECT_LOGGER_NAME_MISMATCH = Util.safeGetBooleanSystemProperty(DETECT_LOGGER_NAME_MISMATCH_PROPERTY);
+
+ static volatile SLF4JServiceProvider PROVIDER;
+
+ // Package access for tests
+ static List<SLF4JServiceProvider> findServiceProviders() {
+ List<SLF4JServiceProvider> providerList = new ArrayList<>();
+
+ // retain behaviour similar to that of 1.7 series and earlier. More specifically, use the class loader that
+ // loaded the present class to search for services
+ final ClassLoader classLoaderOfLoggerFactory = LoggerFactory.class.getClassLoader();
+
+ SLF4JServiceProvider explicitProvider = loadExplicitlySpecified(classLoaderOfLoggerFactory);
+ if(explicitProvider != null) {
+ providerList.add(explicitProvider);
+ return providerList;
+ }
+
+
+ ServiceLoader<SLF4JServiceProvider> serviceLoader = getServiceLoader(classLoaderOfLoggerFactory);
+
+ Iterator<SLF4JServiceProvider> iterator = serviceLoader.iterator();
+ while (iterator.hasNext()) {
+ safelyInstantiate(providerList, iterator);
+ }
+ return providerList;
+ }
+
+ private static ServiceLoader<SLF4JServiceProvider> getServiceLoader(final ClassLoader classLoaderOfLoggerFactory) {
+ ServiceLoader<SLF4JServiceProvider> serviceLoader;
+ SecurityManager securityManager = System.getSecurityManager();
+ if(securityManager == null) {
+ serviceLoader = ServiceLoader.load(SLF4JServiceProvider.class, classLoaderOfLoggerFactory);
+ } else {
+ final PrivilegedAction<ServiceLoader<SLF4JServiceProvider>> action = () -> ServiceLoader.load(SLF4JServiceProvider.class, classLoaderOfLoggerFactory);
+ serviceLoader = AccessController.doPrivileged(action);
+ }
+ return serviceLoader;
+ }
+
+ private static void safelyInstantiate(List<SLF4JServiceProvider> providerList, Iterator<SLF4JServiceProvider> iterator) {
+ try {
+ SLF4JServiceProvider provider = iterator.next();
+ providerList.add(provider);
+ } catch (ServiceConfigurationError e) {
+ Reporter.error("A service provider failed to instantiate:\n" + e.getMessage());
+ }
+ }
/**
* It is LoggerFactory's responsibility to track version changes and manage
* the compatibility list.
- * <p/>
- * <p/>
- * It is assumed that all versions in the 1.6 are mutually compatible.
+ * <p>
*/
- static private final String[] API_COMPATIBILITY_LIST = new String[] { "1.6", "1.7" };
+ static private final String[] API_COMPATIBILITY_LIST = new String[] { "2.0" };
// private constructor prevents instantiation
private LoggerFactory() {
@@ -102,18 +166,17 @@ public final class LoggerFactory {
/**
* Force LoggerFactory to consider itself uninitialized.
- * <p/>
- * <p/>
+ * <p>
+ * <p>
* This method is intended to be called by classes (in the same package) for
* testing purposes. This method is internal. It can be modified, renamed or
* removed at any time without notice.
- * <p/>
- * <p/>
+ * <p>
+ * <p>
* You are strongly discouraged from calling this method in production code.
*/
static void reset() {
INITIALIZATION_STATE = UNINITIALIZED;
- TEMP_FACTORY = new SubstituteLoggerFactory();
}
private final static void performInitialization() {
@@ -123,110 +186,77 @@ public final class LoggerFactory {
}
}
- private static boolean messageContainsOrgSlf4jImplStaticLoggerBinder(String msg) {
- if (msg == null)
- return false;
- if (msg.indexOf("org/slf4j/impl/StaticLoggerBinder") != -1)
- return true;
- if (msg.indexOf("org.slf4j.impl.StaticLoggerBinder") != -1)
- return true;
- return false;
- }
-
private final static void bind() {
try {
- Set<URL> staticLoggerBinderPathSet = findPossibleStaticLoggerBinderPathSet();
- reportMultipleBindingAmbiguity(staticLoggerBinderPathSet);
- // the next line does the binding
- StaticLoggerBinder.getSingleton();
- INITIALIZATION_STATE = SUCCESSFUL_INITIALIZATION;
- reportActualBinding(staticLoggerBinderPathSet);
- fixSubstitutedLoggers();
- } catch (NoClassDefFoundError ncde) {
- String msg = ncde.getMessage();
- if (messageContainsOrgSlf4jImplStaticLoggerBinder(msg)) {
- INITIALIZATION_STATE = NOP_FALLBACK_INITIALIZATION;
- Util.report("Failed to load class \"org.slf4j.impl.StaticLoggerBinder\".");
- Util.report("Defaulting to no-operation (NOP) logger implementation");
- Util.report("See " + NO_STATICLOGGERBINDER_URL + " for further details.");
+ List<SLF4JServiceProvider> providersList = findServiceProviders();
+ reportMultipleBindingAmbiguity(providersList);
+ if (providersList != null && !providersList.isEmpty()) {
+ PROVIDER = providersList.get(0);
+ // SLF4JServiceProvider.initialize() is intended to be called here and nowhere else.
+ PROVIDER.initialize();
+ INITIALIZATION_STATE = SUCCESSFUL_INITIALIZATION;
+ reportActualBinding(providersList);
} else {
- failedBinding(ncde);
- throw ncde;
- }
- } catch (java.lang.NoSuchMethodError nsme) {
- String msg = nsme.getMessage();
- if (msg != null && msg.indexOf("org.slf4j.impl.StaticLoggerBinder.getSingleton()") != -1) {
- INITIALIZATION_STATE = FAILED_INITIALIZATION;
- Util.report("slf4j-api 1.6.x (or later) is incompatible with this binding.");
- Util.report("Your binding is version 1.5.5 or earlier.");
- Util.report("Upgrade your binding to version 1.6.x.");
+ INITIALIZATION_STATE = NOP_FALLBACK_INITIALIZATION;
+ Reporter.warn("No SLF4J providers were found.");
+ Reporter.warn("Defaulting to no-operation (NOP) logger implementation");
+ Reporter.warn("See " + NO_PROVIDERS_URL + " for further details.");
+
+ Set<URL> staticLoggerBinderPathSet = findPossibleStaticLoggerBinderPathSet();
+ reportIgnoredStaticLoggerBinders(staticLoggerBinderPathSet);
}
- throw nsme;
+ postBindCleanUp();
} catch (Exception e) {
failedBinding(e);
throw new IllegalStateException("Unexpected initialization failure", e);
}
}
- static void failedBinding(Throwable t) {
- INITIALIZATION_STATE = FAILED_INITIALIZATION;
- Util.report("Failed to instantiate SLF4J LoggerFactory", t);
+ static SLF4JServiceProvider loadExplicitlySpecified(ClassLoader classLoader) {
+ String explicitlySpecified = System.getProperty(PROVIDER_PROPERTY_KEY);
+ if (null == explicitlySpecified || explicitlySpecified.isEmpty()) {
+ return null;
+ }
+ try {
+ String message = String.format("Attempting to load provider \"%s\" specified via \"%s\" system property", explicitlySpecified, PROVIDER_PROPERTY_KEY);
+ Reporter.info(message);
+ Class<?> clazz = classLoader.loadClass(explicitlySpecified);
+ Constructor<?> constructor = clazz.getConstructor();
+ Object provider = constructor.newInstance();
+ return (SLF4JServiceProvider) provider;
+ } catch (ClassNotFoundException | NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) {
+ String message = String.format("Failed to instantiate the specified SLF4JServiceProvider (%s)", explicitlySpecified);
+ Reporter.error(message, e);
+ return null;
+ } catch (ClassCastException e) {
+ String message = String.format("Specified SLF4JServiceProvider (%s) does not implement SLF4JServiceProvider interface", explicitlySpecified);
+ Reporter.error(message, e);
+ return null;
+ }
}
- private final static void fixSubstitutedLoggers() {
- List<SubstituteLogger> loggers = TEMP_FACTORY.getLoggers();
-
- if (loggers.isEmpty()) {
+ private static void reportIgnoredStaticLoggerBinders(Set<URL> staticLoggerBinderPathSet) {
+ if (staticLoggerBinderPathSet.isEmpty()) {
return;
}
+ Reporter.warn("Class path contains SLF4J bindings targeting slf4j-api versions 1.7.x or earlier.");
- Util.report("The following set of substitute loggers may have been accessed");
- Util.report("during the initialization phase. Logging calls during this");
- Util.report("phase were not honored. However, subsequent logging calls to these");
- Util.report("loggers will work as normally expected.");
- Util.report("See also " + SUBSTITUTE_LOGGER_URL);
- for (SubstituteLogger subLogger : loggers) {
- subLogger.setDelegate(getLogger(subLogger.getName()));
- Util.report(subLogger.getName());
+ for (URL path : staticLoggerBinderPathSet) {
+ Reporter.warn("Ignoring binding found at [" + path + "]");
}
+ Reporter.warn("See " + IGNORED_BINDINGS_URL + " for an explanation.");
- TEMP_FACTORY.clear();
- }
-
- private final static void versionSanityCheck() {
- try {
- String requested = StaticLoggerBinder.REQUESTED_API_VERSION;
-
- boolean match = false;
- for (int i = 0; i < API_COMPATIBILITY_LIST.length; i++) {
- if (requested.startsWith(API_COMPATIBILITY_LIST[i])) {
- match = true;
- }
- }
- if (!match) {
- Util.report("The requested version " + requested + " by your slf4j binding is not compatible with "
- + Arrays.asList(API_COMPATIBILITY_LIST).toString());
- Util.report("See " + VERSION_MISMATCH + " for further details.");
- }
- } catch (java.lang.NoSuchFieldError nsfe) {
- // given our large user base and SLF4J's commitment to backward
- // compatibility, we cannot cry here. Only for implementations
- // which willingly declare a REQUESTED_API_VERSION field do we
- // emit compatibility warnings.
- } catch (Throwable e) {
- // we should never reach here
- Util.report("Unexpected problem occured during version sanity check", e);
- }
}
- // We need to use the name of the StaticLoggerBinder class, but we can't reference
- // the class itself.
- private static String STATIC_LOGGER_BINDER_PATH = "org/slf4j/impl/StaticLoggerBinder.class";
+ // We need to use the name of the StaticLoggerBinder class, but we can't
+ // reference the class itself.
+ private static final String STATIC_LOGGER_BINDER_PATH = "org/slf4j/impl/StaticLoggerBinder.class";
- private static Set<URL> findPossibleStaticLoggerBinderPathSet() {
+ static Set<URL> findPossibleStaticLoggerBinderPathSet() {
// use Set instead of list in order to deal with bug #138
- // LinkedHashSet appropriate here because it preserves insertion order during iteration
- Set<URL> staticLoggerBinderPathSet = new LinkedHashSet<URL>();
+ // LinkedHashSet appropriate here because it preserves insertion order
+ // during iteration
+ Set<URL> staticLoggerBinderPathSet = new LinkedHashSet<>();
try {
ClassLoader loggerFactoryClassLoader = LoggerFactory.class.getClassLoader();
Enumeration<URL> paths;
@@ -236,47 +266,155 @@ public final class LoggerFactory {
paths = loggerFactoryClassLoader.getResources(STATIC_LOGGER_BINDER_PATH);
}
while (paths.hasMoreElements()) {
- URL path = (URL) paths.nextElement();
+ URL path = paths.nextElement();
staticLoggerBinderPathSet.add(path);
}
} catch (IOException ioe) {
- Util.report("Error getting resources from path", ioe);
+ Reporter.error("Error getting resources from path", ioe);
}
return staticLoggerBinderPathSet;
}
- private static boolean isAmbiguousStaticLoggerBinderPathSet(Set<URL> staticLoggerBinderPathSet) {
- return staticLoggerBinderPathSet.size() > 1;
+ private static void postBindCleanUp() {
+ fixSubstituteLoggers();
+ replayEvents();
+ // release all resources in SUBST_FACTORY
+ SUBST_PROVIDER.getSubstituteLoggerFactory().clear();
+ }
+
+ private static void fixSubstituteLoggers() {
+ synchronized (SUBST_PROVIDER) {
+ SUBST_PROVIDER.getSubstituteLoggerFactory().postInitialization();
+ for (SubstituteLogger substLogger : SUBST_PROVIDER.getSubstituteLoggerFactory().getLoggers()) {
+ Logger logger = getLogger(substLogger.getName());
+ substLogger.setDelegate(logger);
+ }
+ }
+
+ }
+
+ static void failedBinding(Throwable t) {
+ INITIALIZATION_STATE = FAILED_INITIALIZATION;
+ Reporter.error("Failed to instantiate SLF4J LoggerFactory", t);
+ }
+
+ private static void replayEvents() {
+ final LinkedBlockingQueue<SubstituteLoggingEvent> queue = SUBST_PROVIDER.getSubstituteLoggerFactory().getEventQueue();
+ final int queueSize = queue.size();
+ int count = 0;
+ final int maxDrain = 128;
+ List<SubstituteLoggingEvent> eventList = new ArrayList<>(maxDrain);
+ while (true) {
+ int numDrained = queue.drainTo(eventList, maxDrain);
+ if (numDrained == 0)
+ break;
+ for (SubstituteLoggingEvent event : eventList) {
+ replaySingleEvent(event);
+ if (count++ == 0)
+ emitReplayOrSubstituionWarning(event, queueSize);
+ }
+ eventList.clear();
+ }
+ }
+
+ private static void emitReplayOrSubstituionWarning(SubstituteLoggingEvent event, int queueSize) {
+ if (event.getLogger().isDelegateEventAware()) {
+ emitReplayWarning(queueSize);
+ } else if (event.getLogger().isDelegateNOP()) {
+ // nothing to do
+ } else {
+ emitSubstitutionWarning();
+ }
+ }
+
+ private static void replaySingleEvent(SubstituteLoggingEvent event) {
+ if (event == null)
+ return;
+
+ SubstituteLogger substLogger = event.getLogger();
+ String loggerName = substLogger.getName();
+ if (substLogger.isDelegateNull()) {
+ throw new IllegalStateException("Delegate logger cannot be null at this state.");
+ }
+
+ if (substLogger.isDelegateNOP()) {
+ // nothing to do
+ } else if (substLogger.isDelegateEventAware()) {
+ if(substLogger.isEnabledForLevel(event.getLevel())) {
+ substLogger.log(event);
+ }
+ } else {
+ Reporter.warn(loggerName);
+ }
+ }
+
+ private static void emitSubstitutionWarning() {
+ Reporter.warn("The following set of substitute loggers may have been accessed");
+ Reporter.warn("during the initialization phase. Logging calls during this");
+ Reporter.warn("phase were not honored. However, subsequent logging calls to these");
+ Reporter.warn("loggers will work as normally expected.");
+ Reporter.warn("See also " + SUBSTITUTE_LOGGER_URL);
+ }
+
+ private static void emitReplayWarning(int eventCount) {
+ Reporter.warn("A number (" + eventCount + ") of logging calls during the initialization phase have been intercepted and are");
+ Reporter.warn("now being replayed. These are subject to the filtering rules of the underlying logging system.");
+ Reporter.warn("See also " + REPLAY_URL);
+ }
+
+ private final static void versionSanityCheck() {
+ try {
+ String requested = PROVIDER.getRequestedApiVersion();
+
+ boolean match = false;
+ for (String aAPI_COMPATIBILITY_LIST : API_COMPATIBILITY_LIST) {
+ if (requested.startsWith(aAPI_COMPATIBILITY_LIST)) {
+ match = true;
+ }
+ }
+ if (!match) {
+ Reporter.warn("The requested version " + requested + " by your slf4j provider is not compatible with "
+ + Arrays.asList(API_COMPATIBILITY_LIST).toString());
+ Reporter.warn("See " + VERSION_MISMATCH + " for further details.");
+ }
+ } catch (Throwable e) {
+ // we should never reach here
+ Reporter.error("Unexpected problem occurred during version sanity check", e);
+ }
+ }
+
+ private static boolean isAmbiguousProviderList(List<SLF4JServiceProvider> providerList) {
+ return providerList.size() > 1;
}
/**
- * Prints a warning message on the console if multiple bindings were found on the class path.
- * No reporting is done otherwise.
+ * Prints a warning message on the console if multiple bindings were found
+ * on the class path. No reporting is done otherwise.
*
*/
- private static void reportMultipleBindingAmbiguity(Set<URL> staticLoggerBinderPathSet) {
- if (isAmbiguousStaticLoggerBinderPathSet(staticLoggerBinderPathSet)) {
- Util.report("Class path contains multiple SLF4J bindings.");
- Iterator<URL> iterator = staticLoggerBinderPathSet.iterator();
- while (iterator.hasNext()) {
- URL path = (URL) iterator.next();
- Util.report("Found binding in [" + path + "]");
+ private static void reportMultipleBindingAmbiguity(List<SLF4JServiceProvider> providerList) {
+ if (isAmbiguousProviderList(providerList)) {
+ Reporter.warn("Class path contains multiple SLF4J providers.");
+ for (SLF4JServiceProvider provider : providerList) {
+ Reporter.warn("Found provider [" + provider + "]");
}
- Util.report("See " + MULTIPLE_BINDINGS_URL + " for an explanation.");
+ Reporter.warn("See " + MULTIPLE_BINDINGS_URL + " for an explanation.");
}
}
- private static void reportActualBinding(Set<URL> staticLoggerBinderPathSet) {
- if (isAmbiguousStaticLoggerBinderPathSet(staticLoggerBinderPathSet)) {
- Util.report("Actual binding is of type [" + StaticLoggerBinder.getSingleton().getLoggerFactoryClassStr() + "]");
+ private static void reportActualBinding(List<SLF4JServiceProvider> providerList) {
+ // binderPathSet can be null under Android
+ if (!providerList.isEmpty() && isAmbiguousProviderList(providerList)) {
+ Reporter.info("Actual provider is of type [" + providerList.get(0) + "]");
}
}
/**
- * Return a logger named according to the name parameter using the statically
- * bound {@link ILoggerFactory} instance.
+ * Return a logger named according to the name parameter using the
+ * statically bound {@link ILoggerFactory} instance.
*
- * @param name The name of the logger.
+ * @param name
+ * The name of the logger.
* @return logger
*/
public static Logger getLogger(String name) {
@@ -285,29 +423,34 @@ public final class LoggerFactory {
}
/**
- * Return a logger named corresponding to the class passed as parameter, using
- * the statically bound {@link ILoggerFactory} instance.
+ * Return a logger named corresponding to the class passed as parameter,
+ * using the statically bound {@link ILoggerFactory} instance.
+ *
+ * <p>
+ * In case the <code>clazz</code> parameter differs from the name of the
+ * caller as computed internally by SLF4J, a logger name mismatch warning
+ * will be printed but only if the
+ * <code>slf4j.detectLoggerNameMismatch</code> system property is set to
+ * true. By default, this property is not set and no warnings will be
+ * printed even in case of a logger name mismatch.
*
- * <p>In case the the <code>clazz</code> parameter differs from the name of
- * the caller as computed internally by SLF4J, a logger name mismatch warning will be
- * printed but only if the <code>slf4j.detectLoggerNameMismatch</code> system property is
- * set to true. By default, this property is not set and no warnings will be printed
- * even in case of a logger name mismatch.
- *
- * @param clazz the returned logger will be named after clazz
+ * @param clazz
+ * the returned logger will be named after clazz
* @return logger
*
*
- * @see <a href="http://www.slf4j.org/codes.html#loggerNameMismatch">Detected logger name mismatch</a>
+ * @see <a
+ * href="http://www.slf4j.org/codes.html#loggerNameMismatch">Detected
+ * logger name mismatch</a>
*/
public static Logger getLogger(Class<?> clazz) {
Logger logger = getLogger(clazz.getName());
if (DETECT_LOGGER_NAME_MISMATCH) {
Class<?> autoComputedCallingClass = Util.getCallingClass();
- if (nonMatchingClasses(clazz, autoComputedCallingClass)) {
- Util.report(String.format("Detected logger name mismatch. Given name: \"%s\"; computed name: \"%s\".", logger.getName(),
+ if (autoComputedCallingClass != null && nonMatchingClasses(clazz, autoComputedCallingClass)) {
+ Reporter.warn(String.format("Detected logger name mismatch. Given name: \"%s\"; computed name: \"%s\".", logger.getName(),
autoComputedCallingClass.getName()));
- Util.report("See " + LOGGER_NAME_MISMATCH_URL + " for an explanation");
+ Reporter.warn("See " + LOGGER_NAME_MISMATCH_URL + " for an explanation");
}
}
return logger;
@@ -319,28 +462,42 @@ public final class LoggerFactory {
/**
* Return the {@link ILoggerFactory} instance in use.
- * <p/>
- * <p/>
+ * <p>
+ * <p>
* ILoggerFactory instance is bound with this class at compile time.
*
* @return the ILoggerFactory instance in use
*/
public static ILoggerFactory getILoggerFactory() {
+ return getProvider().getLoggerFactory();
+ }
+
+ /**
+ * Return the {@link SLF4JServiceProvider} in use.
+
+ * @return provider in use
+ * @since 1.8.0
+ */
+ static SLF4JServiceProvider getProvider() {
if (INITIALIZATION_STATE == UNINITIALIZED) {
- INITIALIZATION_STATE = ONGOING_INITIALIZATION;
- performInitialization();
+ synchronized (LoggerFactory.class) {
+ if (INITIALIZATION_STATE == UNINITIALIZED) {
+ INITIALIZATION_STATE = ONGOING_INITIALIZATION;
+ performInitialization();
+ }
+ }
}
switch (INITIALIZATION_STATE) {
case SUCCESSFUL_INITIALIZATION:
- return StaticLoggerBinder.getSingleton().getLoggerFactory();
+ return PROVIDER;
case NOP_FALLBACK_INITIALIZATION:
- return NOP_FALLBACK_FACTORY;
+ return NOP_FALLBACK_SERVICE_PROVIDER;
case FAILED_INITIALIZATION:
throw new IllegalStateException(UNSUCCESSFUL_INIT_MSG);
case ONGOING_INITIALIZATION:
// support re-entrant behavior.
- // See also http://bugzilla.slf4j.org/show_bug.cgi?id=106
- return TEMP_FACTORY;
+ // See also http://jira.qos.ch/browse/SLF4J-97
+ return SUBST_PROVIDER;
}
throw new IllegalStateException("Unreachable code");
}
diff --git a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-api/src/main/java/org/slf4j/LoggerFactoryFriend.java
index b35b89b0..06ca2017 100644..100755
--- a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ b/slf4j-api/src/main/java/org/slf4j/LoggerFactoryFriend.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2021 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,37 +22,34 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
-
-import org.slf4j.helpers.NOPMDCAdapter;
-import org.slf4j.spi.MDCAdapter;
+package org.slf4j;
/**
- * This implementation is bound to {@link NOPMDCAdapter}.
+ * All methods in this class are reserved for internal use, for testing purposes.
+ *
+ * <p>They can be modified, renamed or removed at any time without notice.
+ *
+ * <p>You are strongly discouraged calling any of the methods of this class.
+ *
+ * @since 1.8.0
*
- * @author Ceki G&uuml;lc&uuml;
+ * @author Ceki G&uuml;lc&uuml;
*/
-public class StaticMDCBinder {
+public class LoggerFactoryFriend {
- /**
- * The unique instance of this class.
+ /*
+ * Force LoggerFactory to consider itself uninitialized.
*/
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
+ static public void reset() {
+ LoggerFactory.reset();
}
/**
- * Currently this method always returns an instance of
- * {@link NOPMDCAdapter}.
+ * Set LoggerFactory.DETECT_LOGGER_NAME_MISMATCH variable.
*
- * @return instance of NOPMDCAdapter
+ * @param enabled a boolean
*/
- public MDCAdapter getMDCA() {
- return new NOPMDCAdapter();
- }
-
- public String getMDCAdapterClassStr() {
- return NOPMDCAdapter.class.getName();
+ public static void setDetectLoggerNameMismatch(boolean enabled) {
+ LoggerFactory.DETECT_LOGGER_NAME_MISMATCH = enabled;
}
}
diff --git a/slf4j-api/src/main/java/org/slf4j/MDC.java b/slf4j-api/src/main/java/org/slf4j/MDC.java
index 06981772..6b0feded 100644
--- a/slf4j-api/src/main/java/org/slf4j/MDC.java
+++ b/slf4j-api/src/main/java/org/slf4j/MDC.java
@@ -25,13 +25,15 @@
package org.slf4j;
import java.io.Closeable;
+import java.util.Deque;
import java.util.Map;
-import org.slf4j.helpers.NOPMDCAdapter;
import org.slf4j.helpers.BasicMDCAdapter;
+import org.slf4j.helpers.NOPMDCAdapter;
+import org.slf4j.helpers.Reporter;
import org.slf4j.helpers.Util;
-import org.slf4j.impl.StaticMDCBinder;
import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
/**
* This class hides and serves as a substitute for the underlying logging
@@ -42,7 +44,7 @@ import org.slf4j.spi.MDCAdapter;
* i.e. this class, will delegate to the underlying system's MDC. Note that at
* this time, only two logging systems, namely log4j and logback, offer MDC
* functionality. For java.util.logging which does not support MDC,
- * {@link BasicMDCAdapter} will be used. For other systems, i.e slf4j-simple
+ * {@link BasicMDCAdapter} will be used. For other systems, i.e. slf4j-simple
* and slf4j-nop, {@link NOPMDCAdapter} will be used.
*
* <p>
@@ -64,6 +66,7 @@ import org.slf4j.spi.MDCAdapter;
public class MDC {
static final String NULL_MDCA_URL = "http://www.slf4j.org/codes.html#null_MDCA";
+ private static final String MDC_APAPTER_CANNOT_BE_NULL_MESSAGE = "MDCAdapter cannot be null. See also " + NULL_MDCA_URL;
static final String NO_STATIC_MDC_BINDER_URL = "http://www.slf4j.org/codes.html#no_static_mdc_binder";
static MDCAdapter mdcAdapter;
@@ -86,21 +89,16 @@ public class MDC {
}
static {
- try {
- mdcAdapter = StaticMDCBinder.SINGLETON.getMDCA();
- } catch (NoClassDefFoundError ncde) {
+ SLF4JServiceProvider provider = LoggerFactory.getProvider();
+ if (provider != null) {
+ // obtain and attach the MDCAdapter from the provider
+ // If you wish to change the adapter, Setting the MDC.mdcAdapter variable might not be enough as
+ // the provider might perform additional assignments that you would need to replicate/adapt.
+ mdcAdapter = provider.getMDCAdapter();
+ } else {
+ Reporter.error("Failed to find provider.");
+ Reporter.error("Defaulting to no-operation MDCAdapter implementation.");
mdcAdapter = new NOPMDCAdapter();
- String msg = ncde.getMessage();
- if (msg != null && msg.indexOf("StaticMDCBinder") != -1) {
- Util.report("Failed to load class \"org.slf4j.impl.StaticMDCBinder\".");
- Util.report("Defaulting to no-operation MDCAdapter implementation.");
- Util.report("See " + NO_STATIC_MDC_BINDER_URL + " for further details.");
- } else {
- throw ncde;
- }
- } catch (Exception e) {
- // we should never get here
- Util.report("MDC binding unsuccessful.", e);
}
}
@@ -124,7 +122,7 @@ public class MDC {
throw new IllegalArgumentException("key parameter cannot be null");
}
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
mdcAdapter.put(key, val);
}
@@ -169,7 +167,7 @@ public class MDC {
* <p>
* This method delegates all work to the MDC of the underlying logging system.
*
- * @param key
+ * @param key a key
* @return the string value identified by the <code>key</code> parameter.
* @throws IllegalArgumentException
* in case the "key" parameter is null
@@ -180,7 +178,7 @@ public class MDC {
}
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
return mdcAdapter.get(key);
}
@@ -191,7 +189,7 @@ public class MDC {
* cannot be null. This method does nothing if there is no previous value
* associated with <code>key</code>.
*
- * @param key
+ * @param key a key
* @throws IllegalArgumentException
* in case the "key" parameter is null
*/
@@ -201,7 +199,7 @@ public class MDC {
}
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
mdcAdapter.remove(key);
}
@@ -211,7 +209,7 @@ public class MDC {
*/
public static void clear() {
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
mdcAdapter.clear();
}
@@ -225,7 +223,7 @@ public class MDC {
*/
public static Map<String, String> getCopyOfContextMap() {
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
return mdcAdapter.getCopyOfContextMap();
}
@@ -235,13 +233,15 @@ public class MDC {
* then copying the map passed as parameter. The context map passed as
* parameter must only contain keys and values of type String.
*
+ * Null valued argument is allowed (since SLF4J version 2.0.0).
+ *
* @param contextMap
* must contain only keys and values of type String
* @since 1.5.1
*/
public static void setContextMap(Map<String, String> contextMap) {
if (mdcAdapter == null) {
- throw new IllegalStateException("MDCAdapter cannot be null. See also " + NULL_MDCA_URL);
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
}
mdcAdapter.setContextMap(contextMap);
}
@@ -256,4 +256,48 @@ public class MDC {
return mdcAdapter;
}
+
+
+ /**
+ * Push a value into the deque(stack) referenced by 'key'.
+ *
+ * @param key identifies the appropriate stack
+ * @param value the value to push into the stack
+ * @since 2.0.0
+ */
+ static public void pushByKey(String key, String value) {
+ if (mdcAdapter == null) {
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
+ }
+ mdcAdapter.pushByKey(key, value);
+ }
+
+ /**
+ * Pop the stack referenced by 'key' and return the value possibly null.
+ *
+ * @param key identifies the deque(stack)
+ * @return the value just popped. May be null/
+ * @since 2.0.0
+ */
+ static public String popByKey(String key) {
+ if (mdcAdapter == null) {
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
+ }
+ return mdcAdapter.popByKey(key);
+ }
+
+ /**
+ * Returns a copy of the deque(stack) referenced by 'key'. May be null.
+ *
+ * @param key identifies the stack
+ * @return copy of stack referenced by 'key'. May be null.
+ *
+ * @since 2.0.0
+ */
+ public Deque<String> getCopyOfDequeByKey(String key) {
+ if (mdcAdapter == null) {
+ throw new IllegalStateException(MDC_APAPTER_CANNOT_BE_NULL_MESSAGE);
+ }
+ return mdcAdapter.getCopyOfDequeByKey(key);
+ }
}
diff --git a/slf4j-api/src/main/java/org/slf4j/Marker.java b/slf4j-api/src/main/java/org/slf4j/Marker.java
index c6bfd5e2..4a6dd100 100644
--- a/slf4j-api/src/main/java/org/slf4j/Marker.java
+++ b/slf4j-api/src/main/java/org/slf4j/Marker.java
@@ -29,14 +29,16 @@ import java.util.Iterator;
/**
* Markers are named objects used to enrich log statements. Conforming logging
- * system Implementations of SLF4J determine how information conveyed by markers
- * are used, if at all. In particular, many conforming logging systems ignore
- * marker data.
- *
- * <p>
- * Markers can contain references to other markers, which in turn may contain
- * references of their own.
- *
+ * system implementations of SLF4J should determine how information conveyed by
+ * any markers are used, if at all. Many conforming logging systems ignore marker
+ * data entirely.
+ *
+ * <p>Markers can contain references to nested markers, which in turn may
+ * contain references of their own. Note that the fluent API (new in 2.0) allows adding
+ * multiple markers to a logging statement. It is often preferable to use
+ * multiple markers instead of nested markers.
+ * </p>
+ *
* @author Ceki G&uuml;lc&uuml;
*/
public interface Marker extends Serializable {
@@ -60,7 +62,11 @@ public interface Marker extends Serializable {
/**
* Add a reference to another Marker.
- *
+ *
+ * <p>Note that the fluent API allows adding multiple markers to a logging statement.
+ * It is often preferable to use multiple markers instead of nested markers.
+ * </p>
+ *
* @param reference
* a reference to another marker
* @throws IllegalArgumentException
@@ -80,6 +86,7 @@ public interface Marker extends Serializable {
/**
* @deprecated Replaced by {@link #hasReferences()}.
*/
+ @Deprecated
public boolean hasChildren();
/**
diff --git a/slf4j-api/src/main/java/org/slf4j/MarkerFactory.java b/slf4j-api/src/main/java/org/slf4j/MarkerFactory.java
index 8d50698d..0b15d6ff 100644
--- a/slf4j-api/src/main/java/org/slf4j/MarkerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/MarkerFactory.java
@@ -25,8 +25,9 @@
package org.slf4j;
import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.helpers.Reporter;
import org.slf4j.helpers.Util;
-import org.slf4j.impl.StaticMarkerBinder;
+import org.slf4j.spi.SLF4JServiceProvider;
/**
* MarkerFactory is a utility class producing {@link Marker} instances as
@@ -42,20 +43,20 @@ import org.slf4j.impl.StaticMarkerBinder;
* @author Ceki G&uuml;lc&uuml;
*/
public class MarkerFactory {
- static IMarkerFactory markerFactory;
+ static IMarkerFactory MARKER_FACTORY;
private MarkerFactory() {
}
+ // this is where the binding happens
static {
- try {
- markerFactory = StaticMarkerBinder.SINGLETON.getMarkerFactory();
- } catch (NoClassDefFoundError e) {
- markerFactory = new BasicMarkerFactory();
-
- } catch (Exception e) {
- // we should never get here
- Util.report("Unexpected failure while binding MarkerFactory", e);
+ SLF4JServiceProvider provider = LoggerFactory.getProvider();
+ if (provider != null) {
+ MARKER_FACTORY = provider.getMarkerFactory();
+ } else {
+ Reporter.error("Failed to find provider");
+ Reporter.error("Defaulting to BasicMarkerFactory.");
+ MARKER_FACTORY = new BasicMarkerFactory();
}
}
@@ -68,7 +69,7 @@ public class MarkerFactory {
* @return marker
*/
public static Marker getMarker(String name) {
- return markerFactory.getMarker(name);
+ return MARKER_FACTORY.getMarker(name);
}
/**
@@ -79,7 +80,7 @@ public class MarkerFactory {
* @since 1.5.1
*/
public static Marker getDetachedMarker(String name) {
- return markerFactory.getDetachedMarker(name);
+ return MARKER_FACTORY.getDetachedMarker(name);
}
/**
@@ -91,6 +92,6 @@ public class MarkerFactory {
* @return the IMarkerFactory instance in use
*/
public static IMarkerFactory getIMarkerFactory() {
- return markerFactory;
+ return MARKER_FACTORY;
}
} \ No newline at end of file
diff --git a/slf4j-api/src/main/java/org/slf4j/event/DefaultLoggingEvent.java b/slf4j-api/src/main/java/org/slf4j/event/DefaultLoggingEvent.java
new file mode 100755
index 00000000..5a101438
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/DefaultLoggingEvent.java
@@ -0,0 +1,140 @@
+package org.slf4j.event;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+
+/**
+ * A default implementation of {@link LoggingEvent}.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ *
+ * @since 2.0.0
+ */
+public class DefaultLoggingEvent implements LoggingEvent {
+
+ Logger logger;
+ Level level;
+
+ String message;
+ List<Marker> markers;
+ List<Object> arguments;
+ List<KeyValuePair> keyValuePairs;
+
+ Throwable throwable;
+ String threadName;
+ long timeStamp;
+
+ String callerBoundary;
+
+ public DefaultLoggingEvent(Level level, Logger logger) {
+ this.logger = logger;
+ this.level = level;
+ }
+
+ public void addMarker(Marker marker) {
+ if (markers == null) {
+ markers = new ArrayList<>(2);
+ }
+ markers.add(marker);
+ }
+
+ @Override
+ public List<Marker> getMarkers() {
+ return markers;
+ }
+
+ public void addArgument(Object p) {
+ getNonNullArguments().add(p);
+ }
+
+ public void addArguments(Object... args) {
+ getNonNullArguments().addAll(Arrays.asList(args));
+ }
+
+ private List<Object> getNonNullArguments() {
+ if (arguments == null) {
+ arguments = new ArrayList<>(3);
+ }
+ return arguments;
+ }
+
+ @Override
+ public List<Object> getArguments() {
+ return arguments;
+ }
+
+ @Override
+ public Object[] getArgumentArray() {
+ if (arguments == null)
+ return null;
+ return arguments.toArray();
+ }
+
+ public void addKeyValue(String key, Object value) {
+ getNonnullKeyValuePairs().add(new KeyValuePair(key, value));
+ }
+
+ private List<KeyValuePair> getNonnullKeyValuePairs() {
+ if (keyValuePairs == null) {
+ keyValuePairs = new ArrayList<>(4);
+ }
+ return keyValuePairs;
+ }
+
+ @Override
+ public List<KeyValuePair> getKeyValuePairs() {
+ return keyValuePairs;
+ }
+
+ public void setThrowable(Throwable cause) {
+ this.throwable = cause;
+ }
+
+ @Override
+ public Level getLevel() {
+ return level;
+ }
+
+ @Override
+ public String getLoggerName() {
+ return logger.getName();
+ }
+
+ @Override
+ public String getMessage() {
+ return message;
+ }
+
+ public void setMessage(String message) {
+ this.message = message;
+ }
+
+ @Override
+ public Throwable getThrowable() {
+ return throwable;
+ }
+
+ public String getThreadName() {
+ return threadName;
+ }
+
+ public long getTimeStamp() {
+ return timeStamp;
+ }
+
+ public void setTimeStamp(long timeStamp) {
+ this.timeStamp = timeStamp;
+ }
+
+ public void setCallerBoundary(String fqcn) {
+ this.callerBoundary = fqcn;
+ }
+
+ public String getCallerBoundary() {
+ return callerBoundary;
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/EventConstants.java b/slf4j-api/src/main/java/org/slf4j/event/EventConstants.java
new file mode 100755
index 00000000..00975da2
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/EventConstants.java
@@ -0,0 +1,13 @@
+package org.slf4j.event;
+
+import org.slf4j.spi.LocationAwareLogger;
+
+public class EventConstants {
+ public static final int ERROR_INT = LocationAwareLogger.ERROR_INT;
+ public static final int WARN_INT = LocationAwareLogger.WARN_INT;
+ public static final int INFO_INT = LocationAwareLogger.INFO_INT;
+ public static final int DEBUG_INT = LocationAwareLogger.DEBUG_INT;
+ public static final int TRACE_INT = LocationAwareLogger.TRACE_INT;
+ public static final String NA_SUBST = "NA/SubstituteLogger";
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/EventRecordingLogger.java b/slf4j-api/src/main/java/org/slf4j/event/EventRecordingLogger.java
new file mode 100755
index 00000000..b21a2e45
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/EventRecordingLogger.java
@@ -0,0 +1,84 @@
+package org.slf4j.event;
+
+import java.util.Queue;
+
+import org.slf4j.Marker;
+import org.slf4j.helpers.LegacyAbstractLogger;
+import org.slf4j.helpers.SubstituteLogger;
+
+/**
+ *
+ * This class is used to record events during the initialization phase of the
+ * underlying logging framework. It is called by {@link SubstituteLogger}.
+ *
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @author Wessel van Norel
+ *
+ */
+public class EventRecordingLogger extends LegacyAbstractLogger {
+
+ private static final long serialVersionUID = -176083308134819629L;
+
+ String name;
+ SubstituteLogger logger;
+ Queue<SubstituteLoggingEvent> eventQueue;
+
+ // as an event recording logger we have no choice but to record all events
+ final static boolean RECORD_ALL_EVENTS = true;
+
+ public EventRecordingLogger(SubstituteLogger logger, Queue<SubstituteLoggingEvent> eventQueue) {
+ this.logger = logger;
+ this.name = logger.getName();
+ this.eventQueue = eventQueue;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public boolean isTraceEnabled() {
+ return RECORD_ALL_EVENTS;
+ }
+
+ public boolean isDebugEnabled() {
+ return RECORD_ALL_EVENTS;
+ }
+
+ public boolean isInfoEnabled() {
+ return RECORD_ALL_EVENTS;
+ }
+
+ public boolean isWarnEnabled() {
+ return RECORD_ALL_EVENTS;
+ }
+
+ public boolean isErrorEnabled() {
+ return RECORD_ALL_EVENTS;
+ }
+
+ // WARNING: this method assumes that any throwable is properly extracted
+ protected void handleNormalizedLoggingCall(Level level, Marker marker, String msg, Object[] args, Throwable throwable) {
+ SubstituteLoggingEvent loggingEvent = new SubstituteLoggingEvent();
+ loggingEvent.setTimeStamp(System.currentTimeMillis());
+ loggingEvent.setLevel(level);
+ loggingEvent.setLogger(logger);
+ loggingEvent.setLoggerName(name);
+ if (marker != null) {
+ loggingEvent.addMarker(marker);
+ }
+ loggingEvent.setMessage(msg);
+ loggingEvent.setThreadName(Thread.currentThread().getName());
+
+ loggingEvent.setArgumentArray(args);
+ loggingEvent.setThrowable(throwable);
+
+ eventQueue.add(loggingEvent);
+
+ }
+
+ @Override
+ protected String getFullyQualifiedCallerName() {
+ return null;
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/KeyValuePair.java b/slf4j-api/src/main/java/org/slf4j/event/KeyValuePair.java
new file mode 100755
index 00000000..9aebe198
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/KeyValuePair.java
@@ -0,0 +1,32 @@
+package org.slf4j.event;
+
+import java.util.Objects;
+
+public class KeyValuePair {
+
+ public final String key;
+ public final Object value;
+
+ public KeyValuePair(String key, Object value) {
+ this.key = key;
+ this.value = value;
+ }
+
+ @Override
+ public String toString() {
+ return String.valueOf(key) + "=\"" + String.valueOf(value) +"\"";
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if(this == o) return true;
+ if(o == null || getClass() != o.getClass()) return false;
+ KeyValuePair that = (KeyValuePair) o;
+ return Objects.equals(key, that.key) && Objects.equals(value, that.value);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(key, value);
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/Level.java b/slf4j-api/src/main/java/org/slf4j/event/Level.java
new file mode 100755
index 00000000..a288b06b
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/Level.java
@@ -0,0 +1,56 @@
+package org.slf4j.event;
+
+import static org.slf4j.event.EventConstants.DEBUG_INT;
+import static org.slf4j.event.EventConstants.ERROR_INT;
+import static org.slf4j.event.EventConstants.INFO_INT;
+import static org.slf4j.event.EventConstants.TRACE_INT;
+import static org.slf4j.event.EventConstants.WARN_INT;
+
+/**
+ * SLF4J's internal representation of Level.
+ *
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 1.7.15
+ */
+public enum Level {
+
+ ERROR(ERROR_INT, "ERROR"), WARN(WARN_INT, "WARN"), INFO(INFO_INT, "INFO"), DEBUG(DEBUG_INT, "DEBUG"), TRACE(TRACE_INT, "TRACE");
+
+ private final int levelInt;
+ private final String levelStr;
+
+ Level(int i, String s) {
+ levelInt = i;
+ levelStr = s;
+ }
+
+ public int toInt() {
+ return levelInt;
+ }
+
+ public static Level intToLevel(int levelInt) {
+ switch (levelInt) {
+ case (TRACE_INT):
+ return TRACE;
+ case (DEBUG_INT):
+ return DEBUG;
+ case (INFO_INT):
+ return INFO;
+ case (WARN_INT):
+ return WARN;
+ case (ERROR_INT):
+ return ERROR;
+ default:
+ throw new IllegalArgumentException("Level integer [" + levelInt + "] not recognized.");
+ }
+ }
+
+ /**
+ * Returns the string representation of this Level.
+ */
+ public String toString() {
+ return levelStr;
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/LoggingEvent.java b/slf4j-api/src/main/java/org/slf4j/event/LoggingEvent.java
new file mode 100755
index 00000000..27bdf3e2
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/LoggingEvent.java
@@ -0,0 +1,45 @@
+package org.slf4j.event;
+
+import java.util.List;
+
+import org.slf4j.Marker;
+
+/**
+ * The minimal interface sufficient for the restitution of data passed
+ * by the user to the SLF4J API.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 1.7.15
+ */
+public interface LoggingEvent {
+
+ Level getLevel();
+
+ String getLoggerName();
+
+ String getMessage();
+
+ List<Object> getArguments();
+
+ Object[] getArgumentArray();
+
+ List<Marker> getMarkers();
+
+ List<KeyValuePair> getKeyValuePairs();
+
+ Throwable getThrowable();
+
+ long getTimeStamp();
+
+ String getThreadName();
+
+ /**
+ * Returns the presumed caller boundary provided by the logging library (not the user of the library).
+ * Null by default.
+ *
+ * @return presumed caller, null by default.
+ */
+ default String getCallerBoundary() {
+ return null;
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/event/SubstituteLoggingEvent.java b/slf4j-api/src/main/java/org/slf4j/event/SubstituteLoggingEvent.java
new file mode 100755
index 00000000..4c8f7ad7
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/event/SubstituteLoggingEvent.java
@@ -0,0 +1,115 @@
+package org.slf4j.event;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import org.slf4j.Marker;
+import org.slf4j.helpers.SubstituteLogger;
+
+public class SubstituteLoggingEvent implements LoggingEvent {
+
+ Level level;
+ List<Marker> markers;
+ String loggerName;
+ SubstituteLogger logger;
+ String threadName;
+ String message;
+ Object[] argArray;
+ List<KeyValuePair> keyValuePairList;
+
+ long timeStamp;
+ Throwable throwable;
+
+ public Level getLevel() {
+ return level;
+ }
+
+ public void setLevel(Level level) {
+ this.level = level;
+ }
+
+ public List<Marker> getMarkers() {
+ return markers;
+ }
+
+ public void addMarker(Marker marker) {
+ if (marker == null)
+ return;
+
+ if (markers == null) {
+ markers = new ArrayList<>(2);
+ }
+
+ markers.add(marker);
+ }
+
+ public String getLoggerName() {
+ return loggerName;
+ }
+
+ public void setLoggerName(String loggerName) {
+ this.loggerName = loggerName;
+ }
+
+ public SubstituteLogger getLogger() {
+ return logger;
+ }
+
+ public void setLogger(SubstituteLogger logger) {
+ this.logger = logger;
+ }
+
+ public String getMessage() {
+ return message;
+ }
+
+ public void setMessage(String message) {
+ this.message = message;
+ }
+
+ public Object[] getArgumentArray() {
+ return argArray;
+ }
+
+ public void setArgumentArray(Object[] argArray) {
+ this.argArray = argArray;
+ }
+
+ @Override
+ public List<Object> getArguments() {
+ if (argArray == null) {
+ return null;
+ }
+ return Arrays.asList(argArray);
+ }
+
+ public long getTimeStamp() {
+ return timeStamp;
+ }
+
+ public void setTimeStamp(long timeStamp) {
+ this.timeStamp = timeStamp;
+ }
+
+ public String getThreadName() {
+ return threadName;
+ }
+
+ public void setThreadName(String threadName) {
+ this.threadName = threadName;
+ }
+
+ public Throwable getThrowable() {
+ return throwable;
+ }
+
+ public void setThrowable(Throwable throwable) {
+ this.throwable = throwable;
+ }
+
+ @Override
+ public List<KeyValuePair> getKeyValuePairs() {
+ return keyValuePairList;
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/AbstractLogger.java b/slf4j-api/src/main/java/org/slf4j/helpers/AbstractLogger.java
new file mode 100644
index 00000000..0caaf810
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/AbstractLogger.java
@@ -0,0 +1,423 @@
+/**
+ * Copyright (c) 2004-2019 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.helpers;
+
+import java.io.ObjectStreamException;
+import java.io.Serializable;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.Marker;
+import org.slf4j.event.Level;
+
+/**
+ * An abstract implementation which delegates actual logging work to the
+ * {@link #handleNormalizedLoggingCall(Level, Marker, String, Object[], Throwable)} method.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 2.0
+ */
+public abstract class AbstractLogger implements Logger, Serializable {
+
+ private static final long serialVersionUID = -2529255052481744503L;
+
+ protected String name;
+
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * Replace this instance with a homonymous (same name) logger returned
+ * by LoggerFactory. Note that this method is only called during
+ * deserialization.
+ *
+ * <p>
+ * This approach will work well if the desired ILoggerFactory is the one
+ * referenced by {@link org.slf4j.LoggerFactory} However, if the user manages its logger hierarchy
+ * through a different (non-static) mechanism, e.g. dependency injection, then
+ * this approach would be mostly counterproductive.
+ *
+ * @return logger with same name as returned by LoggerFactory
+ * @throws ObjectStreamException
+ */
+ protected Object readResolve() throws ObjectStreamException {
+ // using getName() instead of this.name works even for
+ // NOPLogger
+ return LoggerFactory.getLogger(getName());
+ }
+
+ @Override
+ public void trace(String msg) {
+ if (isTraceEnabled()) {
+ handle_0ArgsCall(Level.TRACE, null, msg, null);
+ }
+ }
+
+ @Override
+ public void trace(String format, Object arg) {
+ if (isTraceEnabled()) {
+ handle_1ArgsCall(Level.TRACE, null, format, arg);
+ }
+ }
+
+ @Override
+ public void trace(String format, Object arg1, Object arg2) {
+ if (isTraceEnabled()) {
+ handle2ArgsCall(Level.TRACE, null, format, arg1, arg2);
+ }
+ }
+
+ @Override
+ public void trace(String format, Object... arguments) {
+ if (isTraceEnabled()) {
+ handleArgArrayCall(Level.TRACE, null, format, arguments);
+ }
+ }
+
+ @Override
+ public void trace(String msg, Throwable t) {
+ if (isTraceEnabled()) {
+ handle_0ArgsCall(Level.TRACE, null, msg, t);
+ }
+ }
+
+ @Override
+ public void trace(Marker marker, String msg) {
+ if (isTraceEnabled(marker)) {
+ handle_0ArgsCall(Level.TRACE, marker, msg, null);
+ }
+ }
+
+ @Override
+ public void trace(Marker marker, String format, Object arg) {
+ if (isTraceEnabled(marker)) {
+ handle_1ArgsCall(Level.TRACE, marker, format, arg);
+ }
+ }
+
+ @Override
+ public void trace(Marker marker, String format, Object arg1, Object arg2) {
+ if (isTraceEnabled(marker)) {
+ handle2ArgsCall(Level.TRACE, marker, format, arg1, arg2);
+ }
+ }
+
+ @Override
+ public void trace(Marker marker, String format, Object... argArray) {
+ if (isTraceEnabled(marker)) {
+ handleArgArrayCall(Level.TRACE, marker, format, argArray);
+ }
+ }
+
+ public void trace(Marker marker, String msg, Throwable t) {
+ if (isTraceEnabled(marker)) {
+ handle_0ArgsCall(Level.TRACE, marker, msg, t);
+ }
+ }
+
+ public void debug(String msg) {
+ if (isDebugEnabled()) {
+ handle_0ArgsCall(Level.DEBUG, null, msg, null);
+ }
+ }
+
+ public void debug(String format, Object arg) {
+ if (isDebugEnabled()) {
+ handle_1ArgsCall(Level.DEBUG, null, format, arg);
+ }
+ }
+
+ public void debug(String format, Object arg1, Object arg2) {
+ if (isDebugEnabled()) {
+ handle2ArgsCall(Level.DEBUG, null, format, arg1, arg2);
+ }
+ }
+
+ public void debug(String format, Object... arguments) {
+ if (isDebugEnabled()) {
+ handleArgArrayCall(Level.DEBUG, null, format, arguments);
+ }
+ }
+
+ public void debug(String msg, Throwable t) {
+ if (isDebugEnabled()) {
+ handle_0ArgsCall(Level.DEBUG, null, msg, t);
+ }
+ }
+
+ public void debug(Marker marker, String msg) {
+ if (isDebugEnabled(marker)) {
+ handle_0ArgsCall(Level.DEBUG, marker, msg, null);
+ }
+ }
+
+ public void debug(Marker marker, String format, Object arg) {
+ if (isDebugEnabled(marker)) {
+ handle_1ArgsCall(Level.DEBUG, marker, format, arg);
+ }
+ }
+
+ public void debug(Marker marker, String format, Object arg1, Object arg2) {
+ if (isDebugEnabled(marker)) {
+ handle2ArgsCall(Level.DEBUG, marker, format, arg1, arg2);
+ }
+ }
+
+ public void debug(Marker marker, String format, Object... arguments) {
+ if (isDebugEnabled(marker)) {
+ handleArgArrayCall(Level.DEBUG, marker, format, arguments);
+ }
+ }
+
+ public void debug(Marker marker, String msg, Throwable t) {
+ if (isDebugEnabled(marker)) {
+ handle_0ArgsCall(Level.DEBUG, marker, msg, t);
+ }
+ }
+
+ public void info(String msg) {
+ if (isInfoEnabled()) {
+ handle_0ArgsCall(Level.INFO, null, msg, null);
+ }
+ }
+
+ public void info(String format, Object arg) {
+ if (isInfoEnabled()) {
+ handle_1ArgsCall(Level.INFO, null, format, arg);
+ }
+ }
+
+ public void info(String format, Object arg1, Object arg2) {
+ if (isInfoEnabled()) {
+ handle2ArgsCall(Level.INFO, null, format, arg1, arg2);
+ }
+ }
+
+ public void info(String format, Object... arguments) {
+ if (isInfoEnabled()) {
+ handleArgArrayCall(Level.INFO, null, format, arguments);
+ }
+ }
+
+ public void info(String msg, Throwable t) {
+ if (isInfoEnabled()) {
+ handle_0ArgsCall(Level.INFO, null, msg, t);
+ }
+ }
+
+ public void info(Marker marker, String msg) {
+ if (isInfoEnabled(marker)) {
+ handle_0ArgsCall(Level.INFO, marker, msg, null);
+ }
+ }
+
+ public void info(Marker marker, String format, Object arg) {
+ if (isInfoEnabled(marker)) {
+ handle_1ArgsCall(Level.INFO, marker, format, arg);
+ }
+ }
+
+ public void info(Marker marker, String format, Object arg1, Object arg2) {
+ if (isInfoEnabled(marker)) {
+ handle2ArgsCall(Level.INFO, marker, format, arg1, arg2);
+ }
+ }
+
+ public void info(Marker marker, String format, Object... arguments) {
+ if (isInfoEnabled(marker)) {
+ handleArgArrayCall(Level.INFO, marker, format, arguments);
+ }
+ }
+
+ public void info(Marker marker, String msg, Throwable t) {
+ if (isInfoEnabled(marker)) {
+ handle_0ArgsCall(Level.INFO, marker, msg, t);
+ }
+ }
+
+ public void warn(String msg) {
+ if (isWarnEnabled()) {
+ handle_0ArgsCall(Level.WARN, null, msg, null);
+ }
+ }
+
+ public void warn(String format, Object arg) {
+ if (isWarnEnabled()) {
+ handle_1ArgsCall(Level.WARN, null, format, arg);
+ }
+ }
+
+ public void warn(String format, Object arg1, Object arg2) {
+ if (isWarnEnabled()) {
+ handle2ArgsCall(Level.WARN, null, format, arg1, arg2);
+ }
+ }
+
+ public void warn(String format, Object... arguments) {
+ if (isWarnEnabled()) {
+ handleArgArrayCall(Level.WARN, null, format, arguments);
+ }
+ }
+
+ public void warn(String msg, Throwable t) {
+ if (isWarnEnabled()) {
+ handle_0ArgsCall(Level.WARN, null, msg, t);
+ }
+ }
+
+ public void warn(Marker marker, String msg) {
+ if (isWarnEnabled(marker)) {
+ handle_0ArgsCall(Level.WARN, marker, msg, null);
+ }
+ }
+
+ public void warn(Marker marker, String format, Object arg) {
+ if (isWarnEnabled(marker)) {
+ handle_1ArgsCall(Level.WARN, marker, format, arg);
+ }
+ }
+
+ public void warn(Marker marker, String format, Object arg1, Object arg2) {
+ if (isWarnEnabled(marker)) {
+ handle2ArgsCall(Level.WARN, marker, format, arg1, arg2);
+ }
+ }
+
+ public void warn(Marker marker, String format, Object... arguments) {
+ if (isWarnEnabled(marker)) {
+ handleArgArrayCall(Level.WARN, marker, format, arguments);
+ }
+ }
+
+ public void warn(Marker marker, String msg, Throwable t) {
+ if (isWarnEnabled(marker)) {
+ handle_0ArgsCall(Level.WARN, marker, msg, t);
+ }
+ }
+
+ public void error(String msg) {
+ if (isErrorEnabled()) {
+ handle_0ArgsCall(Level.ERROR, null, msg, null);
+ }
+ }
+
+ public void error(String format, Object arg) {
+ if (isErrorEnabled()) {
+ handle_1ArgsCall(Level.ERROR, null, format, arg);
+ }
+ }
+
+ public void error(String format, Object arg1, Object arg2) {
+ if (isErrorEnabled()) {
+ handle2ArgsCall(Level.ERROR, null, format, arg1, arg2);
+ }
+ }
+
+ public void error(String format, Object... arguments) {
+ if (isErrorEnabled()) {
+ handleArgArrayCall(Level.ERROR, null, format, arguments);
+ }
+ }
+
+ public void error(String msg, Throwable t) {
+ if (isErrorEnabled()) {
+ handle_0ArgsCall(Level.ERROR, null, msg, t);
+ }
+ }
+
+ public void error(Marker marker, String msg) {
+ if (isErrorEnabled(marker)) {
+ handle_0ArgsCall(Level.ERROR, marker, msg, null);
+ }
+ }
+
+ public void error(Marker marker, String format, Object arg) {
+ if (isErrorEnabled(marker)) {
+ handle_1ArgsCall(Level.ERROR, marker, format, arg);
+ }
+ }
+
+ public void error(Marker marker, String format, Object arg1, Object arg2) {
+ if (isErrorEnabled(marker)) {
+ handle2ArgsCall(Level.ERROR, marker, format, arg1, arg2);
+ }
+ }
+
+ public void error(Marker marker, String format, Object... arguments) {
+ if (isErrorEnabled(marker)) {
+ handleArgArrayCall(Level.ERROR, marker, format, arguments);
+ }
+ }
+
+ public void error(Marker marker, String msg, Throwable t) {
+ if (isErrorEnabled(marker)) {
+ handle_0ArgsCall(Level.ERROR, marker, msg, t);
+ }
+ }
+
+ private void handle_0ArgsCall(Level level, Marker marker, String msg, Throwable t) {
+ handleNormalizedLoggingCall(level, marker, msg, null, t);
+ }
+
+ private void handle_1ArgsCall(Level level, Marker marker, String msg, Object arg1) {
+ handleNormalizedLoggingCall(level, marker, msg, new Object[] { arg1 }, null);
+ }
+
+ private void handle2ArgsCall(Level level, Marker marker, String msg, Object arg1, Object arg2) {
+ if (arg2 instanceof Throwable) {
+ handleNormalizedLoggingCall(level, marker, msg, new Object[] { arg1 }, (Throwable) arg2);
+ } else {
+ handleNormalizedLoggingCall(level, marker, msg, new Object[] { arg1, arg2 }, null);
+ }
+ }
+
+ private void handleArgArrayCall(Level level, Marker marker, String msg, Object[] args) {
+ Throwable throwableCandidate = MessageFormatter.getThrowableCandidate(args);
+ if (throwableCandidate != null) {
+ Object[] trimmedCopy = MessageFormatter.trimmedCopy(args);
+ handleNormalizedLoggingCall(level, marker, msg, trimmedCopy, throwableCandidate);
+ } else {
+ handleNormalizedLoggingCall(level, marker, msg, args, null);
+ }
+ }
+
+ abstract protected String getFullyQualifiedCallerName();
+
+ /**
+ * Given various arguments passed as parameters, perform actual logging.
+ *
+ * <p>This method assumes that the separation of the args array into actual
+ * objects and a throwable has been already operated.
+ *
+ * @param level the SLF4J level for this event
+ * @param marker The marker to be used for this event, may be null.
+ * @param messagePattern The message pattern which will be parsed and formatted
+ * @param arguments the array of arguments to be formatted, may be null
+ * @param throwable The exception whose stack trace should be logged, may be null
+ */
+ abstract protected void handleNormalizedLoggingCall(Level level, Marker marker, String messagePattern, Object[] arguments, Throwable throwable);
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMDCAdapter.java b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMDCAdapter.java
index 67ab9b5a..95cb904a 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMDCAdapter.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMDCAdapter.java
@@ -27,45 +27,43 @@ package org.slf4j.helpers;
import org.slf4j.spi.MDCAdapter;
import java.util.*;
-import java.util.Map;
/**
* Basic MDC implementation, which can be used with logging systems that lack
* out-of-the-box MDC support.
- *
+ *
* This code was initially inspired by logback's LogbackMDCAdapter. However,
* LogbackMDCAdapter has evolved and is now considerably more sophisticated.
*
* @author Ceki Gulcu
* @author Maarten Bosteels
+ * @author Lukasz Cwik
*
* @since 1.5.0
*/
public class BasicMDCAdapter implements MDCAdapter {
- private InheritableThreadLocal<Map<String, String>> inheritableThreadLocal = new InheritableThreadLocal<Map<String, String>>();
+ private final ThreadLocalMapOfStacks threadLocalMapOfDeques = new ThreadLocalMapOfStacks();
- static boolean isJDK14() {
- try {
- String javaVersion = System.getProperty("java.version");
- return javaVersion.startsWith("1.4");
- } catch (SecurityException se) {
- // punt and assume JDK 1.5 or later
- return false;
+ private final InheritableThreadLocal<Map<String, String>> inheritableThreadLocalMap = new InheritableThreadLocal<Map<String, String>>() {
+ @Override
+ protected Map<String, String> childValue(Map<String, String> parentValue) {
+ if (parentValue == null) {
+ return null;
+ }
+ return new HashMap<>(parentValue);
}
- }
-
- static boolean IS_JDK14 = isJDK14();
+ };
/**
* Put a context value (the <code>val</code> parameter) as identified with
* the <code>key</code> parameter into the current thread's context map.
* Note that contrary to log4j, the <code>val</code> parameter can be null.
- *
+ *
* <p>
* If the current thread does not have a context map it is created as a side
* effect of this call.
- *
+ *
* @throws IllegalArgumentException
* in case the "key" parameter is null
*/
@@ -73,10 +71,10 @@ public class BasicMDCAdapter implements MDCAdapter {
if (key == null) {
throw new IllegalArgumentException("key cannot be null");
}
- Map<String, String> map = (Map<String, String>) inheritableThreadLocal.get();
+ Map<String, String> map = inheritableThreadLocalMap.get();
if (map == null) {
- map = Collections.<String, String> synchronizedMap(new HashMap<String, String>());
- inheritableThreadLocal.set(map);
+ map = new HashMap<>();
+ inheritableThreadLocalMap.set(map);
}
map.put(key, val);
}
@@ -85,19 +83,19 @@ public class BasicMDCAdapter implements MDCAdapter {
* Get the context identified by the <code>key</code> parameter.
*/
public String get(String key) {
- Map<String, String> Map = (Map<String, String>) inheritableThreadLocal.get();
- if ((Map != null) && (key != null)) {
- return (String) Map.get(key);
+ Map<String, String> map = inheritableThreadLocalMap.get();
+ if ((map != null) && (key != null)) {
+ return map.get(key);
} else {
return null;
}
}
/**
- * Remove the the context identified by the <code>key</code> parameter.
+ * Remove the context identified by the <code>key</code> parameter.
*/
public void remove(String key) {
- Map<String, String> map = (Map<String, String>) inheritableThreadLocal.get();
+ Map<String, String> map = inheritableThreadLocalMap.get();
if (map != null) {
map.remove(key);
}
@@ -107,27 +105,21 @@ public class BasicMDCAdapter implements MDCAdapter {
* Clear all entries in the MDC.
*/
public void clear() {
- Map<String, String> map = (Map<String, String>) inheritableThreadLocal.get();
+ Map<String, String> map = inheritableThreadLocalMap.get();
if (map != null) {
map.clear();
- // the InheritableThreadLocal.remove method was introduced in JDK 1.5
- // Thus, invoking clear() on previous JDK 1.4 will fail
- if (isJDK14()) {
- inheritableThreadLocal.set(null);
- } else {
- inheritableThreadLocal.remove();
- }
+ inheritableThreadLocalMap.remove();
}
}
/**
* Returns the keys in the MDC as a {@link Set} of {@link String}s The
* returned value can be null.
- *
+ *
* @return the keys in the MDC
*/
public Set<String> getKeys() {
- Map<String, String> map = (Map<String, String>) inheritableThreadLocal.get();
+ Map<String, String> map = inheritableThreadLocalMap.get();
if (map != null) {
return map.keySet();
} else {
@@ -136,26 +128,43 @@ public class BasicMDCAdapter implements MDCAdapter {
}
/**
- * Return a copy of the current thread's context map.
+ * Return a copy of the current thread's context map.
* Returned value may be null.
- *
+ *
*/
public Map<String, String> getCopyOfContextMap() {
- Map<String, String> oldMap = (Map<String, String>) inheritableThreadLocal.get();
+ Map<String, String> oldMap = inheritableThreadLocalMap.get();
if (oldMap != null) {
- Map<String, String> newMap = Collections.<String, String> synchronizedMap(new HashMap<String, String>());
- synchronized (oldMap) {
- newMap.putAll(oldMap);
- }
- return newMap;
+ return new HashMap<>(oldMap);
} else {
return null;
}
}
public void setContextMap(Map<String, String> contextMap) {
- Map<String, String> map = Collections.<String, String> synchronizedMap(new HashMap<String, String>(contextMap));
- inheritableThreadLocal.set(map);
+ Map<String, String> copy = null;
+ if (contextMap != null) {
+ copy = new HashMap<>(contextMap);
+ }
+ inheritableThreadLocalMap.set(copy);
+ }
+
+ @Override
+ public void pushByKey(String key, String value) {
+ threadLocalMapOfDeques.pushByKey(key, value);
}
+ @Override
+ public String popByKey(String key) {
+ return threadLocalMapOfDeques.popByKey(key);
+ }
+
+ @Override
+ public Deque<String> getCopyOfDequeByKey(String key) {
+ return threadLocalMapOfDeques.getCopyOfDequeByKey(key);
+ }
+ @Override
+ public void clearDequeByKey(String key) {
+ threadLocalMapOfDeques.clearDequeByKey(key);
+ }
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarker.java b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarker.java
index b296d5d2..9e3a6aee 100755
--- a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarker.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarker.java
@@ -24,10 +24,9 @@
*/
package org.slf4j.helpers;
-import java.util.Collections;
import java.util.Iterator;
import java.util.List;
-import java.util.Vector;
+import java.util.concurrent.CopyOnWriteArrayList;
import org.slf4j.Marker;
@@ -39,10 +38,9 @@ import org.slf4j.Marker;
*/
public class BasicMarker implements Marker {
- private static final long serialVersionUID = 1803952589649545191L;
-
+ private static final long serialVersionUID = -2849567615646933777L;
private final String name;
- private List<Marker> referenceList;
+ private final List<Marker> referenceList = new CopyOnWriteArrayList<>();
BasicMarker(String name) {
if (name == null) {
@@ -55,7 +53,7 @@ public class BasicMarker implements Marker {
return name;
}
- public synchronized void add(Marker reference) {
+ public void add(Marker reference) {
if (reference == null) {
throw new IllegalArgumentException("A null value cannot be added to a Marker as reference.");
}
@@ -65,49 +63,28 @@ public class BasicMarker implements Marker {
return;
} else if (reference.contains(this)) { // avoid recursion
- // a potential reference should not its future "parent" as a reference
+ // a potential reference should not hold its future "parent" as a reference
return;
} else {
- // let's add the reference
- if (referenceList == null) {
- referenceList = new Vector<Marker>();
- }
referenceList.add(reference);
}
-
}
- public synchronized boolean hasReferences() {
- return ((referenceList != null) && (referenceList.size() > 0));
+ public boolean hasReferences() {
+ return (referenceList.size() > 0);
}
+ @Deprecated
public boolean hasChildren() {
return hasReferences();
}
- public synchronized Iterator<Marker> iterator() {
- if (referenceList != null) {
- return referenceList.iterator();
- } else {
- List<Marker> emptyList = Collections.emptyList();
- return emptyList.iterator();
- }
+ public Iterator<Marker> iterator() {
+ return referenceList.iterator();
}
- public synchronized boolean remove(Marker referenceToRemove) {
- if (referenceList == null) {
- return false;
- }
-
- int size = referenceList.size();
- for (int i = 0; i < size; i++) {
- Marker m = (Marker) referenceList.get(i);
- if (referenceToRemove.equals(m)) {
- referenceList.remove(i);
- return true;
- }
- }
- return false;
+ public boolean remove(Marker referenceToRemove) {
+ return referenceList.remove(referenceToRemove);
}
public boolean contains(Marker other) {
@@ -120,8 +97,7 @@ public class BasicMarker implements Marker {
}
if (hasReferences()) {
- for (int i = 0; i < referenceList.size(); i++) {
- Marker ref = (Marker) referenceList.get(i);
+ for (Marker ref : referenceList) {
if (ref.contains(other)) {
return true;
}
@@ -143,8 +119,7 @@ public class BasicMarker implements Marker {
}
if (hasReferences()) {
- for (int i = 0; i < referenceList.size(); i++) {
- Marker ref = (Marker) referenceList.get(i);
+ for (Marker ref : referenceList) {
if (ref.contains(name)) {
return true;
}
@@ -153,9 +128,9 @@ public class BasicMarker implements Marker {
return false;
}
- private static String OPEN = "[ ";
- private static String CLOSE = " ]";
- private static String SEP = ", ";
+ private static final String OPEN = "[ ";
+ private static final String CLOSE = " ]";
+ private static final String SEP = ", ";
public boolean equals(Object obj) {
if (this == obj)
@@ -182,7 +157,7 @@ public class BasicMarker implements Marker {
StringBuilder sb = new StringBuilder(this.getName());
sb.append(' ').append(OPEN);
while (it.hasNext()) {
- reference = (Marker) it.next();
+ reference = it.next();
sb.append(reference.getName());
if (it.hasNext()) {
sb.append(SEP);
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarkerFactory.java b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarkerFactory.java
index 5139bb66..06b0ec58 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarkerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/BasicMarkerFactory.java
@@ -41,7 +41,7 @@ import org.slf4j.Marker;
*/
public class BasicMarkerFactory implements IMarkerFactory {
- private final ConcurrentMap<String, Marker> markerMap = new ConcurrentHashMap<String, Marker>();
+ private final ConcurrentMap<String, Marker> markerMap = new ConcurrentHashMap<>();
/**
* Regular users should <em>not</em> create
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/CheckReturnValue.java b/slf4j-api/src/main/java/org/slf4j/helpers/CheckReturnValue.java
new file mode 100644
index 00000000..e1c9803a
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/CheckReturnValue.java
@@ -0,0 +1,30 @@
+package org.slf4j.helpers;
+
+
+import org.slf4j.Marker;
+
+import java.lang.annotation.*;
+
+/**
+ * <p>Used to annotate methods in the {@link org.slf4j.spi.LoggingEventBuilder} interface
+ * which return an instance of LoggingEventBuilder (usually as <code>this</code>). Such
+ * methods should be followed by one of the terminating <code>log()</code> methods returning
+ * <code>void</code>.</p>
+ * <p></p>
+ * <p>IntelliJ IDEA supports a check for annotations named as <code>CheckReturnValue</code>
+ * regardless of the containing package. For more information on this feature in IntelliJ IDEA,
+ * select File &#8594; Setting &#8594; Editor &#8594; Inspections and then Java &#8594; Probable Bugs &#8594;
+ * Result of method call ignored. </p>
+ * <p></p>
+ *
+ * <p>As for Eclipse, this feature has been requested in
+ * <a href="https://bugs.eclipse.org/bugs/show_bug.cgi?id=572496">bug 572496</a></p>
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 2.0.0-beta1
+ */
+@Documented
+@Target( { ElementType.METHOD })
+@Retention(RetentionPolicy.RUNTIME)
+public @interface CheckReturnValue {
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/FormattingTuple.java b/slf4j-api/src/main/java/org/slf4j/helpers/FormattingTuple.java
index 8d49ba45..a416e1d4 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/FormattingTuple.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/FormattingTuple.java
@@ -33,9 +33,9 @@ public class FormattingTuple {
static public FormattingTuple NULL = new FormattingTuple(null);
- private String message;
- private Throwable throwable;
- private Object[] argArray;
+ private final String message;
+ private final Throwable throwable;
+ private final Object[] argArray;
public FormattingTuple(String message) {
this(message, null, null);
@@ -44,21 +44,7 @@ public class FormattingTuple {
public FormattingTuple(String message, Object[] argArray, Throwable throwable) {
this.message = message;
this.throwable = throwable;
- if (throwable == null) {
- this.argArray = argArray;
- } else {
- this.argArray = trimmedCopy(argArray);
- }
- }
-
- static Object[] trimmedCopy(Object[] argArray) {
- if (argArray == null || argArray.length == 0) {
- throw new IllegalStateException("non-sensical empty or null argument array");
- }
- final int trimemdLen = argArray.length - 1;
- Object[] trimmed = new Object[trimemdLen];
- System.arraycopy(argArray, 0, trimmed, 0, trimemdLen);
- return trimmed;
+ this.argArray = argArray;
}
public String getMessage() {
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/LegacyAbstractLogger.java b/slf4j-api/src/main/java/org/slf4j/helpers/LegacyAbstractLogger.java
new file mode 100644
index 00000000..dcc90009
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/LegacyAbstractLogger.java
@@ -0,0 +1,39 @@
+package org.slf4j.helpers;
+
+import org.slf4j.Marker;
+
+/**
+ * Provides minimal default implementations for {@link #isTraceEnabled(Marker)}, {@link #isDebugEnabled(Marker)} and other similar methods.
+ *
+ * @since 2.0
+ */
+abstract public class LegacyAbstractLogger extends AbstractLogger {
+
+ private static final long serialVersionUID = -7041884104854048950L;
+
+ @Override
+ public boolean isTraceEnabled(Marker marker) {
+ return isTraceEnabled();
+ }
+
+ @Override
+ public boolean isDebugEnabled(Marker marker) {
+ return isDebugEnabled();
+ }
+
+ @Override
+ public boolean isInfoEnabled(Marker marker) {
+ return isInfoEnabled();
+ }
+
+ @Override
+ public boolean isWarnEnabled(Marker marker) {
+ return isWarnEnabled();
+ }
+
+ @Override
+ public boolean isErrorEnabled(Marker marker) {
+ return isErrorEnabled();
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/MarkerIgnoringBase.java b/slf4j-api/src/main/java/org/slf4j/helpers/MarkerIgnoringBase.java
index dd765384..715cec75 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/MarkerIgnoringBase.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/MarkerIgnoringBase.java
@@ -34,6 +34,7 @@ import org.slf4j.Marker;
* any marker data passed as argument.
*
* @author Ceki Gulcu
+ * @deprecated
*/
public abstract class MarkerIgnoringBase extends NamedLoggerBase implements Logger {
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/MessageFormatter.java b/slf4j-api/src/main/java/org/slf4j/helpers/MessageFormatter.java
index cbecbfc6..47f95daa 100755
--- a/slf4j-api/src/main/java/org/slf4j/helpers/MessageFormatter.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/MessageFormatter.java
@@ -33,14 +33,14 @@ import java.util.Map;
/**
* Formats messages according to very simple substitution rules. Substitutions
* can be made 1, 2 or more arguments.
- *
+ *
* <p>
* For example,
- *
+ *
* <pre>
* MessageFormatter.format(&quot;Hi {}.&quot;, &quot;there&quot;)
* </pre>
- *
+ *
* will return the string "Hi there.".
* <p>
* The {} pair is called the <em>formatting anchor</em>. It serves to designate
@@ -50,48 +50,48 @@ import java.util.Map;
* In case your message contains the '{' or the '}' character, you do not have
* to do anything special unless the '}' character immediately follows '{'. For
* example,
- *
+ *
* <pre>
* MessageFormatter.format(&quot;Set {1,2,3} is not equal to {}.&quot;, &quot;1,2&quot;);
* </pre>
- *
+ *
* will return the string "Set {1,2,3} is not equal to 1,2.".
- *
+ *
* <p>
* If for whatever reason you need to place the string "{}" in the message
* without its <em>formatting anchor</em> meaning, then you need to escape the
* '{' character with '\', that is the backslash character. Only the '{'
* character should be escaped. There is no need to escape the '}' character.
* For example,
- *
+ *
* <pre>
* MessageFormatter.format(&quot;Set \\{} is not equal to {}.&quot;, &quot;1,2&quot;);
* </pre>
- *
+ *
* will return the string "Set {} is not equal to 1,2.".
- *
+ *
* <p>
* The escaping behavior just described can be overridden by escaping the escape
* character '\'. Calling
- *
+ *
* <pre>
* MessageFormatter.format(&quot;File name is C:\\\\{}.&quot;, &quot;file.zip&quot;);
* </pre>
- *
+ *
* will return the string "File name is C:\file.zip".
- *
+ *
* <p>
- * The formatting conventions are different than those of {@link MessageFormat}
+ * The formatting conventions are different from those of {@link MessageFormat}
* which ships with the Java platform. This is justified by the fact that
* SLF4J's implementation is 10 times faster than that of {@link MessageFormat}.
* This local performance difference is both measurable and significant in the
* larger context of the complete logging processing chain.
- *
+ *
* <p>
* See also {@link #format(String, Object)},
* {@link #format(String, Object, Object)} and
* {@link #arrayFormat(String, Object[])} methods for more details.
- *
+ *
* @author Ceki G&uuml;lc&uuml;
* @author Joern Huxhorn
*/
@@ -106,17 +106,17 @@ final public class MessageFormatter {
* parameter.
* <p>
* For example,
- *
+ *
* <pre>
* MessageFormatter.format(&quot;Hi {}.&quot;, &quot;there&quot;);
* </pre>
- *
+ *
* will return the string "Hi there.".
* <p>
- *
+ *
* @param messagePattern
* The message pattern which will be parsed and formatted
- * @param argument
+ * @param arg
* The argument to be substituted in place of the formatting anchor
* @return The formatted message
*/
@@ -125,18 +125,18 @@ final public class MessageFormatter {
}
/**
- *
+ *
* Performs a two argument substitution for the 'messagePattern' passed as
* parameter.
* <p>
* For example,
- *
+ *
* <pre>
* MessageFormatter.format(&quot;Hi {}. My name is {}.&quot;, &quot;Alice&quot;, &quot;Bob&quot;);
* </pre>
- *
+ *
* will return the string "Hi Alice. My name is Bob.".
- *
+ *
* @param messagePattern
* The message pattern which will be parsed and formatted
* @param arg1
@@ -151,36 +151,34 @@ final public class MessageFormatter {
return arrayFormat(messagePattern, new Object[] { arg1, arg2 });
}
- static final Throwable getThrowableCandidate(Object[] argArray) {
- if (argArray == null || argArray.length == 0) {
- return null;
- }
-
- final Object lastEntry = argArray[argArray.length - 1];
- if (lastEntry instanceof Throwable) {
- return (Throwable) lastEntry;
+ final public static FormattingTuple arrayFormat(final String messagePattern, final Object[] argArray) {
+ Throwable throwableCandidate = MessageFormatter.getThrowableCandidate(argArray);
+ Object[] args = argArray;
+ if (throwableCandidate != null) {
+ args = MessageFormatter.trimmedCopy(argArray);
}
- return null;
+ return arrayFormat(messagePattern, args, throwableCandidate);
}
/**
- * Same principle as the {@link #format(String, Object)} and
- * {@link #format(String, Object, Object)} methods except that any number of
- * arguments can be passed in an array.
+ * Assumes that argArray only contains arguments with no throwable as last element.
*
* @param messagePattern
- * The message pattern which will be parsed and formatted
* @param argArray
- * An array of arguments to be substituted in place of formatting
- * anchors
- * @return The formatted message
*/
- final public static FormattingTuple arrayFormat(final String messagePattern, final Object[] argArray) {
+ final public static String basicArrayFormat(final String messagePattern, final Object[] argArray) {
+ FormattingTuple ft = arrayFormat(messagePattern, argArray, null);
+ return ft.getMessage();
+ }
- Throwable throwableCandidate = getThrowableCandidate(argArray);
+ public static String basicArrayFormat(NormalizedParameters np) {
+ return basicArrayFormat(np.getMessage(), np.getArguments());
+ }
+
+ final public static FormattingTuple arrayFormat(final String messagePattern, final Object[] argArray, Throwable throwable) {
if (messagePattern == null) {
- return new FormattingTuple(null, argArray, throwableCandidate);
+ return new FormattingTuple(null, argArray, throwable);
}
if (argArray == null) {
@@ -200,42 +198,38 @@ final public class MessageFormatter {
if (j == -1) {
// no more variables
if (i == 0) { // this is a simple string
- return new FormattingTuple(messagePattern, argArray, throwableCandidate);
+ return new FormattingTuple(messagePattern, argArray, throwable);
} else { // add the tail string which contains no variables and return
// the result.
- sbuf.append(messagePattern.substring(i, messagePattern.length()));
- return new FormattingTuple(sbuf.toString(), argArray, throwableCandidate);
+ sbuf.append(messagePattern, i, messagePattern.length());
+ return new FormattingTuple(sbuf.toString(), argArray, throwable);
}
} else {
if (isEscapedDelimeter(messagePattern, j)) {
if (!isDoubleEscaped(messagePattern, j)) {
L--; // DELIM_START was escaped, thus should not be incremented
- sbuf.append(messagePattern.substring(i, j - 1));
+ sbuf.append(messagePattern, i, j - 1);
sbuf.append(DELIM_START);
i = j + 1;
} else {
// The escape character preceding the delimiter start is
// itself escaped: "abc x:\\{}"
// we have to consume one backward slash
- sbuf.append(messagePattern.substring(i, j - 1));
- deeplyAppendParameter(sbuf, argArray[L], new HashMap<Object[], Object>());
+ sbuf.append(messagePattern, i, j - 1);
+ deeplyAppendParameter(sbuf, argArray[L], new HashMap<>());
i = j + 2;
}
} else {
// normal case
- sbuf.append(messagePattern.substring(i, j));
- deeplyAppendParameter(sbuf, argArray[L], new HashMap<Object[], Object>());
+ sbuf.append(messagePattern, i, j);
+ deeplyAppendParameter(sbuf, argArray[L], new HashMap<>());
i = j + 2;
}
}
}
// append the characters following the last {} pair.
- sbuf.append(messagePattern.substring(i, messagePattern.length()));
- if (L < argArray.length - 1) {
- return new FormattingTuple(sbuf.toString(), argArray, throwableCandidate);
- } else {
- return new FormattingTuple(sbuf.toString(), argArray, null);
- }
+ sbuf.append(messagePattern, i, messagePattern.length());
+ return new FormattingTuple(sbuf.toString(), argArray, throwable);
}
final static boolean isEscapedDelimeter(String messagePattern, int delimeterStartIndex) {
@@ -297,8 +291,7 @@ final public class MessageFormatter {
String oAsString = o.toString();
sbuf.append(oAsString);
} catch (Throwable t) {
- System.err.println("SLF4J: Failed toString() invocation on an object of type [" + o.getClass().getName() + "]");
- t.printStackTrace();
+ Reporter.error("Failed toString() invocation on an object of type [" + o.getClass().getName() + "]", t);
sbuf.append("[FAILED toString()]");
}
@@ -409,4 +402,29 @@ final public class MessageFormatter {
}
sbuf.append(']');
}
+
+ /**
+ * Helper method to determine if an {@link Object} array contains a {@link Throwable} as last element
+ *
+ * @param argArray
+ * The arguments off which we want to know if it contains a {@link Throwable} as last element
+ * @return if the last {@link Object} in argArray is a {@link Throwable} this method will return it,
+ * otherwise it returns null
+ */
+ public static Throwable getThrowableCandidate(final Object[] argArray) {
+ return NormalizedParameters.getThrowableCandidate(argArray);
+ }
+
+ /**
+ * Helper method to get all but the last element of an array
+ *
+ * @param argArray
+ * The arguments from which we want to remove the last element
+ *
+ * @return a copy of the array without the last element
+ */
+ public static Object[] trimmedCopy(final Object[] argArray) {
+ return NormalizedParameters.trimmedCopy(argArray);
+ }
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NOPLogger.java b/slf4j-api/src/main/java/org/slf4j/helpers/NOPLogger.java
index 5e0909d8..4b9a3597 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/NOPLogger.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NOPLogger.java
@@ -25,14 +25,14 @@
package org.slf4j.helpers;
import org.slf4j.Logger;
-import org.slf4j.helpers.MarkerIgnoringBase;
+import org.slf4j.Marker;
/**
* A direct NOP (no operation) implementation of {@link Logger}.
*
* @author Ceki G&uuml;lc&uuml;
*/
-public class NOPLogger extends MarkerIgnoringBase {
+public class NOPLogger extends NamedLoggerBase implements Logger {
private static final long serialVersionUID = -517220405410904473L;
@@ -42,8 +42,9 @@ public class NOPLogger extends MarkerIgnoringBase {
public static final NOPLogger NOP_LOGGER = new NOPLogger();
/**
- * There is no point in creating multiple instances of NOPLOgger,
- * except by derived classes, hence the protected access for the constructor.
+ * There is no point in creating multiple instances of NOPLogger.
+ *
+ * The present constructor should be "private" but we are leaving it as "protected" for compatibility.
*/
protected NOPLogger() {
}
@@ -51,6 +52,7 @@ public class NOPLogger extends MarkerIgnoringBase {
/**
* Always returns the string value "NOP".
*/
+ @Override
public String getName() {
return "NOP";
}
@@ -59,31 +61,37 @@ public class NOPLogger extends MarkerIgnoringBase {
* Always returns false.
* @return always false
*/
+ @Override
final public boolean isTraceEnabled() {
return false;
}
/** A NOP implementation. */
+ @Override
final public void trace(String msg) {
// NOP
}
/** A NOP implementation. */
+ @Override
final public void trace(String format, Object arg) {
// NOP
}
/** A NOP implementation. */
+ @Override
public final void trace(String format, Object arg1, Object arg2) {
// NOP
}
/** A NOP implementation. */
+ @Override
public final void trace(String format, Object... argArray) {
// NOP
}
/** A NOP implementation. */
+ @Override
final public void trace(String msg, Throwable t) {
// NOP
}
@@ -107,12 +115,12 @@ public class NOPLogger extends MarkerIgnoringBase {
}
/** A NOP implementation. */
- public final void debug(String format, Object arg1, Object arg2) {
+ final public void debug(String format, Object arg1, Object arg2) {
// NOP
}
/** A NOP implementation. */
- public final void debug(String format, Object... argArray) {
+ final public void debug(String format, Object... argArray) {
// NOP
}
@@ -146,7 +154,7 @@ public class NOPLogger extends MarkerIgnoringBase {
}
/** A NOP implementation. */
- public final void info(String format, Object... argArray) {
+ final public void info(String format, Object... argArray) {
// NOP
}
@@ -179,7 +187,7 @@ public class NOPLogger extends MarkerIgnoringBase {
}
/** A NOP implementation. */
- public final void warn(String format, Object... argArray) {
+ final public void warn(String format, Object... argArray) {
// NOP
}
@@ -209,7 +217,7 @@ public class NOPLogger extends MarkerIgnoringBase {
}
/** A NOP implementation. */
- public final void error(String format, Object... argArray) {
+ final public void error(String format, Object... argArray) {
// NOP
}
@@ -217,4 +225,203 @@ public class NOPLogger extends MarkerIgnoringBase {
final public void error(String msg, Throwable t) {
// NOP
}
+
+ // ============================================================
+ // Added NOP methods since MarkerIgnoringBase is now deprecated
+ // ============================================================
+ /**
+ * Always returns false.
+ * @return always false
+ */
+ final public boolean isTraceEnabled(Marker marker) {
+ // NOP
+ return false;
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void trace(Marker marker, String msg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void trace(Marker marker, String format, Object arg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void trace(Marker marker, String format, Object arg1, Object arg2) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void trace(Marker marker, String format, Object... argArray) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void trace(Marker marker, String msg, Throwable t) {
+ // NOP
+ }
+
+ /**
+ * Always returns false.
+ * @return always false
+ */
+ final public boolean isDebugEnabled(Marker marker) {
+ return false;
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void debug(Marker marker, String msg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void debug(Marker marker, String format, Object arg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void debug(Marker marker, String format, Object arg1, Object arg2) {
+ // NOP
+ }
+
+ @Override
+ final public void debug(Marker marker, String format, Object... arguments) {
+ // NOP
+ }
+
+ @Override
+ final public void debug(Marker marker, String msg, Throwable t) {
+ // NOP
+ }
+
+ /**
+ * Always returns false.
+ * @return always false
+ */
+ @Override
+ public boolean isInfoEnabled(Marker marker) {
+ return false;
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void info(Marker marker, String msg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void info(Marker marker, String format, Object arg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void info(Marker marker, String format, Object arg1, Object arg2) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void info(Marker marker, String format, Object... arguments) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void info(Marker marker, String msg, Throwable t) {
+ // NOP
+ }
+
+ /**
+ * Always returns false.
+ * @return always false
+ */
+ @Override
+ final public boolean isWarnEnabled(Marker marker) {
+ return false;
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void warn(Marker marker, String msg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void warn(Marker marker, String format, Object arg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void warn(Marker marker, String format, Object arg1, Object arg2) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void warn(Marker marker, String format, Object... arguments) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void warn(Marker marker, String msg, Throwable t) {
+ // NOP
+ }
+
+ /**
+ * Always returns false.
+ * @return always false
+ */
+ @Override
+ final public boolean isErrorEnabled(Marker marker) {
+ return false;
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void error(Marker marker, String msg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void error(Marker marker, String format, Object arg) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void error(Marker marker, String format, Object arg1, Object arg2) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void error(Marker marker, String format, Object... arguments) {
+ // NOP
+ }
+
+ /** A NOP implementation. */
+ @Override
+ final public void error(Marker marker, String msg, Throwable t) {
+ // NOP
+ }
+ // ===================================================================
+ // End of added NOP methods since MarkerIgnoringBase is now deprecated
+ // ===================================================================
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NOPLoggerFactory.java b/slf4j-api/src/main/java/org/slf4j/helpers/NOPLoggerFactory.java
index b8a55dc9..7cc83914 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/NOPLoggerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NOPLoggerFactory.java
@@ -26,10 +26,9 @@ package org.slf4j.helpers;
import org.slf4j.ILoggerFactory;
import org.slf4j.Logger;
-import org.slf4j.helpers.NOPLogger;
/**
- * NOPLoggerFactory is an trivial implementation of {@link
+ * NOPLoggerFactory is a trivial implementation of {@link
* ILoggerFactory} which always returns the unique instance of
* NOPLogger.
*
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NOPMDCAdapter.java b/slf4j-api/src/main/java/org/slf4j/helpers/NOPMDCAdapter.java
index 22f3ea45..7c34fca0 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/NOPMDCAdapter.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NOPMDCAdapter.java
@@ -24,6 +24,7 @@
*/
package org.slf4j.helpers;
+import java.util.Deque;
import java.util.Map;
import org.slf4j.spi.MDCAdapter;
@@ -60,4 +61,21 @@ public class NOPMDCAdapter implements MDCAdapter {
// NOP
}
+ @Override
+ public void pushByKey(String key, String value) {
+ }
+
+ @Override
+ public String popByKey(String key) {
+ return null;
+ }
+
+ @Override
+ public Deque<String> getCopyOfDequeByKey(String key) {
+ return null;
+ }
+
+ public void clearDequeByKey(String key) {
+ }
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NOP_FallbackServiceProvider.java b/slf4j-api/src/main/java/org/slf4j/helpers/NOP_FallbackServiceProvider.java
new file mode 100755
index 00000000..87d287a6
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NOP_FallbackServiceProvider.java
@@ -0,0 +1,47 @@
+package org.slf4j.helpers;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class NOP_FallbackServiceProvider implements SLF4JServiceProvider {
+
+ /**
+ * Declare the version of the SLF4J API this implementation is compiled
+ * against. The value of this field is modified with each major release.
+ */
+ // to avoid constant folding by the compiler, this field must *not* be final
+ public static String REQUESTED_API_VERSION = "2.0.99"; // !final
+
+ private final ILoggerFactory loggerFactory = new NOPLoggerFactory();
+ private final IMarkerFactory markerFactory = new BasicMarkerFactory();
+ private final MDCAdapter mdcAdapter = new NOPMDCAdapter();
+
+
+ @Override
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+
+ @Override
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return REQUESTED_API_VERSION;
+ }
+
+ @Override
+ public void initialize() {
+ // already initialized
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NamedLoggerBase.java b/slf4j-api/src/main/java/org/slf4j/helpers/NamedLoggerBase.java
index 184c3942..97b31837 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/NamedLoggerBase.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NamedLoggerBase.java
@@ -32,9 +32,10 @@ import org.slf4j.LoggerFactory;
/**
* Serves as base class for named logger implementation. More significantly, this
- * class establishes deserialization behavior. See @see #readResolve.
+ * class establishes deserialization behavior.
*
* @author Ceki Gulcu
+ * @see #readResolve
* @since 1.5.3
*/
abstract class NamedLoggerBase implements Logger, Serializable {
@@ -54,7 +55,7 @@ abstract class NamedLoggerBase implements Logger, Serializable {
*
* <p>
* This approach will work well if the desired ILoggerFactory is the one
- * references by LoggerFactory. However, if the user manages its logger hierarchy
+ * referenced by LoggerFactory. However, if the user manages its logger hierarchy
* through a different (non-static) mechanism, e.g. dependency injection, then
* this approach would be mostly counterproductive.
*
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/NormalizedParameters.java b/slf4j-api/src/main/java/org/slf4j/helpers/NormalizedParameters.java
new file mode 100644
index 00000000..ec278f46
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/NormalizedParameters.java
@@ -0,0 +1,116 @@
+package org.slf4j.helpers;
+
+import org.slf4j.event.LoggingEvent;
+
+/**
+ * Holds normalized call parameters.
+ *
+ * Includes utility methods such as {@link #normalize(String, Object[], Throwable)} to help the normalization of parameters.
+ *
+ * @author ceki
+ * @since 2.0
+ */
+public class NormalizedParameters {
+
+ final String message;
+ final Object[] arguments;
+ final Throwable throwable;
+
+ public NormalizedParameters(String message, Object[] arguments, Throwable throwable) {
+ this.message = message;
+ this.arguments = arguments;
+ this.throwable = throwable;
+ }
+
+ public NormalizedParameters(String message, Object[] arguments) {
+ this(message, arguments, null);
+ }
+
+ public String getMessage() {
+ return message;
+ }
+
+ public Object[] getArguments() {
+ return arguments;
+ }
+
+ public Throwable getThrowable() {
+ return throwable;
+ }
+
+ /**
+ * Helper method to determine if an {@link Object} array contains a
+ * {@link Throwable} as last element
+ *
+ * @param argArray The arguments off which we want to know if it contains a
+ * {@link Throwable} as last element
+ * @return if the last {@link Object} in argArray is a {@link Throwable} this
+ * method will return it, otherwise it returns null
+ */
+ public static Throwable getThrowableCandidate(final Object[] argArray) {
+ if (argArray == null || argArray.length == 0) {
+ return null;
+ }
+
+ final Object lastEntry = argArray[argArray.length - 1];
+ if (lastEntry instanceof Throwable) {
+ return (Throwable) lastEntry;
+ }
+
+ return null;
+ }
+
+ /**
+ * Helper method to get all but the last element of an array
+ *
+ * @param argArray The arguments from which we want to remove the last element
+ *
+ * @return a copy of the array without the last element
+ */
+ public static Object[] trimmedCopy(final Object[] argArray) {
+ if (argArray == null || argArray.length == 0) {
+ throw new IllegalStateException("non-sensical empty or null argument array");
+ }
+
+ final int trimmedLen = argArray.length - 1;
+
+ Object[] trimmed = new Object[trimmedLen];
+
+ if (trimmedLen > 0) {
+ System.arraycopy(argArray, 0, trimmed, 0, trimmedLen);
+ }
+
+ return trimmed;
+ }
+
+ /**
+ * This method serves to normalize logging call invocation parameters.
+ *
+ * More specifically, if a throwable argument is not supplied directly, it
+ * attempts to extract it from the argument array.
+ */
+ public static NormalizedParameters normalize(String msg, Object[] arguments, Throwable t) {
+
+ if (t != null) {
+ return new NormalizedParameters(msg, arguments, t);
+ }
+
+ if (arguments == null || arguments.length == 0) {
+ return new NormalizedParameters(msg, arguments, t);
+ }
+
+ Throwable throwableCandidate = NormalizedParameters.getThrowableCandidate(arguments);
+ if (throwableCandidate != null) {
+ Object[] trimmedArguments = MessageFormatter.trimmedCopy(arguments);
+ return new NormalizedParameters(msg, trimmedArguments, throwableCandidate);
+ } else {
+ return new NormalizedParameters(msg, arguments);
+ }
+
+ }
+
+ public static NormalizedParameters normalize(LoggingEvent event) {
+ return normalize(event.getMessage(), event.getArgumentArray(), event.getThrowable());
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/Reporter.java b/slf4j-api/src/main/java/org/slf4j/helpers/Reporter.java
new file mode 100644
index 00000000..2f269969
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/Reporter.java
@@ -0,0 +1,181 @@
+package org.slf4j.helpers;
+
+import java.io.PrintStream;
+
+/**
+ * An internally used class for reporting internal messages generated by SLF4J itself during initialization.
+ *
+ * <p>
+ * Internal reporting is performed by calling the {@link #info(String)}, {@link #warn(String)} (String)}
+ * {@link #error(String)} (String)} and {@link #error(String, Throwable)} methods.
+ * </p>
+ * <p>See {@link #SLF4J_INTERNAL_VERBOSITY_KEY} and {@link #SLF4J_INTERNAL_REPORT_STREAM_KEY} for
+ * configuration options.</p>
+ * <p>
+ * <p>
+ * Note that this system is independent of the logging back-end in use.
+ *
+ * @since 2.0.10
+ */
+public class Reporter {
+
+ /**
+ * this class is used internally by Reporter
+ */
+ private enum Level {
+ INFO(1), WARN(2), ERROR(3);
+
+ int levelInt;
+
+ private Level(int levelInt) {
+ this.levelInt = levelInt;
+ }
+
+ private int getLevelInt() {
+ return levelInt;
+ }
+ }
+
+ private enum TargetChoice {
+ Stderr, Stdout;
+ }
+
+ static final String SLF4J_INFO_PREFIX = "SLF4J(I): ";
+ static final String SLF4J_WARN_PREFIX = "SLF4J(W): ";
+ static final String SLF4J_ERROR_PREFIX = "SLF4J(E): ";
+
+
+ /**
+ * This system property controls the target for internal reports output by SLF4J.
+ * Recognized values for this key are "System.out", "stdout", "sysout", "System.err",
+ * "stderr" and "syserr".
+ *
+ * <p>By default, output is directed to "stderr".</p>
+ */
+ public static final String SLF4J_INTERNAL_REPORT_STREAM_KEY = "slf4j.internal.report.stream";
+ static private final String[] SYSOUT_KEYS = {"System.out", "stdout", "sysout"};
+
+ /**
+ * This system property controls the internal level of chattiness
+ * of SLF4J. Recognized settings are "INFO", "WARN" and "ERROR". The default value is "INFO".
+ */
+ public static final String SLF4J_INTERNAL_VERBOSITY_KEY = "slf4j.internal.verbosity";
+
+
+ static private final TargetChoice TARGET_CHOICE = initTargetChoice();
+
+ static private final Level INTERNAL_VERBOSITY = initVerbosity();
+
+ static private TargetChoice initTargetChoice() {
+ String reportStreamStr = System.getProperty(SLF4J_INTERNAL_REPORT_STREAM_KEY);
+
+ if(reportStreamStr == null || reportStreamStr.isEmpty()) {
+ return TargetChoice.Stderr;
+ }
+
+ for(String s : SYSOUT_KEYS) {
+ if(s.equalsIgnoreCase(reportStreamStr))
+ return TargetChoice.Stdout;
+ }
+ return TargetChoice.Stderr;
+ }
+
+
+ static private Level initVerbosity() {
+ String verbosityStr = System.getProperty(SLF4J_INTERNAL_VERBOSITY_KEY);
+
+ if(verbosityStr == null || verbosityStr.isEmpty()) {
+ return Level.INFO;
+ }
+
+ if(verbosityStr.equalsIgnoreCase("ERROR")) {
+ return Level.ERROR;
+ }
+
+
+ if(verbosityStr.equalsIgnoreCase("WARN")) {
+ return Level.WARN;
+ }
+
+ return Level.INFO;
+ }
+
+ static boolean isEnabledFor(Level level) {
+ return (level.levelInt >= INTERNAL_VERBOSITY.levelInt);
+ }
+
+ static private PrintStream getTarget() {
+ switch(TARGET_CHOICE) {
+ case Stdout:
+ return System.out;
+ case Stderr:
+ default:
+ return System.err;
+ }
+ }
+
+ /**
+ * Report an internal message of level INFO. Message text is prefixed with the string "SLF4J(I)", with
+ * (I) standing as a shorthand for INFO.
+ *
+ * <p>Messages of level INFO are be enabled when the {@link #SLF4J_INTERNAL_VERBOSITY_KEY} system property is
+ * set to "INFO" and disabled when set to "WARN" or "ERROR". By default, {@link #SLF4J_INTERNAL_VERBOSITY_KEY} is
+ * set to "INFO".</p>
+ *
+ * @param msg the message text
+ */
+ public static void info(String msg) {
+ if(isEnabledFor(Level.INFO)) {
+ getTarget().println(SLF4J_INFO_PREFIX + msg);
+ }
+ }
+
+
+ /**
+ * Report an internal message of level "WARN". Message text is prefixed with the string "SLF4J(W)", with
+ * (W) standing as a shorthand for WARN.
+ *
+ * <p>Messages of level WARN are be enabled when the {@link #SLF4J_INTERNAL_VERBOSITY_KEY} system property is
+ * set to "INFO" or "WARN" and disabled when set to "ERROR". By default, {@link #SLF4J_INTERNAL_VERBOSITY_KEY} is
+ * set to "INFO".</p>
+ *
+ * @param msg the message text
+ */
+ static final public void warn(String msg) {
+ if(isEnabledFor(Level.WARN)) {
+ getTarget().println(SLF4J_WARN_PREFIX + msg);
+ }
+ }
+
+
+ /**
+ * Report an internal message of level "ERROR accompanied by a {@link Throwable}.
+ * Message text is prefixed with the string "SLF4J(E)", with (E) standing as a shorthand for ERROR.
+ *
+ * <p>Messages of level ERROR are always enabled.
+ *
+ * @param msg the message text
+ * @param t a Throwable
+ */
+ static final public void error(String msg, Throwable t) {
+ // error cannot be disabled
+ getTarget().println(SLF4J_ERROR_PREFIX + msg);
+ getTarget().println(SLF4J_ERROR_PREFIX + "Reported exception:");
+ t.printStackTrace(getTarget());
+ }
+
+
+ /**
+ * Report an internal message of level "ERROR". Message text is prefixed with the string "SLF4J(E)", with
+ * (E) standing as a shorthand for ERROR.
+ *
+ * <p>Messages of level ERROR are always enabled.
+ *
+ * @param msg the message text
+ */
+
+ static final public void error(String msg) {
+ // error cannot be disabled
+ getTarget().println(SLF4J_ERROR_PREFIX + msg);
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLogger.java b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLogger.java
index 1c37977e..b9e160d7 100644
--- a/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLogger.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLogger.java
@@ -24,196 +24,286 @@
*/
package org.slf4j.helpers;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.Queue;
+
import org.slf4j.Logger;
import org.slf4j.Marker;
+import org.slf4j.event.EventRecordingLogger;
+import org.slf4j.event.Level;
+import org.slf4j.event.LoggingEvent;
+import org.slf4j.event.SubstituteLoggingEvent;
+import org.slf4j.spi.LoggingEventBuilder;
/**
* A logger implementation which logs via a delegate logger. By default, the delegate is a
- * {@link NOPLogger}. However, a different delegate can be set at anytime.
- * <p/>
- * See also the <a href="http://www.slf4j.org/codes.html#substituteLogger">relevant
+ * {@link NOPLogger}. However, a different delegate can be set at any time.
+ *
+ * <p>See also the <a href="http://www.slf4j.org/codes.html#substituteLogger">relevant
* error code</a> documentation.
*
* @author Chetan Mehrotra
+ * @author Ceki Gulcu
*/
public class SubstituteLogger implements Logger {
private final String name;
-
private volatile Logger _delegate;
+ private Boolean delegateEventAware;
+ private Method logMethodCache;
+ private EventRecordingLogger eventRecordingLogger;
+ private final Queue<SubstituteLoggingEvent> eventQueue;
+
+ public final boolean createdPostInitialization;
- public SubstituteLogger(String name) {
+ public SubstituteLogger(String name, Queue<SubstituteLoggingEvent> eventQueue, boolean createdPostInitialization) {
this.name = name;
+ this.eventQueue = eventQueue;
+ this.createdPostInitialization = createdPostInitialization;
}
+ @Override
public String getName() {
return name;
}
+
+ @Override
+ public LoggingEventBuilder makeLoggingEventBuilder(Level level) {
+ return delegate().makeLoggingEventBuilder(level);
+ }
+ @Override
+ public LoggingEventBuilder atLevel(Level level) {
+ return delegate().atLevel(level);
+ }
+
+ @Override
+ public boolean isEnabledForLevel(Level level) {
+ return delegate().isEnabledForLevel(level);
+ }
+
+ @Override
public boolean isTraceEnabled() {
return delegate().isTraceEnabled();
}
-
+
+ @Override
public void trace(String msg) {
delegate().trace(msg);
}
-
+
+ @Override
public void trace(String format, Object arg) {
delegate().trace(format, arg);
}
-
+
+ @Override
public void trace(String format, Object arg1, Object arg2) {
delegate().trace(format, arg1, arg2);
}
-
+
+ @Override
public void trace(String format, Object... arguments) {
delegate().trace(format, arguments);
- }
-
+ }
+
+ @Override
public void trace(String msg, Throwable t) {
delegate().trace(msg, t);
}
-
+
+ @Override
public boolean isTraceEnabled(Marker marker) {
return delegate().isTraceEnabled(marker);
}
-
+
+ @Override
public void trace(Marker marker, String msg) {
delegate().trace(marker, msg);
}
-
+
+ @Override
public void trace(Marker marker, String format, Object arg) {
delegate().trace(marker, format, arg);
}
-
+
+ @Override
public void trace(Marker marker, String format, Object arg1, Object arg2) {
delegate().trace(marker, format, arg1, arg2);
}
-
+ @Override
public void trace(Marker marker, String format, Object... arguments) {
delegate().trace(marker, format, arguments);
}
-
+ @Override
public void trace(Marker marker, String msg, Throwable t) {
delegate().trace(marker, msg, t);
}
-
+
+ @Override
+ public LoggingEventBuilder atTrace() {
+ return delegate().atTrace();
+ }
+
+ @Override
public boolean isDebugEnabled() {
return delegate().isDebugEnabled();
}
-
+
+ @Override
public void debug(String msg) {
delegate().debug(msg);
}
-
+
+ @Override
public void debug(String format, Object arg) {
delegate().debug(format, arg);
}
-
+
+ @Override
public void debug(String format, Object arg1, Object arg2) {
delegate().debug(format, arg1, arg2);
}
-
+
+ @Override
public void debug(String format, Object... arguments) {
delegate().debug(format, arguments);
}
-
+
+ @Override
public void debug(String msg, Throwable t) {
delegate().debug(msg, t);
}
-
+
+ @Override
public boolean isDebugEnabled(Marker marker) {
return delegate().isDebugEnabled(marker);
}
-
+
+ @Override
public void debug(Marker marker, String msg) {
delegate().debug(marker, msg);
}
-
+
+ @Override
public void debug(Marker marker, String format, Object arg) {
delegate().debug(marker, format, arg);
}
-
+
+ @Override
public void debug(Marker marker, String format, Object arg1, Object arg2) {
delegate().debug(marker, format, arg1, arg2);
}
-
+
+ @Override
public void debug(Marker marker, String format, Object... arguments) {
delegate().debug(marker, format, arguments);
}
-
+
+ @Override
public void debug(Marker marker, String msg, Throwable t) {
delegate().debug(marker, msg, t);
}
-
+
+ @Override
+ public LoggingEventBuilder atDebug() {
+ return delegate().atDebug();
+ }
+
+ @Override
public boolean isInfoEnabled() {
return delegate().isInfoEnabled();
}
+
+ @Override
public void info(String msg) {
delegate().info(msg);
}
-
+
+ @Override
public void info(String format, Object arg) {
delegate().info(format, arg);
}
-
+
+ @Override
public void info(String format, Object arg1, Object arg2) {
delegate().info(format, arg1, arg2);
}
-
+
+ @Override
public void info(String format, Object... arguments) {
delegate().info(format, arguments);
}
-
+
+ @Override
public void info(String msg, Throwable t) {
delegate().info(msg, t);
}
-
+
+ @Override
public boolean isInfoEnabled(Marker marker) {
return delegate().isInfoEnabled(marker);
}
-
+
+ @Override
public void info(Marker marker, String msg) {
delegate().info(marker, msg);
}
-
+
+ @Override
public void info(Marker marker, String format, Object arg) {
delegate().info(marker, format, arg);
}
-
+
+ @Override
public void info(Marker marker, String format, Object arg1, Object arg2) {
delegate().info(marker, format, arg1, arg2);
}
-
+
+ @Override
public void info(Marker marker, String format, Object... arguments) {
delegate().info(marker, format, arguments);
}
-
+
+ @Override
public void info(Marker marker, String msg, Throwable t) {
delegate().info(marker, msg, t);
}
+
+ @Override
+ public LoggingEventBuilder atInfo() {
+ return delegate().atInfo();
+ }
+
+ @Override
public boolean isWarnEnabled() {
return delegate().isWarnEnabled();
}
-
+
+ @Override
public void warn(String msg) {
delegate().warn(msg);
}
-
+
+ @Override
public void warn(String format, Object arg) {
delegate().warn(format, arg);
}
-
+
+ @Override
public void warn(String format, Object arg1, Object arg2) {
delegate().warn(format, arg1, arg2);
}
-
+
+ @Override
public void warn(String format, Object... arguments) {
delegate().warn(format, arguments);
}
-
+
+ @Override
public void warn(String msg, Throwable t) {
delegate().warn(msg, t);
}
@@ -221,76 +311,105 @@ public class SubstituteLogger implements Logger {
public boolean isWarnEnabled(Marker marker) {
return delegate().isWarnEnabled(marker);
}
-
+
+ @Override
public void warn(Marker marker, String msg) {
delegate().warn(marker, msg);
}
-
+
+ @Override
public void warn(Marker marker, String format, Object arg) {
delegate().warn(marker, format, arg);
}
-
+
+ @Override
public void warn(Marker marker, String format, Object arg1, Object arg2) {
delegate().warn(marker, format, arg1, arg2);
}
-
+
+ @Override
public void warn(Marker marker, String format, Object... arguments) {
delegate().warn(marker, format, arguments);
}
-
+
+ @Override
public void warn(Marker marker, String msg, Throwable t) {
delegate().warn(marker, msg, t);
}
+
+ @Override
+ public LoggingEventBuilder atWarn() {
+ return delegate().atWarn();
+ }
+
+
+ @Override
public boolean isErrorEnabled() {
return delegate().isErrorEnabled();
}
-
+
+ @Override
public void error(String msg) {
delegate().error(msg);
}
-
+
+ @Override
public void error(String format, Object arg) {
delegate().error(format, arg);
}
-
+
+ @Override
public void error(String format, Object arg1, Object arg2) {
delegate().error(format, arg1, arg2);
}
-
+
+ @Override
public void error(String format, Object... arguments) {
delegate().error(format, arguments);
}
-
+
+ @Override
public void error(String msg, Throwable t) {
delegate().error(msg, t);
}
-
+
+ @Override
public boolean isErrorEnabled(Marker marker) {
return delegate().isErrorEnabled(marker);
}
-
+
+ @Override
public void error(Marker marker, String msg) {
delegate().error(marker, msg);
}
-
+
+ @Override
public void error(Marker marker, String format, Object arg) {
delegate().error(marker, format, arg);
}
-
+
+ @Override
public void error(Marker marker, String format, Object arg1, Object arg2) {
delegate().error(marker, format, arg1, arg2);
}
-
+
+ @Override
public void error(Marker marker, String format, Object... arguments) {
delegate().error(marker, format, arguments);
}
-
+
+ @Override
public void error(Marker marker, String msg, Throwable t) {
delegate().error(marker, msg, t);
}
@Override
+ public LoggingEventBuilder atError() {
+ return delegate().atError();
+ }
+
+ @Override
public boolean equals(Object o) {
if (this == o)
return true;
@@ -314,8 +433,22 @@ public class SubstituteLogger implements Logger {
* Return the delegate logger instance if set. Otherwise, return a {@link NOPLogger}
* instance.
*/
- Logger delegate() {
- return _delegate != null ? _delegate : NOPLogger.NOP_LOGGER;
+ public Logger delegate() {
+ if (_delegate != null) {
+ return _delegate;
+ }
+ if (createdPostInitialization) {
+ return NOPLogger.NOP_LOGGER;
+ } else {
+ return getEventRecordingLogger();
+ }
+ }
+
+ private Logger getEventRecordingLogger() {
+ if (eventRecordingLogger == null) {
+ eventRecordingLogger = new EventRecordingLogger(this, eventQueue);
+ }
+ return eventRecordingLogger;
}
/**
@@ -325,4 +458,36 @@ public class SubstituteLogger implements Logger {
public void setDelegate(Logger delegate) {
this._delegate = delegate;
}
+
+ public boolean isDelegateEventAware() {
+ if (delegateEventAware != null)
+ return delegateEventAware;
+
+ try {
+ logMethodCache = _delegate.getClass().getMethod("log", LoggingEvent.class);
+ delegateEventAware = Boolean.TRUE;
+ } catch (NoSuchMethodException e) {
+ delegateEventAware = Boolean.FALSE;
+ }
+ return delegateEventAware;
+ }
+
+ public void log(LoggingEvent event) {
+ if (isDelegateEventAware()) {
+ try {
+ logMethodCache.invoke(_delegate, event);
+ } catch (IllegalAccessException e) {
+ } catch (IllegalArgumentException e) {
+ } catch (InvocationTargetException e) {
+ }
+ }
+ }
+
+ public boolean isDelegateNull() {
+ return _delegate == null;
+ }
+
+ public boolean isDelegateNOP() {
+ return _delegate instanceof NOPLogger;
+ }
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLoggerFactory.java b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLoggerFactory.java
index 0697e39f..8a9d5dd3 100755
--- a/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLoggerFactory.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteLoggerFactory.java
@@ -24,13 +24,15 @@
*/
package org.slf4j.helpers;
-import org.slf4j.ILoggerFactory;
-import org.slf4j.Logger;
-
import java.util.ArrayList;
import java.util.List;
+import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
+import java.util.concurrent.LinkedBlockingQueue;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.Logger;
+import org.slf4j.event.SubstituteLoggingEvent;
/**
* SubstituteLoggerFactory manages instances of {@link SubstituteLogger}.
@@ -40,28 +42,39 @@ import java.util.concurrent.ConcurrentMap;
*/
public class SubstituteLoggerFactory implements ILoggerFactory {
- final ConcurrentMap<String, SubstituteLogger> loggers = new ConcurrentHashMap<String, SubstituteLogger>();
+ volatile boolean postInitialization = false;
- public Logger getLogger(String name) {
+ final Map<String, SubstituteLogger> loggers = new ConcurrentHashMap<>();
+
+ final LinkedBlockingQueue<SubstituteLoggingEvent> eventQueue = new LinkedBlockingQueue<>();
+
+ synchronized public Logger getLogger(String name) {
SubstituteLogger logger = loggers.get(name);
if (logger == null) {
- logger = new SubstituteLogger(name);
- SubstituteLogger oldLogger = loggers.putIfAbsent(name, logger);
- if (oldLogger != null)
- logger = oldLogger;
+ logger = new SubstituteLogger(name, eventQueue, postInitialization);
+ loggers.put(name, logger);
}
return logger;
}
public List<String> getLoggerNames() {
- return new ArrayList<String>(loggers.keySet());
+ return new ArrayList<>(loggers.keySet());
}
public List<SubstituteLogger> getLoggers() {
- return new ArrayList<SubstituteLogger>(loggers.values());
+ return new ArrayList<>(loggers.values());
+ }
+
+ public LinkedBlockingQueue<SubstituteLoggingEvent> getEventQueue() {
+ return eventQueue;
+ }
+
+ public void postInitialization() {
+ postInitialization = true;
}
public void clear() {
loggers.clear();
+ eventQueue.clear();
}
}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteServiceProvider.java b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteServiceProvider.java
new file mode 100755
index 00000000..2c59530d
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/SubstituteServiceProvider.java
@@ -0,0 +1,41 @@
+package org.slf4j.helpers;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class SubstituteServiceProvider implements SLF4JServiceProvider {
+ private final SubstituteLoggerFactory loggerFactory = new SubstituteLoggerFactory();
+ private final IMarkerFactory markerFactory = new BasicMarkerFactory();
+ private final MDCAdapter mdcAdapter = new BasicMDCAdapter();
+
+ @Override
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+ public SubstituteLoggerFactory getSubstituteLoggerFactory() {
+ return loggerFactory;
+ }
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+ @Override
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public void initialize() {
+
+ }
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/ThreadLocalMapOfStacks.java b/slf4j-api/src/main/java/org/slf4j/helpers/ThreadLocalMapOfStacks.java
new file mode 100644
index 00000000..89ddee0e
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/ThreadLocalMapOfStacks.java
@@ -0,0 +1,89 @@
+package org.slf4j.helpers;
+
+import java.util.ArrayDeque;
+import java.util.Deque;
+import java.util.HashMap;
+import java.util.Map;
+
+
+/**
+ * A simple implementation of ThreadLocal backed Map containing values of type
+ * Deque<String>.
+ *
+ * @author Ceki Guuml;c&uuml;
+ * @since 2.0.0
+ */
+public class ThreadLocalMapOfStacks {
+
+ // BEWARE: Keys or values placed in a ThreadLocal should not be of a type/class
+ // not included in the JDK. See also https://jira.qos.ch/browse/LOGBACK-450
+
+ final ThreadLocal<Map<String, Deque<String>>> tlMapOfStacks = new ThreadLocal<>();
+
+ public void pushByKey(String key, String value) {
+ if (key == null)
+ return;
+
+ Map<String, Deque<String>> map = tlMapOfStacks.get();
+
+ if (map == null) {
+ map = new HashMap<>();
+ tlMapOfStacks.set(map);
+ }
+
+ Deque<String> deque = map.get(key);
+ if (deque == null) {
+ deque = new ArrayDeque<>();
+ }
+ deque.push(value);
+ map.put(key, deque);
+ }
+
+ public String popByKey(String key) {
+ if (key == null)
+ return null;
+
+ Map<String, Deque<String>> map = tlMapOfStacks.get();
+ if (map == null)
+ return null;
+ Deque<String> deque = map.get(key);
+ if (deque == null)
+ return null;
+ return deque.pop();
+ }
+
+ public Deque<String> getCopyOfDequeByKey(String key) {
+ if (key == null)
+ return null;
+
+ Map<String, Deque<String>> map = tlMapOfStacks.get();
+ if (map == null)
+ return null;
+ Deque<String> deque = map.get(key);
+ if (deque == null)
+ return null;
+
+ return new ArrayDeque<String>(deque);
+ }
+
+ /**
+ * Clear the deque(stack) referenced by 'key'.
+ *
+ * @param key identifies the stack
+ *
+ * @since 2.0.0
+ */
+ public void clearDequeByKey(String key) {
+ if (key == null)
+ return;
+
+ Map<String, Deque<String>> map = tlMapOfStacks.get();
+ if (map == null)
+ return;
+ Deque<String> deque = map.get(key);
+ if (deque == null)
+ return;
+ deque.clear();
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/helpers/Util.java b/slf4j-api/src/main/java/org/slf4j/helpers/Util.java
index 91a09837..98858315 100755
--- a/slf4j-api/src/main/java/org/slf4j/helpers/Util.java
+++ b/slf4j-api/src/main/java/org/slf4j/helpers/Util.java
@@ -35,6 +35,27 @@ public final class Util {
private Util() {
}
+ public static String safeGetSystemProperty(String key) {
+ if (key == null)
+ throw new IllegalArgumentException("null input");
+
+ String result = null;
+ try {
+ result = System.getProperty(key);
+ } catch (java.lang.SecurityException sm) {
+ ; // ignore
+ }
+ return result;
+ }
+
+ public static boolean safeGetBooleanSystemProperty(String key) {
+ String value = safeGetSystemProperty(key);
+ if (value == null)
+ return false;
+ else
+ return value.equalsIgnoreCase("true");
+ }
+
/**
* In order to call {@link SecurityManager#getClassContext()}, which is a
* protected method, we add this wrapper which allows the method to be visible
@@ -46,7 +67,28 @@ public final class Util {
}
}
- private static final ClassContextSecurityManager SECURITY_MANAGER = new ClassContextSecurityManager();
+ private static ClassContextSecurityManager SECURITY_MANAGER;
+ private static boolean SECURITY_MANAGER_CREATION_ALREADY_ATTEMPTED = false;
+
+ private static ClassContextSecurityManager getSecurityManager() {
+ if (SECURITY_MANAGER != null)
+ return SECURITY_MANAGER;
+ else if (SECURITY_MANAGER_CREATION_ALREADY_ATTEMPTED)
+ return null;
+ else {
+ SECURITY_MANAGER = safeCreateSecurityManager();
+ SECURITY_MANAGER_CREATION_ALREADY_ATTEMPTED = true;
+ return SECURITY_MANAGER;
+ }
+ }
+
+ private static ClassContextSecurityManager safeCreateSecurityManager() {
+ try {
+ return new ClassContextSecurityManager();
+ } catch (java.lang.SecurityException sm) {
+ return null;
+ }
+ }
/**
* Returns the name of the class which called the invoking method.
@@ -54,7 +96,10 @@ public final class Util {
* @return the name of the class which called the invoking method.
*/
public static Class<?> getCallingClass() {
- Class<?>[] trace = SECURITY_MANAGER.getClassContext();
+ ClassContextSecurityManager securityManager = getSecurityManager();
+ if (securityManager == null)
+ return null;
+ Class<?>[] trace = securityManager.getClassContext();
String thisClassName = Util.class.getName();
// Advance until Util is found
@@ -72,13 +117,28 @@ public final class Util {
return trace[i + 2];
}
+ /**
+ * See {@link Reporter#error(String, Throwable)} class for alternative.
+ *
+ * @deprecated replaced by the {@link Reporter#error(String, Throwable)} method.
+ * @param msg message to print
+ * @param t throwable to print
+ */
static final public void report(String msg, Throwable t) {
System.err.println(msg);
System.err.println("Reported exception:");
t.printStackTrace();
}
+ /**
+ * See {@link Reporter} class for alternatives.
+ *
+ * @deprecated replaced by one of {@link Reporter#info(String)},
+ * {@link Reporter#warn(String)} or {@link Reporter#error(String)} methods.
+ * @param msg message to print
+ */
static final public void report(String msg) {
System.err.println("SLF4J: " + msg);
}
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-api/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index e6747e53..00000000
--- a/slf4j-api/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * This class is meant to provide a dummy StaticLoggerBinder to the slf4j-api module.
- * Real implementations are found in each SLF4J binding project, e.g. slf4j-nop,
- * slf4j-log4j12 etc.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder {
-
- /**
- * The unique instance of this class.
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled against.
- * The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
- private StaticLoggerBinder() {
- throw new UnsupportedOperationException("This code should have never made it into slf4j-api.jar");
- }
-
- public ILoggerFactory getLoggerFactory() {
- throw new UnsupportedOperationException("This code should never make it into slf4j-api.jar");
- }
-
- public String getLoggerFactoryClassStr() {
- throw new UnsupportedOperationException("This code should never make it into slf4j-api.jar");
- }
-}
diff --git a/slf4j-api/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-api/src/main/java/org/slf4j/impl/StaticMDCBinder.java
deleted file mode 100644
index 4fd65f40..00000000
--- a/slf4j-api/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.spi.MDCAdapter;
-
-/**
- * This class is only a stub. Real implementations are found in
- * each SLF4J binding project, e.g. slf4j-nop, slf4j-log4j12 etc.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link StaticMDCBinder}.
- */
- public MDCAdapter getMDCA() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-
- public String getMDCAdapterClassStr() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-}
diff --git a/slf4j-api/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-api/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 0823b827..00000000
--- a/slf4j-api/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * This class is meant to provide a *dummy* StaticMarkerBinder to the slf4j-api module.
- * Real implementations are found in each SLF4J binding project, e.g. slf4j-nop,
- * slf4j-simple, slf4j-log4j12 etc.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- private StaticMarkerBinder() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- throw new UnsupportedOperationException("This code should never make it into the jar");
- }
-
-}
diff --git a/slf4j-api/src/main/java/org/slf4j/impl/package.html b/slf4j-api/src/main/java/org/slf4j/impl/package.html
deleted file mode 100644
index 6b84bada..00000000
--- a/slf4j-api/src/main/java/org/slf4j/impl/package.html
+++ /dev/null
@@ -1,17 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
-
-
-<html>
- <head>
- <title></title>
- </head>
-
-
- <body>
-
- <p>Implementations of core logging interfaces defined in the {@link
- org.slf4j} package.</p>
-
- <hr/>
- </body>
-</html>
diff --git a/slf4j-api/src/main/java/org/slf4j/package.html b/slf4j-api/src/main/java/org/slf4j/package.html
index e50b3ee2..323bac21 100644
--- a/slf4j-api/src/main/java/org/slf4j/package.html
+++ b/slf4j-api/src/main/java/org/slf4j/package.html
@@ -11,6 +11,6 @@
<p>Core logging interfaces.</p>
- <hr/>
+ <hr>
</body>
</html>
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/CallerBoundaryAware.java b/slf4j-api/src/main/java/org/slf4j/spi/CallerBoundaryAware.java
new file mode 100644
index 00000000..e1a2de95
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/CallerBoundaryAware.java
@@ -0,0 +1,25 @@
+package org.slf4j.spi;
+
+import org.slf4j.event.LoggingEvent;
+
+/**
+ * Additional interface to {@link LoggingEventBuilder} and
+ * {@link org.slf4j.event.LoggingEvent LoggingEvent}.
+ *
+ * Implementations of {@link LoggingEventBuilder} and {@link LoggingEvent} may optionally
+ * implement {@link CallerBoundaryAware} in order to support caller info extraction.
+ *
+ * This interface is intended for use by logging backends or logging bridges.
+ *
+ * @author Ceki Gulcu
+ *
+ */
+public interface CallerBoundaryAware {
+
+ /**
+ * Add a fqcn (fully qualified class name) to this event, presumed to be the caller boundary.
+ *
+ * @param fqcn
+ */
+ void setCallerBoundary(String fqcn);
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/DefaultLoggingEventBuilder.java b/slf4j-api/src/main/java/org/slf4j/spi/DefaultLoggingEventBuilder.java
new file mode 100755
index 00000000..66652b07
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/DefaultLoggingEventBuilder.java
@@ -0,0 +1,246 @@
+/**
+ * Copyright (c) 2004-2022 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.spi;
+
+import java.util.function.Supplier;
+
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+import org.slf4j.event.DefaultLoggingEvent;
+import org.slf4j.event.KeyValuePair;
+import org.slf4j.event.Level;
+import org.slf4j.event.LoggingEvent;
+
+/**
+ * Default implementation of {@link LoggingEventBuilder}
+ */
+public class DefaultLoggingEventBuilder implements LoggingEventBuilder, CallerBoundaryAware {
+
+
+ // The caller boundary when the log() methods are invoked, is this class itself.
+
+ static String DLEB_FQCN = DefaultLoggingEventBuilder.class.getName();
+
+ protected DefaultLoggingEvent loggingEvent;
+ protected Logger logger;
+
+ public DefaultLoggingEventBuilder(Logger logger, Level level) {
+ this.logger = logger;
+ loggingEvent = new DefaultLoggingEvent(level, logger);
+ }
+
+ /**
+ * Add a marker to the current logging event being built.
+ *
+ * It is possible to add multiple markers to the same logging event.
+ *
+ * @param marker the marker to add
+ */
+ @Override
+ public LoggingEventBuilder addMarker(Marker marker) {
+ loggingEvent.addMarker(marker);
+ return this;
+ }
+
+ @Override
+ public LoggingEventBuilder setCause(Throwable t) {
+ loggingEvent.setThrowable(t);
+ return this;
+ }
+
+ @Override
+ public LoggingEventBuilder addArgument(Object p) {
+ loggingEvent.addArgument(p);
+ return this;
+ }
+
+ @Override
+ public LoggingEventBuilder addArgument(Supplier<?> objectSupplier) {
+ loggingEvent.addArgument(objectSupplier.get());
+ return this;
+ }
+
+ @Override
+ public void setCallerBoundary(String fqcn) {
+ loggingEvent.setCallerBoundary(fqcn);
+ }
+
+ @Override
+ public void log() {
+ log(loggingEvent);
+ }
+
+ @Override
+ public LoggingEventBuilder setMessage(String message) {
+ loggingEvent.setMessage(message);
+ return this;
+ }
+ @Override
+ public LoggingEventBuilder setMessage(Supplier<String> messageSupplier) {
+ loggingEvent.setMessage(messageSupplier.get());
+ return this;
+ }
+
+ @Override
+ public void log(String message) {
+ loggingEvent.setMessage(message);
+ log(loggingEvent);
+ }
+
+ @Override
+ public void log(String message, Object arg) {
+ loggingEvent.setMessage(message);
+ loggingEvent.addArgument(arg);
+ log(loggingEvent);
+ }
+
+ @Override
+ public void log(String message, Object arg0, Object arg1) {
+ loggingEvent.setMessage(message);
+ loggingEvent.addArgument(arg0);
+ loggingEvent.addArgument(arg1);
+ log(loggingEvent);
+ }
+
+ @Override
+ public void log(String message, Object... args) {
+ loggingEvent.setMessage(message);
+ loggingEvent.addArguments(args);
+
+ log(loggingEvent);
+ }
+
+ @Override
+ public void log(Supplier<String> messageSupplier) {
+ if (messageSupplier == null) {
+ log((String) null);
+ } else {
+ log(messageSupplier.get());
+ }
+ }
+
+ protected void log(LoggingEvent aLoggingEvent) {
+ setCallerBoundary(DLEB_FQCN);
+ if (logger instanceof LoggingEventAware) {
+ ((LoggingEventAware) logger).log(aLoggingEvent);
+ } else {
+ logViaPublicSLF4JLoggerAPI(aLoggingEvent);
+ }
+ }
+
+ private void logViaPublicSLF4JLoggerAPI(LoggingEvent aLoggingEvent) {
+ Object[] argArray = aLoggingEvent.getArgumentArray();
+ int argLen = argArray == null ? 0 : argArray.length;
+
+ Throwable t = aLoggingEvent.getThrowable();
+ int tLen = t == null ? 0 : 1;
+
+ String msg = aLoggingEvent.getMessage();
+
+ Object[] combinedArguments = new Object[argLen + tLen];
+
+ if (argArray != null) {
+ System.arraycopy(argArray, 0, combinedArguments, 0, argLen);
+ }
+ if (t != null) {
+ combinedArguments[argLen] = t;
+ }
+
+ msg = mergeMarkersAndKeyValuePairs(aLoggingEvent, msg);
+
+ switch (aLoggingEvent.getLevel()) {
+ case TRACE:
+ logger.trace(msg, combinedArguments);
+ break;
+ case DEBUG:
+ logger.debug(msg, combinedArguments);
+ break;
+ case INFO:
+ logger.info(msg, combinedArguments);
+ break;
+ case WARN:
+ logger.warn(msg, combinedArguments);
+ break;
+ case ERROR:
+ logger.error(msg, combinedArguments);
+ break;
+ }
+
+ }
+
+ /**
+ * Prepend markers and key-value pairs to the message.
+ *
+ * @param aLoggingEvent
+ * @param msg
+ * @return
+ */
+ private String mergeMarkersAndKeyValuePairs(LoggingEvent aLoggingEvent, String msg) {
+
+ StringBuilder sb = null;
+
+ if (aLoggingEvent.getMarkers() != null) {
+ sb = new StringBuilder();
+ for (Marker marker : aLoggingEvent.getMarkers()) {
+ sb.append(marker);
+ sb.append(' ');
+ }
+ }
+
+ if (aLoggingEvent.getKeyValuePairs() != null) {
+ if (sb == null) {
+ sb = new StringBuilder();
+ }
+ for (KeyValuePair kvp : aLoggingEvent.getKeyValuePairs()) {
+ sb.append(kvp.key);
+ sb.append('=');
+ sb.append(kvp.value);
+ sb.append(' ');
+ }
+ }
+
+ if (sb != null) {
+ sb.append(msg);
+ return sb.toString();
+ } else {
+ return msg;
+ }
+ }
+
+
+
+ @Override
+ public LoggingEventBuilder addKeyValue(String key, Object value) {
+ loggingEvent.addKeyValue(key, value);
+ return this;
+ }
+
+ @Override
+ public LoggingEventBuilder addKeyValue(String key, Supplier<Object> value) {
+ loggingEvent.addKeyValue(key, value.get());
+ return this;
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/LocationAwareLogger.java b/slf4j-api/src/main/java/org/slf4j/spi/LocationAwareLogger.java
index 8e0a2070..d0d1a31b 100644
--- a/slf4j-api/src/main/java/org/slf4j/spi/LocationAwareLogger.java
+++ b/slf4j-api/src/main/java/org/slf4j/spi/LocationAwareLogger.java
@@ -34,11 +34,13 @@ import org.slf4j.Marker;
* which need to provide hints so that the underlying logging system can extract
* the correct location information (method name, line number).
*
- * @author Ceki Gulcu
+ * @author Ceki G&uuml;lc&uuml;
* @since 1.3
*/
public interface LocationAwareLogger extends Logger {
+ // these constants should be in EventConstants. However, in order to preserve binary backward compatibility
+ // we keep these constants here. {@link EventConstants} redefines these constants using the values below.
final public int TRACE_INT = 00;
final public int DEBUG_INT = 10;
final public int INFO_INT = 20;
@@ -49,9 +51,12 @@ public interface LocationAwareLogger extends Logger {
* Printing method with support for location information.
*
* @param marker The marker to be used for this event, may be null.
+ *
* @param fqcn The fully qualified class name of the <b>logger instance</b>,
* typically the logger class, logger bridge or a logger wrapper.
+ *
* @param level One of the level integers defined in this interface
+ *
* @param message The message for the log event
* @param t Throwable associated with the log event, may be null.
*/
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/LoggerFactoryBinder.java b/slf4j-api/src/main/java/org/slf4j/spi/LoggerFactoryBinder.java
index c0c2ca05..169691f3 100644
--- a/slf4j-api/src/main/java/org/slf4j/spi/LoggerFactoryBinder.java
+++ b/slf4j-api/src/main/java/org/slf4j/spi/LoggerFactoryBinder.java
@@ -31,6 +31,7 @@ import org.slf4j.ILoggerFactory;
* class bind with the appropriate {@link ILoggerFactory} instance.
*
* @author Ceki G&uuml;lc&uuml;
+ * @deprecated
*/
public interface LoggerFactoryBinder {
@@ -47,9 +48,9 @@ public interface LoggerFactoryBinder {
* The String form of the {@link ILoggerFactory} object that this
* <code>LoggerFactoryBinder</code> instance is <em>intended</em> to return.
*
- * <p>This method allows the developer to intterogate this binder's intention
+ * <p>This method allows the developer to interrogate this binder's intention
* which may be different from the {@link ILoggerFactory} instance it is able to
- * yield in practice. The discrepency should only occur in case of errors.
+ * yield in practice. The discrepancy should only occur in case of errors.
*
* @return the class name of the intended {@link ILoggerFactory} instance
*/
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventAware.java b/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventAware.java
new file mode 100644
index 00000000..b833e40c
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventAware.java
@@ -0,0 +1,23 @@
+package org.slf4j.spi;
+
+import org.slf4j.event.LoggingEvent;
+
+/**
+ * A logger capable of logging from org.slf4j.event.LoggingEvent implements this interface.
+ *
+ * <p>Please note that when the {@link #log(LoggingEvent)} method assumes that
+ * the event was filtered beforehand and no further filtering needs to occur by the method itself.
+ * <p>
+ *
+ * <p>Implementations of this interface <b>may</b> apply further filtering but they are not
+ * required to do so. In other words, {@link #log(LoggingEvent)} method is free to assume that
+ * the event was filtered beforehand and no further filtering needs to occur in the method itself.</p>
+ *
+ * See also https://jira.qos.ch/browse/SLF4J-575
+ *
+ * @author Ceki Gulcu
+ * @since 2.0.0
+ */
+public interface LoggingEventAware {
+ void log(LoggingEvent event);
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventBuilder.java b/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventBuilder.java
new file mode 100755
index 00000000..55e24cfb
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/LoggingEventBuilder.java
@@ -0,0 +1,169 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.spi;
+
+import java.util.function.Supplier;
+
+import org.slf4j.Marker;
+
+import org.slf4j.helpers.CheckReturnValue;
+
+/**
+ * This is the main interface in slf4j's fluent API for creating
+ * {@link org.slf4j.event.LoggingEvent logging events}.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 2.0.0
+ */
+public interface LoggingEventBuilder {
+
+ /**
+ * Set the cause for the logging event being built.
+ * @param cause a throwable
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder setCause(Throwable cause);
+
+ /**
+ * A {@link Marker marker} to the event being built.
+ *
+ * @param marker a Marker instance to add.
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder addMarker(Marker marker);
+
+ /**
+ * Add an argument to the event being built.
+ *
+ * @param p an Object to add.
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder addArgument(Object p);
+
+ /**
+ * Add an argument supplier to the event being built.
+ *
+ * @param objectSupplier an Object supplier to add.
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder addArgument(Supplier<?> objectSupplier);
+
+
+ /**
+ * Add a {@link org.slf4j.event.KeyValuePair key value pair} to the event being built.
+ *
+ * @param key the key of the key value pair.
+ * @param value the value of the key value pair.
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder addKeyValue(String key, Object value);
+
+ /**
+ * Add a {@link org.slf4j.event.KeyValuePair key value pair} to the event being built.
+ *
+ * @param key the key of the key value pair.
+ * @param valueSupplier a supplier of a value for the key value pair.
+ * @return a LoggingEventBuilder, usually <b>this</b>.
+ */
+ @CheckReturnValue
+ LoggingEventBuilder addKeyValue(String key, Supplier<Object> valueSupplier);
+
+ /**
+ * Sets the message of the logging event.
+ *
+ * @since 2.0.0-beta0
+ */
+ @CheckReturnValue
+ LoggingEventBuilder setMessage(String message);
+
+ /**
+ * Sets the message of the event via a message supplier.
+ *
+ * @param messageSupplier supplies a String to be used as the message for the event
+ * @since 2.0.0-beta0
+ */
+ @CheckReturnValue
+ LoggingEventBuilder setMessage(Supplier<String> messageSupplier);
+
+ /**
+ * After the logging event is built, performs actual logging. This method must be called
+ * for logging to occur.
+ *
+ * If the call to {@link #log()} is omitted, a {@link org.slf4j.event.LoggingEvent LoggingEvent}
+ * will be built but no logging will occur.
+ *
+ * @since 2.0.0-beta0
+ */
+ void log();
+
+ /**
+ * Equivalent to calling {@link #setMessage(String)} followed by {@link #log()};
+ *
+ * @param message the message to log
+ */
+ void log(String message);
+
+ /**
+ * Equivalent to calling {@link #setMessage(String)} followed by {@link #addArgument(Object)}}
+ * and then {@link #log()}
+ *
+ * @param message the message to log
+ * @param arg an argument to be used with the message to log
+ */
+ void log(String message, Object arg);
+
+ /**
+ * Equivalent to calling {@link #setMessage(String)} followed by two calls to
+ * {@link #addArgument(Object)} and then {@link #log()}
+ *
+ * @param message the message to log
+ * @param arg0 first argument to be used with the message to log
+ * @param arg1 second argument to be used with the message to log
+ */
+ void log(String message, Object arg0, Object arg1);
+
+
+ /**
+ * Equivalent to calling {@link #setMessage(String)} followed by zero or more calls to
+ * {@link #addArgument(Object)} (depending on the size of args array) and then {@link #log()}
+ *
+ * @param message the message to log
+ * @param args a list (actually an array) of arguments to be used with the message to log
+ */
+ void log(String message, Object... args);
+
+ /**
+ * Equivalent to calling {@link #setMessage(Supplier)} followed by {@link #log()}
+ *
+ * @param messageSupplier a Supplier returning a message of type String
+ */
+ void log(Supplier<String> messageSupplier);
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/MDCAdapter.java b/slf4j-api/src/main/java/org/slf4j/spi/MDCAdapter.java
index 2e637cbe..924849d1 100644
--- a/slf4j-api/src/main/java/org/slf4j/spi/MDCAdapter.java
+++ b/slf4j-api/src/main/java/org/slf4j/spi/MDCAdapter.java
@@ -24,6 +24,7 @@
*/
package org.slf4j.spi;
+import java.util.Deque;
import java.util.Map;
/**
@@ -38,7 +39,7 @@ public interface MDCAdapter {
/**
* Put a context value (the <code>val</code> parameter) as identified with
* the <code>key</code> parameter into the current thread's context map.
- * The <code>key</code> parameter cannot be null. The code>val</code> parameter
+ * The <code>key</code> parameter cannot be null. The <code>val</code> parameter
* can be null only if the underlying implementation supports it.
*
* <p>If the current thread does not have a context map it is created as a side
@@ -55,7 +56,7 @@ public interface MDCAdapter {
public String get(String key);
/**
- * Remove the the context identified by the <code>key</code> parameter.
+ * Remove the context identified by the <code>key</code> parameter.
* The <code>key</code> parameter cannot be null.
*
* <p>
@@ -83,9 +84,50 @@ public interface MDCAdapter {
* map and then copying the map passed as parameter. The context map
* parameter must only contain keys and values of type String.
*
+ * Implementations must support null valued map passed as parameter.
+ *
* @param contextMap must contain only keys and values of type String
*
* @since 1.5.1
*/
public void setContextMap(Map<String, String> contextMap);
+
+ /**
+ * Push a value into the deque(stack) referenced by 'key'.
+ *
+ * @param key identifies the appropriate stack
+ * @param value the value to push into the stack
+ * @since 2.0.0
+ */
+ public void pushByKey(String key, String value);
+
+ /**
+ * Pop the stack referenced by 'key' and return the value possibly null.
+ *
+ * @param key identifies the deque(stack)
+ * @return the value just popped. May be null/
+ * @since 2.0.0
+ */
+ public String popByKey(String key);
+
+ /**
+ * Returns a copy of the deque(stack) referenced by 'key'. May be null.
+ *
+ * @param key identifies the stack
+ * @return copy of stack referenced by 'key'. May be null.
+ *
+ * @since 2.0.0
+ */
+ public Deque<String> getCopyOfDequeByKey(String key);
+
+
+ /**
+ * Clear the deque(stack) referenced by 'key'.
+ *
+ * @param key identifies the stack
+ *
+ * @since 2.0.0
+ */
+ public void clearDequeByKey(String key);
+
}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/MarkerFactoryBinder.java b/slf4j-api/src/main/java/org/slf4j/spi/MarkerFactoryBinder.java
index a71140c9..0502ffad 100644
--- a/slf4j-api/src/main/java/org/slf4j/spi/MarkerFactoryBinder.java
+++ b/slf4j-api/src/main/java/org/slf4j/spi/MarkerFactoryBinder.java
@@ -31,6 +31,7 @@ import org.slf4j.IMarkerFactory;
* class bind with the appropriate {@link IMarkerFactory} instance.
*
* @author Ceki G&uuml;lc&uuml;
+ * @deprecated
*/
public interface MarkerFactoryBinder {
@@ -47,9 +48,9 @@ public interface MarkerFactoryBinder {
* The String form of the {@link IMarkerFactory} object that this
* <code>MarkerFactoryBinder</code> instance is <em>intended</em> to return.
*
- * <p>This method allows the developer to intterogate this binder's intention
+ * <p>This method allows the developer to interrogate this binder's intention
* which may be different from the {@link IMarkerFactory} instance it is able to
- * return. Such a discrepency should only occur in case of errors.
+ * return. Such a discrepancy should only occur in case of errors.
*
* @return the class name of the intended {@link IMarkerFactory} instance
*/
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/NOPLoggingEventBuilder.java b/slf4j-api/src/main/java/org/slf4j/spi/NOPLoggingEventBuilder.java
new file mode 100755
index 00000000..e356b47f
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/NOPLoggingEventBuilder.java
@@ -0,0 +1,100 @@
+package org.slf4j.spi;
+
+import java.util.function.Supplier;
+
+import org.slf4j.Marker;
+import org.slf4j.event.Level;
+
+/**
+ * <p>A no-operation implementation of {@link LoggingEventBuilder}.</p>
+ *
+ * <p>As the name indicates, the method in this class do nothing, except when a return value is expected
+ * in which case a singleton, i.e. the unique instance of this class is returned.
+ * </p
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 2.0.0
+ *
+ */
+public class NOPLoggingEventBuilder implements LoggingEventBuilder {
+
+ static final NOPLoggingEventBuilder SINGLETON = new NOPLoggingEventBuilder();
+
+ private NOPLoggingEventBuilder() {
+ }
+
+ /**
+ * <p>Returns the singleton instance of this class.
+ * Used by {@link org.slf4j.Logger#makeLoggingEventBuilder(Level) makeLoggingEventBuilder(Level)}.</p>
+ *
+ * @return the singleton instance of this class
+ */
+ public static LoggingEventBuilder singleton() {
+ return SINGLETON;
+ }
+
+ @Override
+ public LoggingEventBuilder addMarker(Marker marker) {
+ return singleton();
+ }
+
+ @Override
+ public LoggingEventBuilder addArgument(Object p) {
+ return singleton();
+ }
+
+ @Override
+ public LoggingEventBuilder addArgument(Supplier<?> objectSupplier) {
+ return singleton();
+ }
+
+ @Override
+ public LoggingEventBuilder addKeyValue(String key, Object value) {
+ return singleton();
+ }
+
+ @Override
+ public LoggingEventBuilder addKeyValue(String key, Supplier<Object> value) {
+ return singleton();
+ }
+
+ @Override
+ public LoggingEventBuilder setCause(Throwable cause) {
+ return singleton();
+ }
+
+ @Override
+ public void log() {
+ }
+
+ @Override
+ public LoggingEventBuilder setMessage(String message) {
+ return this;
+ }
+ @Override
+ public LoggingEventBuilder setMessage(Supplier<String> messageSupplier) {
+ return this;
+ }
+
+ @Override
+ public void log(String message) {
+ }
+
+ @Override
+ public void log(Supplier<String> messageSupplier) {
+ }
+
+ @Override
+ public void log(String message, Object arg) {
+ }
+
+ @Override
+ public void log(String message, Object arg0, Object arg1) {
+ }
+
+ @Override
+ public void log(String message, Object... args) {
+
+ }
+
+}
diff --git a/slf4j-api/src/main/java/org/slf4j/spi/SLF4JServiceProvider.java b/slf4j-api/src/main/java/org/slf4j/spi/SLF4JServiceProvider.java
new file mode 100755
index 00000000..83e08741
--- /dev/null
+++ b/slf4j-api/src/main/java/org/slf4j/spi/SLF4JServiceProvider.java
@@ -0,0 +1,60 @@
+package org.slf4j.spi;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+
+/**
+ * This interface based on {@link java.util.ServiceLoader} paradigm.
+ *
+ * <p>It replaces the old static-binding mechanism used in SLF4J versions 1.0.x to 1.7.x.
+ *
+ * @author Ceki G&uml;lc&uml;
+ * @since 1.8
+ */
+public interface SLF4JServiceProvider {
+
+ /**
+ * Return the instance of {@link ILoggerFactory} that
+ * {@link org.slf4j.LoggerFactory} class should bind to.
+ *
+ * @return instance of {@link ILoggerFactory}
+ */
+ public ILoggerFactory getLoggerFactory();
+
+ /**
+ * Return the instance of {@link IMarkerFactory} that
+ * {@link org.slf4j.MarkerFactory} class should bind to.
+ *
+ * @return instance of {@link IMarkerFactory}
+ */
+ public IMarkerFactory getMarkerFactory();
+
+ /**
+ * Return the instance of {@link MDCAdapter} that
+ * {@link MDC} should bind to.
+ *
+ * @return instance of {@link MDCAdapter}
+ */
+ public MDCAdapter getMDCAdapter();
+
+ /**
+ * Return the maximum API version for SLF4J that the logging
+ * implementation supports.
+ *
+ * <p>For example: {@code "2.0.1"}.
+ *
+ * @return the string API version.
+ */
+ public String getRequestedApiVersion();
+
+ /**
+ * Initialize the logging back-end.
+ *
+ * <p><b>WARNING:</b> This method is intended to be called once by
+ * {@link LoggerFactory} class and from nowhere else.
+ *
+ */
+ public void initialize();
+}
diff --git a/slf4j-api/src/main/java9/module-info.java b/slf4j-api/src/main/java9/module-info.java
new file mode 100755
index 00000000..96f08f29
--- /dev/null
+++ b/slf4j-api/src/main/java9/module-info.java
@@ -0,0 +1,8 @@
+module org.slf4j {
+ exports org.slf4j;
+ exports org.slf4j.spi;
+ exports org.slf4j.event;
+ exports org.slf4j.helpers;
+ uses org.slf4j.spi.SLF4JServiceProvider;
+requires java.base;
+}
diff --git a/slf4j-api/src/main/resources/META-INF/MANIFEST.MF b/slf4j-api/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 2940ef8f..00000000
--- a/slf4j-api/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,8 +0,0 @@
-Implementation-Title: slf4j-api
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.api
-Bundle-Name: slf4j-api
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j.impl;version=${slf4j.api.minimum.compatible.version}
diff --git a/slf4j-api/src/test/java/org/slf4j/LoggerAccessingThread.java b/slf4j-api/src/test/java/org/slf4j/LoggerAccessingThread.java
new file mode 100755
index 00000000..30ab5705
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/LoggerAccessingThread.java
@@ -0,0 +1,62 @@
+/**
+ * Copyright (c) 2004-2016 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j;
+
+import java.util.List;
+import java.util.concurrent.CyclicBarrier;
+import java.util.concurrent.atomic.AtomicLong;
+
+public class LoggerAccessingThread extends Thread {
+ private static final int LOOP_LEN = 32;
+
+ final CyclicBarrier barrier;
+ final int count;
+ final AtomicLong eventCount;
+ List<Logger> loggerList;
+
+ public LoggerAccessingThread(final CyclicBarrier barrier, List<Logger> loggerList, final int count, final AtomicLong eventCount) {
+ this.barrier = barrier;
+ this.loggerList = loggerList;
+ this.count = count;
+ this.eventCount = eventCount;
+ }
+
+ public void run() {
+ try {
+ barrier.await();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+
+ String loggerNamePrefix = this.getClass().getName();
+ for (int i = 0; i < LOOP_LEN; i++) {
+ Logger logger = LoggerFactory.getLogger(loggerNamePrefix + "-" + count + "-" + i);
+ loggerList.add(logger);
+ Thread.yield();
+ logger.info("in run method");
+ eventCount.getAndIncrement();
+ }
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/LoggerFactoryTest.java b/slf4j-api/src/test/java/org/slf4j/LoggerFactoryTest.java
new file mode 100644
index 00000000..ed618171
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/LoggerFactoryTest.java
@@ -0,0 +1,91 @@
+package org.slf4j;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+import java.io.ByteArrayOutputStream;
+import java.io.PrintStream;
+
+import static org.hamcrest.CoreMatchers.is;
+import static org.junit.Assert.*;
+
+public class LoggerFactoryTest {
+ private PrintStream rawSyserr;
+ private ByteArrayOutputStream mockedSyserr;
+
+ final ClassLoader classLoaderOfLoggerFactory = LoggerFactory.class.getClassLoader();
+
+ @Before
+ public void setUp() {
+ rawSyserr = System.err;
+ mockedSyserr = new ByteArrayOutputStream();
+ System.setErr(new PrintStream(mockedSyserr));
+ }
+
+ @After
+ public void cleanUp() {
+ System.clearProperty(LoggerFactory.PROVIDER_PROPERTY_KEY);
+ System.setErr(rawSyserr);
+ }
+
+ @Test
+ public void testExplicitlySpecified() {
+ System.setProperty(LoggerFactory.PROVIDER_PROPERTY_KEY, "org.slf4j.LoggerFactoryTest$TestingProvider");
+ SLF4JServiceProvider provider = LoggerFactory.loadExplicitlySpecified(classLoaderOfLoggerFactory);
+ assertTrue("provider should be instance of TestingProvider class", provider instanceof TestingProvider);
+ assertTrue(mockedSyserr.toString().contains(" Attempting to load provider \"org.slf4j.LoggerFactoryTest$TestingProvider\" specified via \"slf4j.provider\" system property"));
+ System.out.println(mockedSyserr.toString());
+
+
+ }
+
+ @Test
+ public void testExplicitlySpecifiedNull() {
+ assertNull(LoggerFactory.loadExplicitlySpecified(classLoaderOfLoggerFactory));
+ }
+
+ @Test
+ public void testExplicitlySpecifyMissingServiceProvider() {
+ System.setProperty(LoggerFactory.PROVIDER_PROPERTY_KEY, "com.example.ServiceProvider");
+ SLF4JServiceProvider provider = LoggerFactory.loadExplicitlySpecified(classLoaderOfLoggerFactory);
+ assertNull(provider);
+ assertTrue(mockedSyserr.toString().contains("Failed to instantiate the specified SLF4JServiceProvider (com.example.ServiceProvider)"));
+ }
+
+ @Test
+ public void testExplicitlySpecifyNonServiceProvider() {
+ System.setProperty(LoggerFactory.PROVIDER_PROPERTY_KEY, "java.lang.String");
+ assertNull(LoggerFactory.loadExplicitlySpecified(classLoaderOfLoggerFactory));
+ assertTrue(mockedSyserr.toString().contains("Specified SLF4JServiceProvider (java.lang.String) does not implement SLF4JServiceProvider interface"));
+ }
+
+ public static class TestingProvider implements SLF4JServiceProvider {
+ @Override
+ public ILoggerFactory getLoggerFactory() {
+ return null;
+ }
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return null;
+ }
+
+ @Override
+ public MDCAdapter getMDCAdapter() {
+ return null;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return null;
+ }
+
+ @Override
+ public void initialize() {
+
+ }
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/BasicMarkerTest.java b/slf4j-api/src/test/java/org/slf4j/basicTests/BasicMarkerTest.java
index 50471b59..5ce33471 100644
--- a/slf4j-api/src/test/java/org/slf4j/BasicMarkerTest.java
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/BasicMarkerTest.java
@@ -22,12 +22,15 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.basicTests;
-import java.util.Iterator;
+import static org.junit.Assert.*;
-import junit.framework.TestCase;
+import java.util.Iterator;
+import org.junit.Test;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.Marker;
import org.slf4j.helpers.BasicMarkerFactory;
/**
@@ -36,7 +39,7 @@ import org.slf4j.helpers.BasicMarkerFactory;
* @author Ceki G&uuml;lc&uuml;
* @author Joern Huxhorn
*/
-public class BasicMarkerTest extends TestCase {
+public class BasicMarkerTest {
static final String BLUE_STR = "BLUE";
static final String RED_STR = "RED";
static final String GREEN_STR = "GREEN";
@@ -69,6 +72,7 @@ public class BasicMarkerTest extends TestCase {
multiComp.add(comp);
}
+ @Test
public void testPrimitive() {
assertEquals(BLUE_STR, blue.getName());
assertTrue(blue.contains(blue));
@@ -80,20 +84,24 @@ public class BasicMarkerTest extends TestCase {
assertTrue(blue2.contains(blue));
}
+ @Test
public void testPrimitiveByName() {
assertTrue(blue.contains(BLUE_STR));
}
+ @Test
public void testComposite() {
assertTrue(comp.contains(comp));
assertTrue(comp.contains(blue));
}
+ @Test
public void testCompositeByName() {
assertTrue(comp.contains(COMP_STR));
assertTrue(comp.contains(BLUE_STR));
}
+ @Test
public void testMultiComposite() {
assertTrue(multiComp.contains(comp));
assertTrue(multiComp.contains(blue));
@@ -101,6 +109,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(multiComp.contains(red));
}
+ @Test
public void testMultiCompositeByName() {
assertTrue(multiComp.contains(COMP_STR));
assertTrue(multiComp.contains(BLUE_STR));
@@ -108,6 +117,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(multiComp.contains(RED_STR));
}
+ @Test
public void testMultiAdd() {
Marker parent = factory.getMarker(PARENT_MARKER_STR);
Marker child = factory.getMarker(CHILD_MARKER_STR);
@@ -122,6 +132,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(iterator.hasNext());
}
+ @Test
public void testAddRemove() {
final String NEW_PREFIX = "NEW_";
Marker parent = factory.getMarker(NEW_PREFIX + PARENT_MARKER_STR);
@@ -142,6 +153,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(parent.remove(child));
}
+ @Test
public void testSelfRecursion() {
final String diffPrefix = "NEW_" + diff;
final String PARENT_NAME = diffPrefix + PARENT_MARKER_STR;
@@ -155,6 +167,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(parent.contains(NOT_CONTAINED_MARKER_STR));
}
+ @Test
public void testIndirectRecursion() {
final String diffPrefix = "NEW_" + diff;
final String PARENT_NAME = diffPrefix + PARENT_MARKER_STR;
@@ -175,6 +188,7 @@ public class BasicMarkerTest extends TestCase {
assertFalse(parent.contains(NOT_CONTAINED_MARKER_STR));
}
+ @Test
public void testHomonyms() {
final String diffPrefix = "homonym" + diff;
final String PARENT_NAME = diffPrefix + PARENT_MARKER_STR;
diff --git a/slf4j-api/src/test/java/org/slf4j/Differentiator.java b/slf4j-api/src/test/java/org/slf4j/basicTests/Differentiator.java
index 09b9a35a..fe2a72ee 100644
--- a/slf4j-api/src/test/java/org/slf4j/Differentiator.java
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/Differentiator.java
@@ -23,7 +23,7 @@
*
*/
-package org.slf4j;
+package org.slf4j.basicTests;
import java.util.Random;
diff --git a/slf4j-api/src/test/java/org/slf4j/basicTests/DoubleCheckedInt.java b/slf4j-api/src/test/java/org/slf4j/basicTests/DoubleCheckedInt.java
new file mode 100755
index 00000000..42a39e64
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/DoubleCheckedInt.java
@@ -0,0 +1,141 @@
+package org.slf4j.basicTests;
+
+import java.util.concurrent.BrokenBarrierException;
+import java.util.concurrent.CyclicBarrier;
+
+/**
+ * This class demonstrates that threads accessing the STATE variable always see a consistent value.
+ *
+ * During ongoing initialization the observed value is either ONGOING_INITIALIZATION
+ * or one of {SUCCESS, FAILURE}.
+ *
+ * Post initialization the observed value is always one of {SUCCESS, FAILURE}.
+ *
+ * See also http://jira.qos.ch/browse/SLF4J-167
+ *
+ * @author ceki
+ *
+ */
+public class DoubleCheckedInt {
+
+ final static int THREAD_COUNT = 10 + Runtime.getRuntime().availableProcessors() * 2;
+ final static int UNINITIALIZED_STATE = 0;
+ final static int ONGOING_INITIALIZATION = 1;
+ final static int SUCCESS = 2;
+ final static int FAILURE = 3;
+ final static int NUMBER_OF_STATES = FAILURE + 1;
+
+ private static int STATE = UNINITIALIZED_STATE;
+
+ public static int getState() {
+ if (STATE == 0) {
+ synchronized (DoubleCheckedInt.class) {
+ if (STATE == UNINITIALIZED_STATE) {
+ STATE = ONGOING_INITIALIZATION;
+ long r = System.nanoTime();
+ try {
+ Thread.sleep(10);
+ } catch (InterruptedException e) {
+ }
+ if (r % 2 == 0) {
+ STATE = SUCCESS;
+ } else {
+ STATE = FAILURE;
+ }
+ }
+ }
+ }
+ return STATE;
+ }
+
+ static public void main(String[] args) throws InterruptedException, BrokenBarrierException {
+ StateAccessingThread[] preInitializationThreads = harness();
+ check(preInitializationThreads, false);
+
+ System.out.println("============");
+ StateAccessingThread[] postInitializationThreads = harness();
+ check(postInitializationThreads, true);
+ }
+
+ private static StateAccessingThread[] harness() throws InterruptedException, BrokenBarrierException {
+ StateAccessingThread[] threads = new StateAccessingThread[THREAD_COUNT];
+ final CyclicBarrier barrier = new CyclicBarrier(THREAD_COUNT + 1);
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i] = new StateAccessingThread(barrier);
+ threads[i].start();
+ }
+
+ barrier.await();
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i].join();
+ }
+ return threads;
+ }
+
+ private static void check(StateAccessingThread[] threads, boolean postInit) {
+
+ int[] stateCount = getStateCount(threads);
+ printStateCount(stateCount);
+
+ if (stateCount[UNINITIALIZED_STATE] != 0) {
+ throw new IllegalStateException("getState() should never return a zero value");
+ }
+
+ if (stateCount[SUCCESS] != 0 && stateCount[FAILURE] != 0) {
+ throw new IllegalStateException("getState() should return consistent values");
+ }
+
+ if (postInit) {
+ if (stateCount[SUCCESS] != THREAD_COUNT && stateCount[FAILURE] != THREAD_COUNT) {
+ throw new IllegalStateException("getState() should return consistent values");
+ }
+ }
+
+ }
+
+ private static void printStateCount(int[] stateCount) {
+ for (int i = 0; i < NUMBER_OF_STATES; i++) {
+ switch (i) {
+ case UNINITIALIZED_STATE:
+ System.out.println("UNINITIALIZED_STATE count: " + stateCount[i]);
+ break;
+ case ONGOING_INITIALIZATION:
+ System.out.println("ONGOING_INITIALIZATION count: " + stateCount[i]);
+ break;
+ case SUCCESS:
+ System.out.println("SUCCESS count: " + stateCount[i]);
+ break;
+ case FAILURE:
+ System.out.println("FAILURE count: " + stateCount[i]);
+ break;
+ }
+ }
+ }
+
+ private static int[] getStateCount(StateAccessingThread[] threads) {
+ int[] valCount = new int[NUMBER_OF_STATES];
+ for (StateAccessingThread thread : threads) {
+ int val = thread.state;
+ valCount[val] = valCount[val] + 1;
+ }
+ return valCount;
+ }
+
+ static class StateAccessingThread extends Thread {
+ public int state = -1;
+ final CyclicBarrier barrier;
+
+ StateAccessingThread(CyclicBarrier barrier) {
+ this.barrier = barrier;
+ }
+
+ public void run() {
+ try {
+ barrier.await();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ state = DoubleCheckedInt.getState();
+ }
+ };
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/basicTests/FluentAPIUsage.java b/slf4j-api/src/test/java/org/slf4j/basicTests/FluentAPIUsage.java
new file mode 100755
index 00000000..cc8434a9
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/FluentAPIUsage.java
@@ -0,0 +1,27 @@
+package org.slf4j.basicTests;
+
+import static org.junit.Assert.assertFalse;
+
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.event.Level;
+
+public class FluentAPIUsage {
+
+ @Test
+ public void smoke() {
+ String name = "smoke";
+ Logger logger = LoggerFactory.getLogger(name);
+ logger.atTrace().addKeyValue("a", "n").setCause(new Throwable()).log("hello");
+ }
+
+
+ @Test
+ public void smokxce() {
+ String name = "smoke";
+ Logger logger = LoggerFactory.getLogger(name);
+ assertFalse(logger.isEnabledForLevel(Level.DEBUG));
+ }
+
+}
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingMultithreadedInitializationTest.java
index 77742309..024a7f82 100644
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingMultithreadedInitializationTest.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2016 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,34 +22,35 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.basicTests;
-import org.slf4j.spi.MDCAdapter;
+import org.junit.After;
+import org.junit.Before;
+import org.slf4j.LoggerFactoryFriend;
+import org.slf4j.testHarness.MultithreadedInitializationTest;
/**
- * This implementation is bound to {@link Log4jMDCAdapter}.
- *
- * @author Ceki G&uuml;lc&uuml;
+ * Checks that when no binding is present, proper clean up is performed by LoggerFactory.
+ *
+ * See SLF4J-469
+ *
+ * @author David Harsha
*/
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
+public class NoBindingMultithreadedInitializationTest extends MultithreadedInitializationTest {
+ final String loggerName = this.getClass().getName();
- private StaticMDCBinder() {
+ @Before
+ public void setup() {
+ LoggerFactoryFriend.reset();
}
- /**
- * Currently this method always returns an instance of
- * {@link StaticMDCBinder}.
- */
- public MDCAdapter getMDCA() {
- return new Log4jMDCAdapter();
+ @After
+ public void tearDown() throws Exception {
+ LoggerFactoryFriend.reset();
}
- public String getMDCAdapterClassStr() {
- return Log4jMDCAdapter.class.getName();
+ @Override
+ protected long getRecordedEventCount() {
+ return eventCount.get();
}
}
diff --git a/slf4j-api/src/test/java/org/slf4j/NoBindingTest.java b/slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingTest.java
index 7a5ec2d8..8e1dd16c 100644
--- a/slf4j-api/src/test/java/org/slf4j/NoBindingTest.java
+++ b/slf4j-api/src/test/java/org/slf4j/basicTests/NoBindingTest.java
@@ -22,30 +22,40 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.basicTests;
+
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
import java.util.Random;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
import org.slf4j.helpers.BasicMarker;
import org.slf4j.helpers.NOPLogger;
-import junit.framework.TestCase;
-
-public class NoBindingTest extends TestCase {
+public class NoBindingTest {
int diff = new Random().nextInt(10000);
+ @Test
public void testLogger() {
Logger logger = LoggerFactory.getLogger(NoBindingTest.class);
logger.debug("hello" + diff);
assertTrue(logger instanceof NOPLogger);
}
+ @Test
public void testMDC() {
MDC.put("k" + diff, "v");
assertNull(MDC.get("k"));
}
+ @Test
public void testMarker() {
Marker m = MarkerFactory.getMarker("a" + diff);
assertTrue(m instanceof BasicMarker);
diff --git a/slf4j-api/src/test/java/org/slf4j/eventTest/EventRecordingLoggerTest.java b/slf4j-api/src/test/java/org/slf4j/eventTest/EventRecordingLoggerTest.java
new file mode 100644
index 00000000..e2ec1c05
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/eventTest/EventRecordingLoggerTest.java
@@ -0,0 +1,531 @@
+package org.slf4j.eventTest;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Marker;
+import org.slf4j.event.EventRecordingLogger;
+import org.slf4j.event.Level;
+import org.slf4j.event.SubstituteLoggingEvent;
+import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.helpers.SubstituteLogger;
+
+import java.util.Queue;
+import java.util.concurrent.LinkedBlockingQueue;
+
+import static org.junit.Assert.*;
+
+public class EventRecordingLoggerTest {
+ private Queue<SubstituteLoggingEvent> queue;
+ private EventRecordingLogger logger;
+ private String message;
+ private Object param1;
+ private Object param2;
+ private Object param3;
+ private Object[] oneParam;
+ private Object[] twoParams;
+ private Object[] threeParams;
+ private Throwable exception;
+ private Marker marker;
+
+ @Before
+ public void setUp() {
+ queue = new LinkedBlockingQueue<>();
+ logger = new EventRecordingLogger(new SubstituteLogger("testLogger", queue, true), queue);
+ message = "Test message with 3 parameters {} {} {} {}";
+ param1 = 1;
+ param2 = 2;
+ param3 = 3;
+ oneParam = new Object[] { param1 };
+ twoParams = new Object[] { param1, param2 };
+ threeParams = new Object[] { param1, param2, param3 };
+ exception = new IllegalStateException("We just need an exception");
+ marker = new BasicMarkerFactory().getMarker("testMarker");
+ }
+
+ @After
+ public void tearDown() {
+ assertTrue(queue.isEmpty());
+ }
+
+ @Test
+ public void singleMessage() {
+ for (Level level : Level.values()) {
+ singleMessageCheck(level);
+ }
+ }
+
+ private void singleMessageCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message);
+ break;
+ case DEBUG:
+ logger.debug(message);
+ break;
+ case INFO:
+ logger.info(message);
+ break;
+ case WARN:
+ logger.warn(message);
+ break;
+ case ERROR:
+ logger.error(message);
+ break;
+ }
+ verifyMessageWithoutMarker(level, null, null);
+ }
+
+ @Test
+ public void oneParameter() {
+ for (Level level : Level.values()) {
+ oneParameterCheck(level);
+ }
+ }
+
+ private void oneParameterCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1);
+ break;
+ case DEBUG:
+ logger.debug(message, param1);
+ break;
+ case INFO:
+ logger.info(message, param1);
+ break;
+ case WARN:
+ logger.warn(message, param1);
+ break;
+ case ERROR:
+ logger.error(message, param1);
+ break;
+ }
+ verifyMessageWithoutMarker(level, oneParam, null);
+ }
+
+ @Test
+ public void messageTwoParameters() {
+ for (Level level : Level.values()) {
+ messageTwoParametersCheck(level);
+ }
+ }
+
+ private void messageTwoParametersCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1, param2);
+ break;
+ case DEBUG:
+ logger.debug(message, param1, param2);
+ break;
+ case INFO:
+ logger.info(message, param1, param2);
+ break;
+ case WARN:
+ logger.warn(message, param1, param2);
+ break;
+ case ERROR:
+ logger.error(message, param1, param2);
+ break;
+ }
+ verifyMessageWithoutMarker(level, twoParams, null);
+ }
+
+ @Test
+ public void traceMessageThreeParameters() {
+ for (Level level : Level.values()) {
+ threeParameterCheck(level);
+ }
+ }
+
+ private void threeParameterCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1, param2, param3);
+ break;
+ case DEBUG:
+ logger.debug(message, param1, param2, param3);
+ break;
+ case INFO:
+ logger.info(message, param1, param2, param3);
+ break;
+ case WARN:
+ logger.warn(message, param1, param2, param3);
+ break;
+ case ERROR:
+ logger.error(message, param1, param2, param3);
+ break;
+ }
+ verifyMessageWithoutMarker(level, threeParams, null);
+ }
+
+ @Test
+ public void testMessageThrowable() {
+ for (Level level : Level.values()) {
+ throwableCheck(level);
+ }
+ }
+
+ private void throwableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, exception);
+ break;
+ case DEBUG:
+ logger.debug(message, exception);
+ break;
+ case INFO:
+ logger.info(message, exception);
+ break;
+ case WARN:
+ logger.warn(message, exception);
+ break;
+ case ERROR:
+ logger.error(message, exception);
+ break;
+ }
+ verifyMessageWithoutMarker(level, null, exception);
+ }
+
+ @Test
+ public void traceMessageOneParameterThrowable() {
+ for (Level level : Level.values()) {
+ oneParamThrowableCheck(level);
+ }
+ }
+
+ private void oneParamThrowableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1, exception);
+ break;
+ case DEBUG:
+ logger.debug(message, param1, exception);
+ break;
+ case INFO:
+ logger.info(message, param1, exception);
+ break;
+ case WARN:
+ logger.warn(message, param1, exception);
+ break;
+ case ERROR:
+ logger.error(message, param1, exception);
+ break;
+ }
+ verifyMessageWithoutMarker(level, oneParam, exception);
+ }
+
+ @Test
+ public void traceMessageTwoParametersThrowable() {
+ for (Level level : Level.values()) {
+ twoParamThrowableCheck(level);
+ }
+ }
+
+ private void twoParamThrowableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1, param2, exception);
+ break;
+ case DEBUG:
+ logger.debug(message, param1, param2, exception);
+ break;
+ case INFO:
+ logger.info(message, param1, param2, exception);
+ break;
+ case WARN:
+ logger.warn(message, param1, param2, exception);
+ break;
+ case ERROR:
+ logger.error(message, param1, param2, exception);
+ break;
+ }
+ verifyMessageWithoutMarker(level, twoParams, exception);
+ }
+
+ @Test
+ public void testMessageThreeParametersThrowable() {
+ for (Level level : Level.values()) {
+ messageWith3ArgsPlusException(level);
+ }
+ }
+
+ private void messageWith3ArgsPlusException(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(message, param1, param2, param3, exception);
+ break;
+ case DEBUG:
+ logger.debug(message, param1, param2, param3, exception);
+ break;
+ case INFO:
+ logger.info(message, param1, param2, param3, exception);
+ break;
+ case WARN:
+ logger.warn(message, param1, param2, param3, exception);
+ break;
+ case ERROR:
+ logger.error(message, param1, param2, param3, exception);
+ break;
+ }
+ verifyMessageWithoutMarker(level, threeParams, exception);
+ }
+
+ @Test
+ public void markerMessage() {
+ for (Level level : Level.values()) {
+ markerMessageCheck(level);
+ }
+ }
+
+ private void markerMessageCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message);
+ break;
+ case DEBUG:
+ logger.debug(marker, message);
+ break;
+ case INFO:
+ logger.info(marker, message);
+ break;
+ case WARN:
+ logger.warn(marker, message);
+ break;
+ case ERROR:
+ logger.error(marker, message);
+ break;
+ }
+ verifyMessage(level, marker, null, null);
+ }
+
+ @Test
+ public void markerMessageOneParameter() {
+ for (Level level : Level.values()) {
+ markerMessageOneParameter(level);
+ }
+ }
+
+ private void markerMessageOneParameter(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1);
+ break;
+ case INFO:
+ logger.info(marker, message, param1);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1);
+ break;
+ }
+ verifyMessage(level, marker, oneParam, null);
+ }
+
+ @Test
+ public void traceMarkerMessageTwoParameters() {
+ for (Level level : Level.values()) {
+ markerMessageTwoParameters(level);
+ }
+ }
+
+ private void markerMessageTwoParameters(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1, param2);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1, param2);
+ break;
+ case INFO:
+ logger.info(marker, message, param1, param2);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1, param2);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1, param2);
+ break;
+ }
+ verifyMessage(level, marker, twoParams, null);
+ }
+
+ @Test
+ public void traceMarkerMessageThreeParameters() {
+ for (Level level : Level.values()) {
+ markerMessageThreeParameters(level);
+ }
+ }
+
+ private void markerMessageThreeParameters(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1, param2, param3);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1, param2, param3);
+ break;
+ case INFO:
+ logger.info(marker, message, param1, param2, param3);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1, param2, param3);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1, param2, param3);
+ break;
+ }
+ verifyMessage(level, marker, threeParams, null);
+ }
+
+ @Test
+ public void markerMessageThrowable() {
+ for (Level level : Level.values()) {
+ markerMessageThrowable(level);
+ }
+ }
+
+ private void markerMessageThrowable(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, exception);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, exception);
+ break;
+ case INFO:
+ logger.info(marker, message, exception);
+ break;
+ case WARN:
+ logger.warn(marker, message, exception);
+ break;
+ case ERROR:
+ logger.error(marker, message, exception);
+ break;
+ }
+ verifyMessage(level, marker, null, exception);
+ }
+
+ @Test
+ public void markerMessageOneParameterThrowable() {
+ for (Level level : Level.values()) {
+ markerMessageOneParameterThrowableCheck(level);
+ }
+ }
+
+ private void markerMessageOneParameterThrowableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1, exception);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1, exception);
+ break;
+ case INFO:
+ logger.info(marker, message, param1, exception);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1, exception);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1, exception);
+ break;
+ }
+ verifyMessage(level, marker, oneParam, exception);
+ }
+
+ @Test
+ public void traceMarkerMessageTwoParametersThrowable() {
+ for (Level level : Level.values()) {
+ markerMessageTwoParametersThrowableCheck(level);
+ }
+ }
+
+ private void markerMessageTwoParametersThrowableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1, param2, exception);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1, param2, exception);
+ break;
+ case INFO:
+ logger.info(marker, message, param1, param2, exception);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1, param2, exception);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1, param2, exception);
+ break;
+ }
+ verifyMessage(level, marker, twoParams, exception);
+ }
+
+ @Test
+ public void traceMarkerMessageThreeParametersThrowable() {
+ for (Level level : Level.values()) {
+ markerMessageThreeParametersThrowableCheck(level);
+ }
+ }
+
+ private void markerMessageThreeParametersThrowableCheck(Level level) {
+ switch (level) {
+ case TRACE:
+ logger.trace(marker, message, param1, param2, param3, exception);
+ break;
+ case DEBUG:
+ logger.debug(marker, message, param1, param2, param3, exception);
+ break;
+ case INFO:
+ logger.info(marker, message, param1, param2, param3, exception);
+ break;
+ case WARN:
+ logger.warn(marker, message, param1, param2, param3, exception);
+ break;
+ case ERROR:
+ logger.error(marker, message, param1, param2, param3, exception);
+ break;
+ }
+ verifyMessage(level, marker, threeParams, exception);
+ }
+
+ private void verifyMessageWithoutMarker(Level level, Object[] arguments, Throwable exception) {
+ verifyMessage(level, null, arguments, exception);
+ }
+
+ private void verifyMessage(Level level, Marker marker, Object[] arguments, Throwable exception) {
+
+ assertEquals("missing event: ", 1, queue.size());
+ SubstituteLoggingEvent event = queue.poll();
+ assertNotNull(event);
+
+ if (marker == null) {
+ assertNull(event.getMarkers());
+ } else {
+ assertEquals(marker, event.getMarkers().get(0));
+ }
+
+ assertEquals(message, event.getMessage());
+
+ if (arguments == null) {
+ assertNull(event.getArgumentArray());
+ } else {
+ assertArrayEquals(arguments, event.getArgumentArray());
+ }
+
+ assertEquals("wrong level: ", level, event.getLevel());
+
+ if (exception == null) {
+ assertNull(event.getThrowable());
+ } else {
+ assertEquals(exception, event.getThrowable());
+ }
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/BasicMDCAdapterTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/BasicMDCAdapterTest.java
new file mode 100755
index 00000000..f73a6e06
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/BasicMDCAdapterTest.java
@@ -0,0 +1,17 @@
+package org.slf4j.helpers;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNull;
+
+import org.junit.Test;
+
+public class BasicMDCAdapterTest extends MDCAdapterTestBase {
+
+ @Test
+ public void testClearingMDC() {
+ mdc.put("testKey", "testValue");
+ assertFalse(mdc.getCopyOfContextMap().isEmpty());
+ mdc.clear();
+ assertNull(mdc.getCopyOfContextMap());
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/BogoPerf.java b/slf4j-api/src/test/java/org/slf4j/helpers/BogoPerf.java
deleted file mode 100644
index 86f7d67d..00000000
--- a/slf4j-api/src/test/java/org/slf4j/helpers/BogoPerf.java
+++ /dev/null
@@ -1,150 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.helpers;
-
-import junit.framework.AssertionFailedError;
-
-/**
- * BogoPerf is used to check that the time required to perform a certain
- * operation does not deteriorate over time. BogoPerf adjusts to the CPU speed
- * and capabilities of the host.
- *
- * @author Ceki G&uuml;lc&uuml;
- *
- */
-public class BogoPerf {
-
- private static long NANOS_IN_ONE_SECOND = 1000 * 1000 * 1000;
- private static int INITIAL_N = 1000;
- private static int LAST_N = 100;
- private static int SLACK_FACTOR = 3;
-
- static {
- // let the JIT warm up
- computeBogoIPS(INITIAL_N);
- double bogo_ips = computeBogoIPS(INITIAL_N);
- System.out.println("Host runs at " + bogo_ips + " BIPS");
- }
-
- /**
- * Compute bogoInstructions per second
- * <p>
- * on a 3.2 Ghz Pentium D CPU (around 2007), we obtain about 9'000 bogoIPS.
- *
- * @param N
- * number of bogoInstructions to average over in order to
- * compute the result
- * @return bogo Instructions Per Second
- */
- private static double computeBogoIPS(int N) {
- long begin = System.nanoTime();
-
- for (int i = 0; i < N; i++) {
- bogoInstruction();
- }
- long end = System.nanoTime();
-
- // duration
- double D = end - begin;
- // average duration per instruction
- double avgDPIS = D / N;
- // System.out.println(D + " nanos for " + N + " instructions");
- // System.out.println(avgD + " nanos per instruction");
-
- double bogoIPS = NANOS_IN_ONE_SECOND / avgDPIS;
- // System.out.println(bogoIPS + " bogoIPS");
-
- return bogoIPS;
- }
-
- private static void bogoInstruction() {
- // use our own random number generator, independent of the host JDK
- MyRandom myRandom = new MyRandom(100);
- int len = 150;
- int[] intArray = new int[len];
- for (int i = 0; i < len; i++) {
- intArray[i] = myRandom.nextInt();
- }
- // use our own sort algorithm, independent of the host JDK
- BubbleSort.sort(intArray);
- }
-
- /**
- * Computed the BogoIPS for this host CPU.
- *
- * @return
- */
- public static double currentBIPS() {
- return computeBogoIPS(LAST_N);
- }
-
- static double min(double a, double b) {
- return (a <= b) ? a : b;
- }
-
- /**
- * Assertion used for values that <b>decrease</b> with faster CPUs, typically
- * the time (duration) needed to perform a task.
- *
- * @param currentDuration
- * @param referenceDuration
- * @param referenceBIPS
- * @throws AssertionFailedError
- */
- public static void assertDuration(double currentDuration, long referenceDuration, double referenceBIPS) throws AssertionFailedError {
- double ajustedDuration = adjustExpectedDuration(referenceDuration, referenceBIPS);
- if (currentDuration > ajustedDuration * SLACK_FACTOR) {
- throw new AssertionFailedError("current duration " + currentDuration + " exceeded expected " + ajustedDuration + " (adjusted reference), "
- + referenceDuration + " (raw reference)");
- }
- }
-
- /**
- * Assertion used for values that <b>increase<b> with faster CPUs, typically
- * the number of operations accomplished per unit of time.
- *
- * @param currentPerformance
- * @param referencePerformance
- * @param referenceBIPS
- * @throws AssertionFailedError
- */
- public static void assertPerformance(double currentPerformance, long referencePerformance, double referenceBIPS) throws AssertionFailedError {
- double ajustedPerf = adjustExpectedPerformance(referencePerformance, referenceBIPS);
- if (currentPerformance * SLACK_FACTOR < ajustedPerf) {
- throw new AssertionFailedError(currentPerformance + " below expected " + ajustedPerf + " (adjusted), " + referencePerformance + " (raw)");
- }
- }
-
- private static double adjustExpectedPerformance(long referenceDuration, double referenceBIPS) {
- double currentBIPS = currentBIPS();
- return referenceDuration * (currentBIPS / referenceBIPS);
- }
-
- private static double adjustExpectedDuration(long referenceDuration, double referenceBIPS) {
- double currentBIPS = currentBIPS();
- System.out.println("currentBIPS=" + currentBIPS + " BIPS");
- return referenceDuration * (referenceBIPS / currentBIPS);
- }
-}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/BubbleSortTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/BubbleSortTest.java
deleted file mode 100644
index 3592eb02..00000000
--- a/slf4j-api/src/test/java/org/slf4j/helpers/BubbleSortTest.java
+++ /dev/null
@@ -1,100 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.helpers;
-
-import java.util.Arrays;
-import java.util.Random;
-
-import junit.framework.TestCase;
-
-/**
- * Test that our BubbleSort algorithm is correctly implemented.
- *
- * @author Ceki
- *
- */
-public class BubbleSortTest extends TestCase {
-
- public void testSmoke() {
- int[] a = new int[] { 5, 3, 2, 7 };
- BubbleSort.sort(a);
- int i = 0;
- assertEquals(2, a[i++]);
- assertEquals(3, a[i++]);
- assertEquals(5, a[i++]);
- assertEquals(7, a[i++]);
- }
-
- public void testEmpty() {
- int[] a = new int[] {};
- BubbleSort.sort(a);
- }
-
- public void testSorted() {
- int[] a = new int[] { 3, 30, 300, 3000 };
- BubbleSort.sort(a);
- int i = 0;
- assertEquals(3, a[i++]);
- assertEquals(30, a[i++]);
- assertEquals(300, a[i++]);
- assertEquals(3000, a[i++]);
- }
-
- public void testInverted() {
- int[] a = new int[] { 3000, 300, 30, 3 };
- BubbleSort.sort(a);
- int i = 0;
- assertEquals(3, a[i++]);
- assertEquals(30, a[i++]);
- assertEquals(300, a[i++]);
- assertEquals(3000, a[i++]);
- }
-
- public void testWithSameEntry() {
- int[] a = new int[] { 10, 20, 10, 20 };
- BubbleSort.sort(a);
- int i = 0;
- assertEquals(10, a[i++]);
- assertEquals(10, a[i++]);
- assertEquals(20, a[i++]);
- assertEquals(20, a[i++]);
- }
-
- public void testRandom() {
- int len = 100;
- Random random = new Random(156);
- int[] a = new int[len];
- int[] witness = new int[len];
- for (int i = 0; i < len; i++) {
- int r = random.nextInt();
- a[i] = r;
- witness[i] = r;
- }
- BubbleSort.sort(a);
- Arrays.sort(witness);
- assertTrue(Arrays.equals(witness, a));
- }
-
-}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/MDCAdapterTestBase.java b/slf4j-api/src/test/java/org/slf4j/helpers/MDCAdapterTestBase.java
new file mode 100644
index 00000000..cd97b1c3
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/MDCAdapterTestBase.java
@@ -0,0 +1,147 @@
+/**
+ * Copyright (c) 2004-2013 QOS.ch, Copyright (C) 2015 Google Inc.
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+package org.slf4j.helpers;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.fail;
+
+import java.lang.Thread.UncaughtExceptionHandler;
+import java.util.Map;
+
+import org.junit.After;
+import org.junit.Test;
+import org.slf4j.spi.MDCAdapter;
+
+/**
+ * Tests for {@link BasicMDCAdapter}
+ *
+ * @author Lukasz Cwik
+ */
+public class MDCAdapterTestBase {
+
+ protected MDCAdapter mdc = instantiateMDC();
+
+
+
+ protected MDCAdapter instantiateMDC() {
+ return new BasicMDCAdapter();
+ }
+
+ // leave MDC clean
+ @After
+ public void tearDown() throws Exception {
+ mdc.clear();
+ }
+
+ @Test
+ public void testSettingAndGettingWithMDC() {
+ assertNull(mdc.get("testKey"));
+ mdc.put("testKey", "testValue");
+ assertEquals(mdc.get("testKey"), "testValue");
+ }
+
+ @Test
+ public void testOverwritingAKeyInMDC() {
+ assertNull(mdc.get("testKey"));
+ mdc.put("testKey", "testValue");
+ mdc.put("testKey", "differentTestValue");
+ assertEquals(mdc.get("testKey"), "differentTestValue");
+ }
+
+ @Test
+ public void testGetCopyOfContextMapFromMDC() {
+ mdc.put("testKey", "testValue");
+ Map<String, String> copy = mdc.getCopyOfContextMap();
+ mdc.put("anotherTestKey", "anotherTestValue");
+ assertFalse(copy.size() == mdc.getCopyOfContextMap().size());
+ }
+
+ @Test
+ public void testMDCInheritsValuesFromParentThread() throws Exception {
+ mdc.put("parentKey", "parentValue");
+ runAndWait(() -> {
+ mdc.put("childKey", "childValue");
+ assertEquals("parentValue", mdc.get("parentKey"));
+ });
+ }
+
+ @Test
+ public void testMDCDoesntGetValuesFromChildThread() throws Exception {
+ mdc.put("parentKey", "parentValue");
+ runAndWait(() -> mdc.put("childKey", "childValue"));
+ assertEquals("parentValue", mdc.get("parentKey"));
+ assertNull(mdc.get("childKey"));
+ }
+
+
+ @Test
+ public void testInvokingSetContextMap_WithANullMap_SLF4J_414() {
+ mdc.setContextMap(null);
+ }
+
+ @Test
+ public void testMDCChildThreadCanOverwriteParentThread() throws Exception {
+ mdc.put("sharedKey", "parentValue");
+ runAndWait(() -> {
+ assertEquals("parentValue", mdc.get("sharedKey"));
+ mdc.put("sharedKey", "childValue");
+ assertEquals("childValue", mdc.get("sharedKey"));
+ });
+ assertEquals("parentValue", mdc.get("sharedKey"));
+ }
+
+ private void runAndWait(Runnable runnable) {
+ RecordingExceptionHandler handler = new RecordingExceptionHandler();
+ Thread thread = new Thread(runnable);
+ thread.setUncaughtExceptionHandler(handler);
+ thread.start();
+ try {
+ thread.join();
+ } catch (Throwable t) {
+ fail("Unexpected failure in child thread:" + t.getMessage());
+ }
+ assertFalse(handler.getMessage(), handler.hadException());
+ }
+
+ /** A {@link UncaughtExceptionHandler} that records whether the thread threw an exception. */
+ private static class RecordingExceptionHandler implements UncaughtExceptionHandler {
+ private Throwable exception;
+
+ @Override
+ public void uncaughtException(Thread t, Throwable e) {
+ exception = e;
+ }
+
+ boolean hadException() {
+ return exception != null;
+ }
+
+ String getMessage() {
+ return exception != null ? exception.getMessage() : "";
+ }
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterPerfTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterPerfTest.java
deleted file mode 100755
index 7b9640bb..00000000
--- a/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterPerfTest.java
+++ /dev/null
@@ -1,111 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.helpers;
-
-import java.text.MessageFormat;
-
-import junit.framework.TestCase;
-import org.junit.Ignore;
-
-@Ignore
-public class MessageFormatterPerfTest extends TestCase {
-
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- static long RUN_LENGTH = 100 * 1000;
- //
- static long REFERENCE_BIPS = 48416;
-
- public MessageFormatterPerfTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- }
-
- protected void tearDown() throws Exception {
- }
-
- public void XtestJDKFormatterPerf() {
- jdkMessageFormatter(RUN_LENGTH);
- double duration = jdkMessageFormatter(RUN_LENGTH);
- System.out.println("jdk duration = " + duration + " nanos");
- }
-
- public void testSLF4JPerf_OneArg() {
- slf4jMessageFormatter_OneArg(RUN_LENGTH);
- double duration = slf4jMessageFormatter_OneArg(RUN_LENGTH);
- System.out.println("duration=" + duration);
- long referencePerf = 36;
- BogoPerf.assertDuration(duration, referencePerf, REFERENCE_BIPS);
- }
-
- public void testSLF4JPerf_TwoArg() {
- slf4jMessageFormatter_TwoArg(RUN_LENGTH);
- double duration = slf4jMessageFormatter_TwoArg(RUN_LENGTH);
- long referencePerf = 60;
- BogoPerf.assertDuration(duration, referencePerf, REFERENCE_BIPS);
- }
-
- public double slf4jMessageFormatter_OneArg(long len) {
- long start = System.nanoTime();
- for (int i = 0; i < len; i++) {
- final FormattingTuple tp = MessageFormatter.format("This is some rather short message {} ", i1);
- tp.getMessage();
- tp.getArgArray();
- tp.getThrowable();
-
- MessageFormatter.format("This is some rather short message {} ", i1);
- }
- long end = System.nanoTime();
- return (end - start) / (1000 * 1000.0);
- }
-
- public double slf4jMessageFormatter_TwoArg(long len) {
- long start = System.nanoTime();
- for (int i = 0; i < len; i++) {
- final FormattingTuple tp = MessageFormatter.format("This is some {} short message {} ", i1, i2);
- tp.getMessage();
- tp.getArgArray();
- tp.getThrowable();
- }
- long end = System.nanoTime();
- return (end - start) / (1000 * 1000.0);
- }
-
- public double jdkMessageFormatter(long len) {
- @SuppressWarnings("unused")
- String s = "";
- s += ""; // keep compiler happy
- long start = System.currentTimeMillis();
- Object[] oa = new Object[] { i1 };
- for (int i = 0; i < len; i++) {
- s = MessageFormat.format("This is some rather short message {0}", oa);
- }
- long end = System.currentTimeMillis();
- return (1.0 * end - start);
- }
-
-}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterTest.java
index 98ebaa78..4edd59f5 100755
--- a/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterTest.java
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/MessageFormatterTest.java
@@ -35,11 +35,11 @@ import static org.junit.Assert.*;
*/
public class MessageFormatterTest {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
+ Integer i1 = Integer.valueOf(1);
+ Integer i2 = Integer.valueOf(2);
+ Integer i3 = Integer.valueOf(3);
Integer[] ia0 = new Integer[] { i1, i2, i3 };
- Integer[] ia1 = new Integer[] { new Integer(10), new Integer(20), new Integer(30) };
+ Integer[] ia1 = new Integer[] { Integer.valueOf(10), Integer.valueOf(20), Integer.valueOf(30) };
String result;
@@ -50,6 +50,15 @@ public class MessageFormatterTest {
}
@Test
+ public void testParamaterContainingAnAnchor() {
+ result = MessageFormatter.format("Value is {}.", "[{}]").getMessage();
+ assertEquals("Value is [{}].", result);
+
+ result = MessageFormatter.format("Values are {} and {}.", i1, "[{}]").getMessage();
+ assertEquals("Values are 1 and [{}].", result);
+ }
+
+ @Test
public void nullParametersShouldBeHandledWithoutBarfing() {
result = MessageFormatter.format("Value is {}.", null).getMessage();
assertEquals("Value is null.", result);
@@ -311,14 +320,20 @@ public class MessageFormatterTest {
assertTrue(Arrays.equals(iaWitness, ft.getArgArray()));
assertEquals(t, ft.getThrowable());
- ft = MessageFormatter.arrayFormat("Value {} is smaller than {} and {} -- {} .", ia);
- assertEquals("Value 1 is smaller than 2 and 3 -- " + t.toString() + " .", ft.getMessage());
- assertTrue(Arrays.equals(ia, ft.getArgArray()));
- assertNull(ft.getThrowable());
+ ft = MessageFormatter.arrayFormat("Value {} is smaller than {} and {}.", ia);
+ assertEquals("Value 1 is smaller than 2 and 3.", ft.getMessage());
+ assertTrue(Arrays.equals(iaWitness, ft.getArgArray()));
+ assertEquals(t, ft.getThrowable());
ft = MessageFormatter.arrayFormat("{}{}{}{}", ia);
- assertEquals("123" + t.toString(), ft.getMessage());
- assertTrue(Arrays.equals(ia, ft.getArgArray()));
- assertNull(ft.getThrowable());
+ assertEquals("123{}", ft.getMessage());
+ assertTrue(Arrays.equals(iaWitness, ft.getArgArray()));
+ assertEquals(t, ft.getThrowable());
+
+ ft = MessageFormatter.arrayFormat("1={}", new Object[] { i1 }, t);
+ assertEquals("1=1", ft.getMessage());
+ assertTrue(Arrays.equals(new Object[] { i1 }, ft.getArgArray()));
+ assertEquals(t, ft.getThrowable());
+
}
}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/MyRandom.java b/slf4j-api/src/test/java/org/slf4j/helpers/MyRandom.java
deleted file mode 100644
index c817d673..00000000
--- a/slf4j-api/src/test/java/org/slf4j/helpers/MyRandom.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.helpers;
-
-class MyRandom {
-
- private final static long m = 200000000041L; // a prime number
- private final static long a = 2000000011L; // a prime number
-
- long y;
- long unused;
- int bits = 32;
-
- public MyRandom() {
- this(System.nanoTime());
- }
-
- public MyRandom(long seed) {
- this.y = seed;
- }
-
- int nextInt() {
- // we don't really care about the randomness of this
- // generator
- y = (a * y + 1) % m;
- unused = y >>> (48 - bits); // just exercise the >>> operator
- return (int) (y);
- }
-}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/StringPrintStream.java b/slf4j-api/src/test/java/org/slf4j/helpers/StringPrintStream.java
new file mode 100755
index 00000000..68a76257
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/StringPrintStream.java
@@ -0,0 +1,74 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.helpers;
+
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Copied from org.slfj.helpers.
+ *
+ * Currently it is not possible to use test-jar from tests running on the module-path.
+ *
+ * @author ceki
+ */
+public class StringPrintStream extends PrintStream {
+
+ public static final String LINE_SEP = System.getProperty("line.separator");
+ PrintStream other;
+ boolean duplicate = false;
+
+ public List<String> stringList = Collections.synchronizedList(new ArrayList<>());
+
+ public StringPrintStream(PrintStream ps, boolean duplicate) {
+ super(ps);
+ other = ps;
+ this.duplicate = duplicate;
+ }
+
+ public StringPrintStream(PrintStream ps) {
+ this(ps, false);
+ }
+
+ public void print(String s) {
+ if (duplicate)
+ other.print(s);
+ stringList.add(s);
+ }
+
+ public void println(String s) {
+ if (duplicate)
+ other.println(s);
+ stringList.add(s);
+ }
+
+ public void println(Object o) {
+ if (duplicate)
+ other.println(o);
+ stringList.add(o.toString());
+ }
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/SubstitutableLoggerTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/SubstitutableLoggerTest.java
index 210252f3..f82c4f5d 100644
--- a/slf4j-api/src/test/java/org/slf4j/helpers/SubstitutableLoggerTest.java
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/SubstitutableLoggerTest.java
@@ -24,56 +24,84 @@
*/
package org.slf4j.helpers;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
-import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashSet;
-import java.util.List;
import java.util.Set;
-import junit.framework.TestCase;
+import org.junit.Test;
import org.slf4j.Logger;
+import org.slf4j.event.EventRecordingLogger;
/**
* @author Chetan Mehrotra
+ * @author Ceki Gülcü
*/
-public class SubstitutableLoggerTest extends TestCase {
- private static final Set<String> EXCLUDED_METHODS = new HashSet<String>(Arrays.asList("getName"));
+public class SubstitutableLoggerTest {
+
+ // NOTE: previous implementations of this class performed a handcrafted conversion of
+ // a method to a string. In this implementation we just invoke method.toString().
+
+ // WARNING: if you need to add an excluded method to have tests pass, ask yourself whether you
+ // forgot to implement the said method with delegation in SubstituteLogger. You probably did.
+ private static final Set<String> EXCLUDED_METHODS = new HashSet<>(
+ Arrays.asList("getName"));
- public void testDelegate() throws Exception {
- SubstituteLogger log = new SubstituteLogger("foo");
- assertTrue(log.delegate() instanceof NOPLogger);
+
+ /**
+ * Test that all SubstituteLogger methods invoke the delegate, except for explicitly excluded methods.
+ */
+ @Test
+ public void delegateIsInvokedTest() throws Exception {
+ SubstituteLogger substituteLogger = new SubstituteLogger("foo", null, false);
+ assertTrue(substituteLogger.delegate() instanceof EventRecordingLogger);
Set<String> expectedMethodSignatures = determineMethodSignatures(Logger.class);
- LoggerInvocationHandler ih = new LoggerInvocationHandler();
- Logger proxyLogger = (Logger) Proxy.newProxyInstance(getClass().getClassLoader(), new Class[] { Logger.class }, ih);
- log.setDelegate(proxyLogger);
+ LoggerInvocationHandler loggerInvocationHandler = new LoggerInvocationHandler();
+ Logger proxyLogger = (Logger) Proxy.newProxyInstance(getClass().getClassLoader(), new Class[] { Logger.class }, loggerInvocationHandler);
+ substituteLogger.setDelegate(proxyLogger);
- invokeMethods(log);
+ invokeAllMethodsOf(substituteLogger);
// Assert that all methods are delegated
- expectedMethodSignatures.removeAll(ih.getInvokedMethodSignatures());
+ expectedMethodSignatures.removeAll(loggerInvocationHandler.getInvokedMethodSignatures());
if (!expectedMethodSignatures.isEmpty()) {
fail("Following methods are not delegated " + expectedMethodSignatures.toString());
}
}
- private void invokeMethods(Logger proxyLogger) throws InvocationTargetException, IllegalAccessException {
+ private void invokeAllMethodsOf(Logger logger) throws InvocationTargetException, IllegalAccessException {
for (Method m : Logger.class.getDeclaredMethods()) {
if (!EXCLUDED_METHODS.contains(m.getName())) {
- m.invoke(proxyLogger, new Object[m.getParameterTypes().length]);
+ m.invoke(logger, new Object[m.getParameterTypes().length]);
}
}
}
+ private static Set<String> determineMethodSignatures(Class<Logger> loggerClass) {
+ Set<String> methodSignatures = new HashSet<>();
+ // Note: Class.getDeclaredMethods() does not include inherited methods
+ for (Method m : loggerClass.getDeclaredMethods()) {
+ if (!EXCLUDED_METHODS.contains(m.getName())) {
+ methodSignatures.add(m.toString());
+ }
+ }
+ return methodSignatures;
+ }
+
+
+ // implements InvocationHandler
private class LoggerInvocationHandler implements InvocationHandler {
- private final Set<String> invokedMethodSignatures = new HashSet<String>();
+ private final Set<String> invokedMethodSignatures = new HashSet<>();
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
- invokedMethodSignatures.add(getMethodSignature(method));
+ invokedMethodSignatures.add(method.toString());
if (method.getName().startsWith("is")) {
return true;
}
@@ -84,23 +112,4 @@ public class SubstitutableLoggerTest extends TestCase {
return invokedMethodSignatures;
}
}
-
- private static Set<String> determineMethodSignatures(Class<Logger> loggerClass) {
- Set<String> methodSignatures = new HashSet<String>();
- for (Method m : loggerClass.getDeclaredMethods()) {
- if (!EXCLUDED_METHODS.contains(m.getName())) {
- methodSignatures.add(getMethodSignature(m));
- }
- }
- return methodSignatures;
- }
-
- private static String getMethodSignature(Method m) {
- List<String> result = new ArrayList<String>();
- result.add(m.getName());
- for (Class<?> clazz : m.getParameterTypes()) {
- result.add(clazz.getSimpleName());
- }
- return result.toString();
- }
}
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/SubstituteLoggerFactoryTest.java b/slf4j-api/src/test/java/org/slf4j/helpers/SubstituteLoggerFactoryTest.java
index 370fc14b..a836f86b 100755
--- a/slf4j-api/src/test/java/org/slf4j/helpers/SubstituteLoggerFactoryTest.java
+++ b/slf4j-api/src/test/java/org/slf4j/helpers/SubstituteLoggerFactoryTest.java
@@ -24,16 +24,21 @@
*/
package org.slf4j.helpers;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+
+import org.junit.Test;
import org.slf4j.Logger;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Set;
-public class SubstituteLoggerFactoryTest extends TestCase {
- private SubstituteLoggerFactory factory = new SubstituteLoggerFactory();
+public class SubstituteLoggerFactoryTest {
+ private final SubstituteLoggerFactory factory = new SubstituteLoggerFactory();
+ @Test
public void testFactory() {
Logger log = factory.getLogger("foo");
assertNotNull(log);
@@ -42,23 +47,25 @@ public class SubstituteLoggerFactoryTest extends TestCase {
assertTrue("Loggers with same name must be same", log == log2);
}
+ @Test
public void testLoggerNameList() {
factory.getLogger("foo1");
factory.getLogger("foo2");
- Set<String> expectedNames = new HashSet<String>(Arrays.asList("foo1", "foo2"));
- Set<String> actualNames = new HashSet<String>(factory.getLoggerNames());
+ Set<String> expectedNames = new HashSet<>(Arrays.asList("foo1", "foo2"));
+ Set<String> actualNames = new HashSet<>(factory.getLoggerNames());
assertEquals(expectedNames, actualNames);
}
+ @Test
public void testLoggers() {
factory.getLogger("foo1");
factory.getLogger("foo2");
- Set<String> expectedNames = new HashSet<String>(Arrays.asList("foo1", "foo2"));
+ Set<String> expectedNames = new HashSet<>(Arrays.asList("foo1", "foo2"));
- Set<String> actualNames = new HashSet<String>();
+ Set<String> actualNames = new HashSet<>();
for (SubstituteLogger slog : factory.getLoggers()) {
actualNames.add(slog.getName());
}
diff --git a/slf4j-api/src/test/java/org/slf4j/rule/BlaTest.java b/slf4j-api/src/test/java/org/slf4j/rule/BlaTest.java
new file mode 100755
index 00000000..259d063a
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/rule/BlaTest.java
@@ -0,0 +1,38 @@
+package org.slf4j.rule;
+
+import static org.junit.Assert.fail;
+
+import org.junit.Ignore;
+import org.junit.Rule;
+import org.junit.Test;
+
+@Ignore // this test has intentional fails
+public class BlaTest {
+
+ @Rule
+ public RunInNewThreadRule runInThread = new RunInNewThreadRule();
+
+ @Test
+ public void aTest() {
+ System.out.println("running aTest in "+ Thread.currentThread().getName());
+ }
+
+ @RunInNewThread
+ @Test
+ public void bTest() {
+ System.out.println("running bTest in "+ Thread.currentThread().getName());
+ }
+
+ @RunInNewThread(timeout = 2000L)
+ @Test
+ public void cTest() {
+ System.out.println("running cTest in "+ Thread.currentThread().getName());
+ }
+ @RunInNewThread()
+ @Test
+ public void dTest() {
+ System.out.println("running dTest in "+ Thread.currentThread().getName());
+ fail();
+ }
+}
+
diff --git a/slf4j-api/src/test/java/org/slf4j/helpers/BubbleSort.java b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThread.java
index e8f7bcfc..1bf5944f 100644..100755
--- a/slf4j-api/src/test/java/org/slf4j/helpers/BubbleSort.java
+++ b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThread.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2021 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,30 +22,18 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.helpers;
-/**
- * This class is used internally by BogoPerf, hence the package private
- * (default) access.
- *
- * @author Ceki
- */
-class BubbleSort {
+package org.slf4j.rule;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
- static void sort(int[] a) {
- int len = a.length;
- for (int i = 0; i < len - 1; i++) {
- for (int j = 0; j < len - 1 - i; j++) {
- if (a[j] > a[j + 1]) {
- swap(a, j, j + 1);
- }
- }
- }
- }
- static void swap(int[] a, int i, int j) {
- int t = a[i];
- a[i] = a[j];
- a[j] = t;
- }
+@Retention(RetentionPolicy.RUNTIME)
+@Target({ElementType.METHOD})
+public @interface RunInNewThread {
+ static final long DEFAULT_TIMEOUT = 1000L;
+ public long timeout() default DEFAULT_TIMEOUT;
}
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/MDCStrLookup.java b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadRule.java
index 5d1e63cf..3945144f 100644..100755
--- a/slf4j-ext/src/main/java/org/slf4j/ext/MDCStrLookup.java
+++ b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadRule.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2021 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,28 +22,33 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.ext;
-import org.apache.commons.lang.text.StrLookup;
-import org.slf4j.MDC;
+package org.slf4j.rule;
-/**
- * This class can be used with the Commons Lang StrSubstitutor to replace
- * tokens that occur in Strings with their values in the MDC.
- *
- * @author Ralph Goers
- */
-public class MDCStrLookup extends StrLookup {
- /**
- * Looks up up a value in the MDC.
- *
- * @param key the key to be looked up, may be null
- * @return the matching value, null if no match
- */
- public String lookup(String key) {
- if (key == null) {
- return null;
+import org.junit.rules.TestRule;
+import org.junit.runner.Description;
+import org.junit.runners.model.Statement;
+
+// This class has been inspired by the article "A JUnit Rule to Run a Test in Its Own Thread"
+// published by Frank Appel, author of the book "Testing with JUnit" published by Packt publishing.
+//
+// See also
+// https://www.codeaffine.com/2014/07/21/a-junit-rule-to-run-a-test-in-its-own-thread/
+
+public class RunInNewThreadRule implements TestRule {
+
+ @Override
+ public Statement apply(Statement base, Description description) {
+ RunInNewThread desiredAnnotaton = description.getAnnotation(RunInNewThread.class);
+
+ if (desiredAnnotaton == null) {
+ System.out.println("test "+ description.getMethodName() +" not annotated");
+ return base;
+ } else {
+ long timeout = desiredAnnotaton.timeout();
+ System.out.println("running "+ description.getMethodName() +" in separate tjread");
+ return new RunInNewThreadStatement(base, timeout);
}
- return MDC.get(key);
}
+
}
diff --git a/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadStatement.java b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadStatement.java
new file mode 100755
index 00000000..2b8869e5
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/rule/RunInNewThreadStatement.java
@@ -0,0 +1,68 @@
+/**
+ * Copyright (c) 2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.rule;
+
+import org.junit.runners.model.Statement;
+
+//This class has been inspired by the article "A JUnit Rule to Run a Test in Its Own Thread"
+//published by Frank Appel, author of the book "Testing with JUnit" published by Packt publishing.
+//
+//See also
+//https://www.codeaffine.com/2014/07/21/a-junit-rule-to-run-a-test-in-its-own-thread/
+
+public class RunInNewThreadStatement extends Statement implements Runnable {
+
+ final Statement base;
+ final long timeout;
+ Throwable throwable;
+
+ RunInNewThreadStatement(Statement base, long timeout) {
+ this.base = base;
+ this.timeout = timeout;
+ }
+
+ @Override
+ public void evaluate() throws Throwable {
+ Thread thread = new Thread(this);
+ thread.start();
+ System.out.println("Timeout is "+timeout);
+ thread.join(timeout);
+
+ if (throwable != null) {
+ throw throwable;
+ }
+ }
+
+ @Override
+ public void run() {
+ try {
+ base.evaluate();
+ } catch (Throwable e) {
+ this.throwable = e;
+ }
+ }
+
+
+}
diff --git a/slf4j-api/src/test/java/org/slf4j/testHarness/MultithreadedInitializationTest.java b/slf4j-api/src/test/java/org/slf4j/testHarness/MultithreadedInitializationTest.java
new file mode 100644
index 00000000..c534bad1
--- /dev/null
+++ b/slf4j-api/src/test/java/org/slf4j/testHarness/MultithreadedInitializationTest.java
@@ -0,0 +1,79 @@
+package org.slf4j.testHarness;
+
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.concurrent.BrokenBarrierException;
+import java.util.concurrent.CyclicBarrier;
+import java.util.concurrent.atomic.AtomicLong;
+
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerAccessingThread;
+import org.slf4j.LoggerFactory;
+import org.slf4j.event.EventRecordingLogger;
+import org.slf4j.helpers.SubstituteLogger;
+
+abstract public class MultithreadedInitializationTest {
+ final protected static int THREAD_COUNT = 4 + Runtime.getRuntime().availableProcessors() * 2;
+
+ private final List<Logger> createdLoggers = Collections.synchronizedList(new ArrayList<>());
+
+ final protected AtomicLong eventCount = new AtomicLong(0);
+ final private CyclicBarrier barrier = new CyclicBarrier(THREAD_COUNT + 1);
+
+ @Test
+ public void multiThreadedInitialization() throws InterruptedException, BrokenBarrierException {
+ @SuppressWarnings("unused")
+ LoggerAccessingThread[] accessors = harness();
+
+ Logger logger = LoggerFactory.getLogger(getClass().getName());
+ logger.info("hello");
+ eventCount.getAndIncrement();
+
+ assertAllSubstLoggersAreFixed();
+ long recordedEventCount = getRecordedEventCount();
+ int LENIENCY_COUNT = 30;
+
+ long expectedEventCount = eventCount.get() + extraLogEvents();
+
+ assertTrue(expectedEventCount + " >= " + recordedEventCount, expectedEventCount >= recordedEventCount);
+ assertTrue(expectedEventCount + " < " + recordedEventCount + "+" + LENIENCY_COUNT, expectedEventCount < recordedEventCount + LENIENCY_COUNT);
+ }
+
+ abstract protected long getRecordedEventCount();
+
+ protected int extraLogEvents() {
+ return 0;
+ }
+
+ private void assertAllSubstLoggersAreFixed() {
+ for (Logger logger : createdLoggers) {
+ if (logger instanceof SubstituteLogger) {
+ SubstituteLogger substLogger = (SubstituteLogger) logger;
+ if (substLogger.delegate() instanceof EventRecordingLogger)
+ fail("substLogger " + substLogger.getName() + " has a delegate of type EventRecodingLogger");
+ }
+ }
+ }
+
+ private LoggerAccessingThread[] harness() throws InterruptedException, BrokenBarrierException {
+ LoggerAccessingThread[] threads = new LoggerAccessingThread[THREAD_COUNT];
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i] = new LoggerAccessingThread(barrier, createdLoggers, i, eventCount);
+ threads[i].start();
+ }
+
+ // trigger barrier
+ barrier.await();
+
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i].join();
+ }
+
+ return threads;
+ }
+}
diff --git a/slf4j-site/LICENSE.txt b/slf4j-ext/LICENSE.txt
index 508a2728..1a3d0532 100644
--- a/slf4j-site/LICENSE.txt
+++ b/slf4j-ext/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-ext/pom.xml b/slf4j-ext/pom.xml
index f2cec047..dd07244d 100755
--- a/slf4j-ext/pom.xml
+++ b/slf4j-ext/pom.xml
@@ -1,5 +1,5 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
@@ -7,7 +7,8 @@
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-ext</artifactId>
@@ -25,13 +26,14 @@
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
- <artifactId>slf4j-log4j12</artifactId>
+ <artifactId>slf4j-reload4j</artifactId>
<version>${project.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>ch.qos.cal10n</groupId>
<artifactId>cal10n-api</artifactId>
+ <optional>true</optional>
</dependency>
<dependency>
<groupId>javassist</groupId>
@@ -39,30 +41,15 @@
<version>3.4.GA</version>
<optional>true</optional>
</dependency>
- <dependency>
- <groupId>commons-lang</groupId>
- <artifactId>commons-lang</artifactId>
- <version>2.4</version>
- <optional>true</optional>
- </dependency>
</dependencies>
<build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-compiler-plugin</artifactId>
- <configuration>
- <source>${required.jdk.version}</source>
- <target>${required.jdk.version}</target>
- </configuration>
- </plugin>
-
+ <plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<configuration>
- <!-- http://maven.apache.org/plugins/maven-surefire-plugin/test-mojo.html -->
+ <!-- http://maven.apache.org/plugins/maven-surefire-plugin/test-mojo.html -->
<printSummary>false</printSummary>
<forkMode>once</forkMode>
<reportFormat>plain</reportFormat>
@@ -74,32 +61,32 @@
</configuration>
</plugin>
-
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<configuration>
<archive>
<manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
<Premain-Class>org.slf4j.agent.AgentPremain</Premain-Class>
<!-- what is the proper way to specify the maven full name? /ravn -->
<Boot-Class-Path>../../../../javassist/javassist/3.4.GA/javassist-3.4.GA.jar javassist-3.4.GA.jar javassist.jar</Boot-Class-Path>
</manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
</archive>
- </configuration>
- </plugin>
- </plugins>
+ </configuration>
+ </plugin>
- </build>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <configuration>
+ <instructions>
+ <Import-Package>ch.qos.cal10n;version="${cal10n.version}";resolution:="optional", org.slf4j, org.slf4j.*</Import-Package>
+ <_exportcontents>org.slf4j.ext, org.slf4j.profiler, org.slf4j.cal10n</_exportcontents>
+ </instructions>
+ </configuration>
+ </plugin>
- <reporting>
- <plugins>
-
</plugins>
- </reporting>
+ </build>
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-ext/src/main/java/org/slf4j/NDC.java b/slf4j-ext/src/main/java/org/slf4j/NDC.java
index fbad2741..623e96d3 100644
--- a/slf4j-ext/src/main/java/org/slf4j/NDC.java
+++ b/slf4j-ext/src/main/java/org/slf4j/NDC.java
@@ -24,8 +24,6 @@
*/
package org.slf4j;
-import org.slf4j.MDC;
-
public class NDC {
public final static String PREFIX = "NDC";
diff --git a/slf4j-ext/src/main/java/org/slf4j/agent/AgentOptions.java b/slf4j-ext/src/main/java/org/slf4j/agent/AgentOptions.java
index 181dfba5..600e5f40 100644
--- a/slf4j-ext/src/main/java/org/slf4j/agent/AgentOptions.java
+++ b/slf4j-ext/src/main/java/org/slf4j/agent/AgentOptions.java
@@ -28,12 +28,12 @@ package org.slf4j.agent;
* <p>
* All recognized options in the string passed to the java agent. For
* "java -javaagent:foo.jar=OPTIONS HelloWorld" this would be "OPTIONS".
- * </p>
+ *
* <p>
* It is considered to be a list of options separated by (currently) ";", on the
* form "option=value". The interpretation of "value" is specific to each
* option.
- * </p>
+ *
*/
public class AgentOptions {
diff --git a/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java b/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java
index bca08135..7db5cb7d 100644
--- a/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java
+++ b/slf4j-ext/src/main/java/org/slf4j/agent/AgentPremain.java
@@ -34,16 +34,14 @@ import org.slf4j.instrumentation.LogTransformer;
/**
* Entry point for slf4j-ext when used as a Java agent.
- *
+ *
*/
public class AgentPremain {
/**
* JavaAgent premain entry point as specified in the MANIFEST.MF file. See
- * {@link http
- * ://java.sun.com/javase/6/docs/api/java/lang/instrument/package-
- * summary.html} for details.
- *
+ * <a href="http://java.sun.com/javase/6/docs/api/java/lang/instrument/package-summary.html">http://java.sun.com/javase/6/docs/api/java/lang/instrument/package-summary.html</a> for details.
+ *
* @param agentArgument
* string provided after "=" up to first space
* @param instrumentation
@@ -85,8 +83,8 @@ public class AgentPremain {
* Consider the argument string to be a property file (by converting the
* splitter character to line feeds), and then reading it like any other
* property file.
- *
- *
+ *
+ *
* @param agentArgument
* string given by instrumentation framework
* @param separator
@@ -109,20 +107,17 @@ public class AgentPremain {
* Print the start message to System.err with the time NOW, and register a
* shutdown hook which will print the stop message to System.err with the
* time then and the number of milliseconds passed since.
- *
+ *
*/
private static void printStartStopTimes() {
final long start = System.currentTimeMillis();
System.err.println("Start at " + new Date());
- Thread hook = new Thread() {
- @Override
- public void run() {
- long timePassed = System.currentTimeMillis() - start;
- System.err.println("Stop at " + new Date() + ", execution time = " + timePassed + " ms");
- }
- };
+ Thread hook = new Thread(() -> {
+ long timePassed = System.currentTimeMillis() - start;
+ System.err.println("Stop at " + new Date() + ", execution time = " + timePassed + " ms");
+ });
Runtime.getRuntime().addShutdownHook(hook);
}
-} \ No newline at end of file
+}
diff --git a/slf4j-ext/src/main/java/org/slf4j/agent/package.html b/slf4j-ext/src/main/java/org/slf4j/agent/package.html
index 61726464..7385f651 100644
--- a/slf4j-ext/src/main/java/org/slf4j/agent/package.html
+++ b/slf4j-ext/src/main/java/org/slf4j/agent/package.html
@@ -24,10 +24,7 @@ E.g.
is changed to
<pre><code>java -javaagent:/path/to/slf4j-ext-X.Y.Z.jar=<em>OPTIONS</em> HelloWorld</code></pre>
-What is actually done, depends on the <em>OPTIONS</em> passed to the agent. These are listed in AgentOptions.java.
-</p>
-
-
+<p>What is actually done, depends on the <em>OPTIONS</em> passed to the agent. These are listed in AgentOptions.java.
</body>
</html>
diff --git a/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLogger.java b/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLogger.java
index d4ee8fe5..3e77b467 100644
--- a/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLogger.java
+++ b/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLogger.java
@@ -35,7 +35,7 @@ import ch.qos.cal10n.MessageParameterObj;
/**
* A logger specialized in localized logging. Localization is based in the <a
- * href="http://cal10n.qos.ch">CAL10N project</p>.
+ * href="http://cal10n.qos.ch">CAL10N project</a>.
*
* @author Ceki G&uuml;lc&uuml;
*/
diff --git a/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLoggerFactory.java b/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLoggerFactory.java
index 2e54beec..f3c52090 100644
--- a/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLoggerFactory.java
+++ b/slf4j-ext/src/main/java/org/slf4j/cal10n/LocLoggerFactory.java
@@ -30,19 +30,19 @@ import org.slf4j.LoggerFactory;
import ch.qos.cal10n.IMessageConveyor;
/**
- *
+ *
* This class is essentially a wrapper around an {@link LoggerFactory} producing
* {@link LocLogger} instances.
- *
+ *
* <p>
* Contrary to {@link LoggerFactory#getLogger(String)} method of
- * {@link LoggerFactory}, each call to {@link getLocLogger} produces a new
+ * {@link LoggerFactory}, each call to {@link #getLocLogger(String)} produces a new
* instance of {@link LocLogger}. This should not matter because a LocLogger
- * instance does have any state beyond that of the {@link Logger} in stance it
+ * instance does have any state beyond that of the {@link Logger} instance it
* wraps and its message conveyor.
- *
- * @author Ceki G&uuml;c&uuml;
- *
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ *
*/
public class LocLoggerFactory {
@@ -54,8 +54,8 @@ public class LocLoggerFactory {
/**
* Get an LocLogger instance by name.
- *
- * @param name
+ *
+ * @param name name of the logger to retrieve
* @return LocLogger instance by name.
*/
public LocLogger getLocLogger(String name) {
@@ -65,8 +65,8 @@ public class LocLoggerFactory {
/**
* Get a new LocLogger instance by class. The returned LocLogger will be named
* after the class.
- *
- * @param clazz
+ *
+ * @param clazz a class
* @return LocLogger instance by class
*/
public LocLogger getLocLogger(Class<?> clazz) {
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/EventData.java b/slf4j-ext/src/main/java/org/slf4j/ext/EventData.java
deleted file mode 100755
index cd661b83..00000000
--- a/slf4j-ext/src/main/java/org/slf4j/ext/EventData.java
+++ /dev/null
@@ -1,305 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.ext;
-
-import java.io.Serializable;
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-import java.beans.XMLDecoder;
-import java.beans.XMLEncoder;
-import java.beans.ExceptionListener;
-
-/**
- * Base class for Event Data. Event Data contains data to be logged about an
- * event. Users may extend this class for each EventType they want to log.
- *
- * @author Ralph Goers
- */
-public class EventData implements Serializable {
-
- private static final long serialVersionUID = 153270778642103985L;
-
- private Map<String, Object> eventData = new HashMap<String, Object>();
- public static final String EVENT_MESSAGE = "EventMessage";
- public static final String EVENT_TYPE = "EventType";
- public static final String EVENT_DATETIME = "EventDateTime";
- public static final String EVENT_ID = "EventId";
-
- /**
- * Default Constructor
- */
- public EventData() {
- }
-
- /**
- * Constructor to create event data from a Map.
- *
- * @param map
- * The event data.
- */
- public EventData(Map<String, Object> map) {
- eventData.putAll(map);
- }
-
- /**
- * Construct from a serialized form of the Map containing the RequestInfo
- * elements
- *
- * @param xml
- * The serialized form of the RequestInfo Map.
- */
- @SuppressWarnings("unchecked")
- public EventData(String xml) {
- ByteArrayInputStream bais = new ByteArrayInputStream(xml.getBytes());
- try {
- XMLDecoder decoder = new XMLDecoder(bais);
- this.eventData = (Map<String, Object>) decoder.readObject();
- } catch (Exception e) {
- throw new EventException("Error decoding " + xml, e);
- }
- }
-
- /**
- * Serialize all the EventData items into an XML representation.
- *
- * @return an XML String containing all the EventDAta items.
- */
- public String toXML() {
- return toXML(eventData);
- }
-
- /**
- * Serialize all the EventData items into an XML representation.
- *
- * @param map the Map to transform
- * @return an XML String containing all the EventDAta items.
- */
- public static String toXML(Map<String, Object> map) {
- ByteArrayOutputStream baos = new ByteArrayOutputStream();
- try {
- XMLEncoder encoder = new XMLEncoder(baos);
- encoder.setExceptionListener(new ExceptionListener() {
- public void exceptionThrown(Exception exception) {
- exception.printStackTrace();
- }
- });
- encoder.writeObject(map);
- encoder.close();
- return baos.toString();
- } catch (Exception e) {
- e.printStackTrace();
- return null;
- }
- }
-
- /**
- * Retrieve the event identifier.
- *
- * @return The event identifier
- */
- public String getEventId() {
- return (String) this.eventData.get(EVENT_ID);
- }
-
- /**
- * Set the event identifier.
- *
- * @param eventId
- * The event identifier.
- */
- public void setEventId(String eventId) {
- if (eventId == null) {
- throw new IllegalArgumentException("eventId cannot be null");
- }
- this.eventData.put(EVENT_ID, eventId);
- }
-
- /**
- * Retrieve the message text associated with this event, if any.
- *
- * @return The message text associated with this event or null if there is
- * none.
- */
- public String getMessage() {
- return (String) this.eventData.get(EVENT_MESSAGE);
- }
-
- /**
- * Set the message text associated with this event.
- *
- * @param message
- * The message text.
- */
- public void setMessage(String message) {
- this.eventData.put(EVENT_MESSAGE, message);
- }
-
- /**
- * Retrieve the date and time the event occurred.
- *
- * @return The Date associated with the event.
- */
- public Date getEventDateTime() {
- return (Date) this.eventData.get(EVENT_DATETIME);
- }
-
- /**
- * Set the date and time the event occurred in case it is not the same as when
- * the event was logged.
- *
- * @param eventDateTime
- * The event Date.
- */
- public void setEventDateTime(Date eventDateTime) {
- this.eventData.put(EVENT_DATETIME, eventDateTime);
- }
-
- /**
- * Set the type of event that occurred.
- *
- * @param eventType
- * The type of the event.
- */
- public void setEventType(String eventType) {
- this.eventData.put(EVENT_TYPE, eventType);
- }
-
- /**
- * Retrieve the type of the event.
- *
- * @return The event type.
- */
- public String getEventType() {
- return (String) this.eventData.get(EVENT_TYPE);
- }
-
- /**
- * Add arbitrary attributes about the event.
- *
- * @param name
- * The attribute's key.
- * @param obj
- * The data associated with the key.
- */
- public void put(String name, Serializable obj) {
- this.eventData.put(name, obj);
- }
-
- /**
- * Retrieve an event attribute.
- *
- * @param name
- * The attribute's key.
- * @return The value associated with the key or null if the key is not
- * present.
- */
- public Serializable get(String name) {
- return (Serializable) this.eventData.get(name);
- }
-
- /**
- * Populate the event data from a Map.
- *
- * @param data
- * The Map to copy.
- */
- public void putAll(Map<String, Object> data) {
- this.eventData.putAll(data);
- }
-
- /**
- * Returns the number of attributes in the EventData.
- *
- * @return the number of attributes in the EventData.
- */
- public int getSize() {
- return this.eventData.size();
- }
-
- /**
- * Returns an Iterator over all the entries in the EventDAta.
- *
- * @return an Iterator that can be used to access all the event attributes.
- */
- public Iterator<Map.Entry<String, Object>> getEntrySetIterator() {
- return this.eventData.entrySet().iterator();
- }
-
- /**
- * Retrieve all the attributes in the EventData as a Map. Changes to this map
- * will be reflected in the EventData.
- *
- * @return The Map of attributes in this EventData instance.
- */
- public Map<String, Object> getEventMap() {
- return this.eventData;
- }
-
- /**
- * Convert the EventData to a String.
- *
- * @return The EventData as a String.
- */
- @Override
- public String toString() {
- return toXML();
- }
-
- /**
- * Compare two EventData objects for equality.
- *
- * @param o
- * The Object to compare.
- * @return true if the objects are the same instance or contain all the same
- * keys and their values.
- */
- @SuppressWarnings("unchecked")
- @Override
- public boolean equals(Object o) {
- if (this == o) {
- return true;
- }
- if (!(o instanceof EventData || o instanceof Map)) {
- return false;
- }
- Map<String, Object> map = (o instanceof EventData) ? ((EventData) o).getEventMap() : (Map<String, Object>) o;
-
- return this.eventData.equals(map);
- }
-
- /**
- * Compute the hashCode for this EventData instance.
- *
- * @return The hashcode for this EventData instance.
- */
- @Override
- public int hashCode() {
- return this.eventData.hashCode();
- }
-} \ No newline at end of file
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/EventException.java b/slf4j-ext/src/main/java/org/slf4j/ext/EventException.java
deleted file mode 100644
index ab220768..00000000
--- a/slf4j-ext/src/main/java/org/slf4j/ext/EventException.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.ext;
-
-/**
- * Exception used to identify issues related to an event that is being logged.
- */
-public class EventException extends RuntimeException {
-
- private static final long serialVersionUID = -22873966112391992L;
-
- /**
- * Default constructor.
- */
- public EventException() {
- super();
- }
-
- /**
- * Constructor that allows an exception message.
- * @param exceptionMessage The exception message.
- */
- public EventException(String exceptionMessage) {
- super(exceptionMessage);
- }
-
- /**
- * Constructor that chains another Exception or Error.
- * @param originalException The original exception.
- */
- public EventException(Throwable originalException) {
- super(originalException);
- }
-
- /**
- * Constructor that chains another Exception or Error and also allows a message
- * to be specified.
- * @param exceptionMessage The exception message.
- * @param originalException The original excepton.
- */
- public EventException(String exceptionMessage, Throwable originalException) {
- super(exceptionMessage, originalException);
- }
-}
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/LoggerWrapper.java b/slf4j-ext/src/main/java/org/slf4j/ext/LoggerWrapper.java
index 392ddaf5..0c890fc9 100644
--- a/slf4j-ext/src/main/java/org/slf4j/ext/LoggerWrapper.java
+++ b/slf4j-ext/src/main/java/org/slf4j/ext/LoggerWrapper.java
@@ -26,8 +26,8 @@ package org.slf4j.ext;
import org.slf4j.Logger;
import org.slf4j.Marker;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MessageFormatter;
+//import org.slf4j.helpers.FormattingTuple;
+//import org.slf4j.helpers.MessageFormatter;
import org.slf4j.spi.LocationAwareLogger;
/**
@@ -40,8 +40,7 @@ import org.slf4j.spi.LocationAwareLogger;
public class LoggerWrapper implements Logger {
// To ensure consistency between two instances sharing the same name
- // (homonyms)
- // a LoggerWrapper should not contain any state beyond
+ // (homonyms) a LoggerWrapper should not contain any state beyond
// the Logger instance it wraps.
// Note that 'instanceofLAL' directly depends on Logger.
// fqcn depend on the caller, but its value would not be different
@@ -98,8 +97,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, format, new Object[] { arg }, null);
} else {
logger.trace(format, arg);
}
@@ -113,8 +111,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.trace(format, arg1, arg2);
}
@@ -128,8 +125,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.TRACE_INT, format, args, null);
} else {
logger.trace(format, args);
}
@@ -169,8 +165,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isTraceEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, format, new Object[] { arg }, null);
} else {
logger.trace(marker, format, arg);
}
@@ -183,8 +178,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isTraceEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.trace(marker, format, arg1, arg2);
}
@@ -197,8 +191,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isTraceEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.TRACE_INT, format, args, null);
} else {
logger.trace(marker, format, args);
}
@@ -253,8 +246,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, format, new Object[] { arg }, null);
} else {
logger.debug(format, arg);
}
@@ -268,8 +260,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.debug(format, arg1, arg2);
}
@@ -283,8 +274,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, ft.getMessage(), ft.getArgArray(), ft.getThrowable());
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.DEBUG_INT, format, argArray, null);
} else {
logger.debug(format, argArray);
}
@@ -324,8 +314,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isDebugEnabled(marker))
return;
if (instanceofLAL) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, ft.getMessage(), ft.getArgArray(), ft.getThrowable());
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, format, new Object[] { arg }, null);
} else {
logger.debug(marker, format, arg);
}
@@ -338,8 +327,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isDebugEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.debug(marker, format, arg1, arg2);
}
@@ -353,8 +341,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, ft.getMessage(), argArray, ft.getThrowable());
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.DEBUG_INT, format, argArray, null);
} else {
logger.debug(marker, format, argArray);
}
@@ -409,8 +396,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, format, new Object[] { arg }, null);
} else {
logger.info(format, arg);
}
@@ -424,8 +410,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.info(format, arg1, arg2);
}
@@ -439,8 +424,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.INFO_INT, format, args, null);
} else {
logger.info(format, args);
}
@@ -480,8 +464,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isInfoEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, format, new Object[] { arg }, null);
} else {
logger.info(marker, format, arg);
}
@@ -494,8 +477,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isInfoEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.info(marker, format, arg1, arg2);
}
@@ -508,8 +490,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isInfoEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.INFO_INT, format, args, null);
} else {
logger.info(marker, format, args);
}
@@ -561,8 +542,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, format, new Object[] { arg }, null);
} else {
logger.warn(format, arg);
}
@@ -576,8 +556,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.warn(format, arg1, arg2);
}
@@ -591,8 +570,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.WARN_INT, format, args, null);
} else {
logger.warn(format, args);
}
@@ -632,8 +610,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isWarnEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, format, new Object[] { arg }, null);
} else {
logger.warn(marker, format, arg);
}
@@ -646,8 +623,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isWarnEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.warn(marker, format, arg1, arg2);
}
@@ -660,8 +636,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isWarnEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.WARN_INT, format, args, null);
} else {
logger.warn(marker, format, args);
}
@@ -716,8 +691,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, format, new Object[] { arg }, null);
} else {
logger.error(format, arg);
}
@@ -731,8 +705,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.error(format, arg1, arg2);
}
@@ -746,8 +719,7 @@ public class LoggerWrapper implements Logger {
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(null, fqcn, LocationAwareLogger.ERROR_INT, format, args, null);
} else {
logger.error(format, args);
}
@@ -787,8 +759,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isErrorEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, new Object[] { arg }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, format, new Object[] { arg }, null);
} else {
logger.error(marker, format, arg);
}
@@ -801,8 +772,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isErrorEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.format(format, arg1, arg2).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, new Object[] { arg1, arg2 }, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, format, new Object[] { arg1, arg2 }, null);
} else {
logger.error(marker, format, arg1, arg2);
}
@@ -815,8 +785,7 @@ public class LoggerWrapper implements Logger {
if (!logger.isErrorEnabled(marker))
return;
if (instanceofLAL) {
- String formattedMessage = MessageFormatter.arrayFormat(format, args).getMessage();
- ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, formattedMessage, args, null);
+ ((LocationAwareLogger) logger).log(marker, fqcn, LocationAwareLogger.ERROR_INT, format, args, null);
} else {
logger.error(marker, format, args);
}
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/XLogger.java b/slf4j-ext/src/main/java/org/slf4j/ext/XLogger.java
index 06f01626..fc7543b6 100644
--- a/slf4j-ext/src/main/java/org/slf4j/ext/XLogger.java
+++ b/slf4j-ext/src/main/java/org/slf4j/ext/XLogger.java
@@ -96,21 +96,19 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Given an underlying logger, construct an XLogger
*
- * @param logger
- * underlying logger
+ * @param logger underlying logger
*/
public XLogger(Logger logger) {
// If class B extends A, assuming B does not override method x(), the caller
// of new B().x() is A and not B, see also
- // http://bugzilla.slf4j.org/show_bug.cgi?id=114
+ // http://jira.qos.ch/browse/SLF4J-105
super(logger, LoggerWrapper.class.getName());
}
/**
* Log method entry.
*
- * @param argArray
- * supplied parameters
+ * @param argArray supplied parameters
*/
public void entry(Object... argArray) {
if (instanceofLAL && logger.isTraceEnabled(ENTRY_MARKER)) {
@@ -137,8 +135,7 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Log method exit
*
- * @param result
- * The result of the method being exited
+ * @param result The result of the method being exited
*/
public <T> T exit(T result) {
if (instanceofLAL && logger.isTraceEnabled(ENTRY_MARKER)) {
@@ -151,8 +148,7 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Log an exception being thrown. The generated log event uses Level ERROR.
*
- * @param throwable
- * the exception being caught.
+ * @param throwable the exception being caught.
*/
public <T extends Throwable> T throwing(T throwable) {
if (instanceofLAL) {
@@ -164,10 +160,8 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Log an exception being thrown allowing the log level to be specified.
*
- * @param level
- * the logging level to use.
- * @param throwable
- * the exception being caught.
+ * @param level the logging level to use.
+ * @param throwable the exception being caught.
*/
public <T extends Throwable> T throwing(Level level, T throwable) {
if (instanceofLAL) {
@@ -179,8 +173,7 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Log an exception being caught. The generated log event uses Level ERROR.
*
- * @param throwable
- * the exception being caught.
+ * @param throwable the exception being caught.
*/
public void catching(Throwable throwable) {
if (instanceofLAL) {
@@ -191,10 +184,8 @@ public class XLogger extends LoggerWrapper implements Logger {
/**
* Log an exception being caught allowing the log level to be specified.
*
- * @param level
- * the logging level to use.
- * @param throwable
- * the exception being caught.
+ * @param level the logging level to use.
+ * @param throwable the exception being caught.
*/
public void catching(Level level, Throwable throwable) {
if (instanceofLAL) {
diff --git a/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java b/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
index 17c52674..5f4c1f26 100644
--- a/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
+++ b/slf4j-ext/src/main/java/org/slf4j/instrumentation/JavassistHelper.java
@@ -40,9 +40,9 @@ import javassist.bytecode.LocalVariableAttribute;
public class JavassistHelper {
/**
- * Create a javaassist source snippet which either is empty (for anything
- * which does not return a value) or a explanatory text around the $_
- * javaassist return value variable.
+ * Create a javassist source snippet which either is empty (for anything
+ * which does not return a value) or an explanatory text around the $_
+ * javassist return value variable.
*
* @param method
* descriptor of method
@@ -82,7 +82,7 @@ public class JavassistHelper {
}
/**
- * Return javaassist source snippet which lists all the parameters and their
+ * Return javassist source snippet which lists all the parameters and their
* values. If available the source names are extracted from the debug
* information and used, otherwise just a number is shown.
*
@@ -92,7 +92,7 @@ public class JavassistHelper {
*/
public static String getSignature(CtBehavior method) throws NotFoundException {
- CtClass parameterTypes[] = method.getParameterTypes();
+ CtClass[] parameterTypes = method.getParameterTypes();
CodeAttribute codeAttribute = method.getMethodInfo().getCodeAttribute();
diff --git a/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java b/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
index 09eff678..1ea44794 100644
--- a/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
+++ b/slf4j-ext/src/main/java/org/slf4j/instrumentation/LogTransformer.java
@@ -23,7 +23,7 @@
*
*/
/**
- *
+ *
*/
package org.slf4j.instrumentation;
@@ -46,28 +46,27 @@ import org.slf4j.helpers.MessageFormatter;
* <p>
* LogTransformer does the work of analyzing each class, and if appropriate add
* log statements to each method to allow logging entry/exit.
- * </p>
+ *
* <p>
* This class is based on the article <a href="http://today.java.net/pub/a/today/2008/04/24/add-logging-at-class-load-time-with-instrumentation.html"
* >Add Logging at Class Load Time with Java Instrumentation</a>.
- * </p>
+ *
*/
public class LogTransformer implements ClassFileTransformer {
/**
* Builder provides a flexible way of configuring some of many options on the
* parent class instead of providing many constructors.
- *
- * {@link http
- * ://rwhansen.blogspot.com/2007/07/theres-builder-pattern-that-joshua.html}
- *
+ *
+ * <a href="http://rwhansen.blogspot.com/2007/07/theres-builder-pattern-that-joshua.html">http://rwhansen.blogspot.com/2007/07/theres-builder-pattern-that-joshua.html</a>
+ *
*/
public static class Builder {
/**
* Build and return the LogTransformer corresponding to the options set in
* this Builder.
- *
+ *
* @return
*/
public LogTransformer build() {
@@ -81,8 +80,8 @@ public class LogTransformer implements ClassFileTransformer {
/**
* Should each method log entry (with parameters) and exit (with parameters
- * and returnvalue)?
- *
+ * and return value)?
+ *
* @param b
* value of flag
* @return
@@ -105,7 +104,7 @@ public class LogTransformer implements ClassFileTransformer {
/**
* Should LogTransformer be verbose in what it does? This currently list the
* names of the classes being processed.
- *
+ *
* @param b
* @return
*/
@@ -136,8 +135,8 @@ public class LogTransformer implements ClassFileTransformer {
}
}
- private String level;
- private String levelEnabled;
+ private final String level;
+ private final String levelEnabled;
private LogTransformer(Builder builder) {
String s = "WARNING: javassist not available on classpath for javaagent, log statements will not be added";
@@ -157,10 +156,10 @@ public class LogTransformer implements ClassFileTransformer {
this.levelEnabled = "is" + builder.level.substring(0, 1).toUpperCase() + builder.level.substring(1) + "Enabled";
}
- private boolean addEntryExit;
+ private final boolean addEntryExit;
// private boolean addVariableAssignment;
- private boolean verbose;
- private String[] ignore;
+ private final boolean verbose;
+ private final String[] ignore;
public byte[] transform(ClassLoader loader, String className, Class<?> clazz, ProtectionDomain domain, byte[] bytes) {
@@ -177,7 +176,7 @@ public class LogTransformer implements ClassFileTransformer {
* transform0 sees if the className starts with any of the namespaces to
* ignore, if so it is returned unchanged. Otherwise it is processed by
* doClass(...)
- *
+ *
* @param className
* @param clazz
* @param domain
@@ -188,8 +187,8 @@ public class LogTransformer implements ClassFileTransformer {
private byte[] transform0(String className, Class<?> clazz, ProtectionDomain domain, byte[] bytes) {
try {
- for (int i = 0; i < ignore.length; i++) {
- if (className.startsWith(ignore[i])) {
+ for (String s : ignore) {
+ if (className.startsWith(s)) {
return bytes;
}
}
@@ -227,7 +226,7 @@ public class LogTransformer implements ClassFileTransformer {
* defined have bodies, and a static final logger object is added with the
* name of this class as an argument, and each method then gets processed with
* doMethod(...) to have logger calls added.
- *
+ *
* @param name
* class name (slashes separate, not dots)
* @param clazz
@@ -264,9 +263,9 @@ public class LogTransformer implements ClassFileTransformer {
// instrumented too.
CtBehavior[] methods = cl.getDeclaredBehaviors();
- for (int i = 0; i < methods.length; i++) {
- if (methods[i].isEmpty() == false) {
- doMethod(methods[i]);
+ for (CtBehavior method : methods) {
+ if (method.isEmpty() == false) {
+ doMethod(method);
}
}
b = cl.toBytecode();
@@ -285,7 +284,7 @@ public class LogTransformer implements ClassFileTransformer {
/**
* process a single method - this means add entry/exit logging if requested.
* It is only called for methods with a body.
- *
+ *
* @param method
* method to work on
* @throws NotFoundException
@@ -310,4 +309,4 @@ public class LogTransformer implements ClassFileTransformer {
method.insertAfter(after);
}
}
-} \ No newline at end of file
+}
diff --git a/slf4j-ext/src/main/java/org/slf4j/instrumentation/ToStringHelper.java b/slf4j-ext/src/main/java/org/slf4j/instrumentation/ToStringHelper.java
index b20f5851..f479dab6 100644
--- a/slf4j-ext/src/main/java/org/slf4j/instrumentation/ToStringHelper.java
+++ b/slf4j-ext/src/main/java/org/slf4j/instrumentation/ToStringHelper.java
@@ -53,10 +53,10 @@ public class ToStringHelper {
* is needed, but unfortunately the runtime library does not contain a
* WeakHashSet class, so the behavior is emulated with a WeakHashmap with
* the class as the key, and a Long containing the value of
- * System.currentTimeMilis when an instance of the class failed to render.
+ * System.currentTimeMillis when an instance of the class failed to render.
*/
- final static Map<Class<?>, Object> unrenderableClasses = new WeakHashMap<Class<?>, Object>();
+ final static Map<Class<?>, Object> unrenderableClasses = new WeakHashMap<>();
/**
* Returns o.toString() unless it throws an exception (which causes it to be
@@ -84,7 +84,7 @@ public class ToStringHelper {
return o.toString();
}
} catch (Exception e) {
- Long now = new Long(System.currentTimeMillis());
+ Long now = Long.valueOf(System.currentTimeMillis());
System.err.println("Disabling exception throwing class " + objectClass.getName() + ", " + e.getMessage());
diff --git a/slf4j-ext/src/main/java/org/slf4j/instrumentation/package.html b/slf4j-ext/src/main/java/org/slf4j/instrumentation/package.html
index 76001498..6816e8f2 100644
--- a/slf4j-ext/src/main/java/org/slf4j/instrumentation/package.html
+++ b/slf4j-ext/src/main/java/org/slf4j/instrumentation/package.html
@@ -9,7 +9,7 @@
<body>
<p>Java instrumentation routines for SLF4J.</p>
-<p>Byte code instrumentation is an way to change behaviour of java
+<p>Byte code instrumentation is a way to change behaviour of java
classes at <i>load time</i>. This is done in-between the original byte
codes are retrieved and the class object is constructed by the class
loader. Currently this depends on the javassist library from JBoss
diff --git a/slf4j-ext/src/main/java/org/slf4j/profiler/Profiler.java b/slf4j-ext/src/main/java/org/slf4j/profiler/Profiler.java
index 56357373..a0ecf43b 100644
--- a/slf4j-ext/src/main/java/org/slf4j/profiler/Profiler.java
+++ b/slf4j-ext/src/main/java/org/slf4j/profiler/Profiler.java
@@ -57,7 +57,7 @@ public class Profiler implements TimeInstrument {
final String name;
final StopWatch globalStopWatch;
- List<TimeInstrument> childTimeInstrumentList = new ArrayList<TimeInstrument>();
+ List<TimeInstrument> childTimeInstrumentList = new ArrayList<>();
// optional field
ProfilerRegistry profilerRegistry;
@@ -209,12 +209,12 @@ public class Profiler implements TimeInstrument {
* @since 1.5.9
*/
public List<TimeInstrument> getCopyOfChildTimeInstruments() {
- List<TimeInstrument> copy = new ArrayList<TimeInstrument>(childTimeInstrumentList);
+ List<TimeInstrument> copy = new ArrayList<>(childTimeInstrumentList);
return copy;
}
/**
- * Return a copy of the global stopwath of this Profiler instance.
+ * Return a copy of the global stopwatch of this Profiler instance.
*
* @return a copy of this instance's global stop watch
* @since 1.5.9
diff --git a/slf4j-ext/src/main/java/org/slf4j/profiler/ProfilerRegistry.java b/slf4j-ext/src/main/java/org/slf4j/profiler/ProfilerRegistry.java
index 61fda75e..264ca493 100644
--- a/slf4j-ext/src/main/java/org/slf4j/profiler/ProfilerRegistry.java
+++ b/slf4j-ext/src/main/java/org/slf4j/profiler/ProfilerRegistry.java
@@ -34,9 +34,9 @@ import java.util.Map;
*/
public class ProfilerRegistry {
- private static final InheritableThreadLocal<ProfilerRegistry> inheritableThreadLocal = new InheritableThreadLocal<ProfilerRegistry>();
+ private static final InheritableThreadLocal<ProfilerRegistry> inheritableThreadLocal = new InheritableThreadLocal<>();
- Map<String, Profiler> profilerMap = new HashMap<String, Profiler>();
+ Map<String, Profiler> profilerMap = new HashMap<>();
public void put(Profiler profiler) {
put(profiler.getName(), profiler);
diff --git a/slf4j-ext/src/main/java/org/slf4j/profiler/StopWatch.java b/slf4j-ext/src/main/java/org/slf4j/profiler/StopWatch.java
index 9ae7d295..60488fc3 100644
--- a/slf4j-ext/src/main/java/org/slf4j/profiler/StopWatch.java
+++ b/slf4j-ext/src/main/java/org/slf4j/profiler/StopWatch.java
@@ -25,7 +25,7 @@
package org.slf4j.profiler;
/**
- * A very basic @{link TimeInstrument} which can be started and stopped
+ * A very basic {@link TimeInstrument} which can be started and stopped
* once and only once.
*
* @author Ceki G&uuml;lc&uuml;
diff --git a/slf4j-ext/src/main/java/org/slf4j/profiler/TimeInstrument.java b/slf4j-ext/src/main/java/org/slf4j/profiler/TimeInstrument.java
index de749df8..6024d46b 100644
--- a/slf4j-ext/src/main/java/org/slf4j/profiler/TimeInstrument.java
+++ b/slf4j-ext/src/main/java/org/slf4j/profiler/TimeInstrument.java
@@ -43,9 +43,9 @@ public interface TimeInstrument {
TimeInstrumentStatus getStatus();
/**
- * Start tis time instrument.
+ * Start this time instrument.
*
- * @param name
+ * @param name the name of this instrument
*/
void start(String name);
diff --git a/slf4j-ext/src/main/resources/META-INF/MANIFEST.MF b/slf4j-ext/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 3328a2cc..00000000
--- a/slf4j-ext/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,8 +0,0 @@
-Implementation-Title: slf4j-ext
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.ext
-Bundle-Name: slf4j-ext
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.profiler;version=${parsedVersion.osgiVersion}, org.slf4j.cal10n;version=${parsedVersion.osgiVersion}, org.slf4j.ext;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}, ch.qos.cal10n;version=${cal10n.version}
diff --git a/slf4j-ext/src/test/java/org/slf4j/NDCTest.java b/slf4j-ext/src/test/java/org/slf4j/NDCTest.java
index 33b02bb0..e25164ee 100644
--- a/slf4j-ext/src/test/java/org/slf4j/NDCTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/NDCTest.java
@@ -24,29 +24,31 @@
*/
package org.slf4j;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
-public class NDCTest extends TestCase {
+import org.junit.Before;
+import org.junit.Test;
- protected void setUp() throws Exception {
- super.setUp();
- MDC.clear();
- }
+public class NDCTest {
- protected void tearDown() throws Exception {
- super.tearDown();
+ @Before
+ public void setUp() throws Exception {
+ MDC.clear();
}
+ @Test
public void testEmpty() {
assertEquals("", NDC.pop());
}
+ @Test
public void testSmoke() {
NDC.push("a");
String result = NDC.pop();
assertEquals("a", result);
}
+ @Test
public void testSmoke2() {
NDC.push("a");
NDC.push("b");
diff --git a/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/LocLoggerTest.java b/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/LocLoggerTest.java
index 9254ad70..becab673 100644
--- a/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/LocLoggerTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/LocLoggerTest.java
@@ -24,11 +24,13 @@
*/
package org.slf4j.cal10n_dummy;
-import java.util.Locale;
+import static org.junit.Assert.assertEquals;
-import junit.framework.TestCase;
+import java.util.Locale;
import org.apache.log4j.spi.LoggingEvent;
+import org.junit.Before;
+import org.junit.Test;
import org.slf4j.cal10n.LocLogger;
import org.slf4j.cal10n.LocLoggerFactory;
import org.slf4j.dummyExt.ListAppender;
@@ -36,7 +38,7 @@ import org.slf4j.dummyExt.ListAppender;
import ch.qos.cal10n.IMessageConveyor;
import ch.qos.cal10n.MessageConveyor;
-public class LocLoggerTest extends TestCase {
+public class LocLoggerTest {
ListAppender listAppender;
org.apache.log4j.Logger log4jRoot;
@@ -46,13 +48,8 @@ public class LocLoggerTest extends TestCase {
final static String EXPECTED_FILE_NAME = "LocLoggerTest.java";
- public LocLoggerTest(String name) {
- super(name);
- }
-
+ @Before
public void setUp() throws Exception {
- super.setUp();
-
// start from a clean slate for each test
listAppender = new ListAppender();
@@ -67,10 +64,7 @@ public class LocLoggerTest extends TestCase {
assertEquals(EXPECTED_FILE_NAME, le.getLocationInformation().getFileName());
}
- public void tearDown() throws Exception {
- super.tearDown();
- }
-
+ @Test
public void testSmoke() {
LocLogger locLogger = llFactory_uk.getLocLogger(this.getClass());
locLogger.info(Months.JAN);
diff --git a/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/PackageTest.java b/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/PackageTest.java
index 88413ba9..f77207b0 100644
--- a/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/PackageTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/cal10n_dummy/PackageTest.java
@@ -24,13 +24,11 @@
*/
package org.slf4j.cal10n_dummy;
-import junit.framework.*;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
+import org.junit.runners.Suite.SuiteClasses;
-public class PackageTest extends TestCase {
-
- public static Test suite() {
- TestSuite suite = new TestSuite();
- suite.addTestSuite(LocLoggerTest.class);
- return suite;
- }
+@RunWith(Suite.class)
+@SuiteClasses({ LocLoggerTest.class })
+public class PackageTest {
}
diff --git a/slf4j-ext/src/test/java/org/slf4j/dummyExt/EventLoggerTest.java b/slf4j-ext/src/test/java/org/slf4j/dummyExt/EventLoggerTest.java
deleted file mode 100644
index f04aecb6..00000000
--- a/slf4j-ext/src/test/java/org/slf4j/dummyExt/EventLoggerTest.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.dummyExt;
-
-import java.util.Date;
-import java.util.Locale;
-import java.util.TimeZone;
-
-import junit.framework.TestCase;
-
-import org.apache.log4j.spi.LocationInfo;
-import org.apache.log4j.spi.LoggingEvent;
-import org.slf4j.MDC;
-import org.slf4j.ext.EventData;
-import org.slf4j.ext.EventLogger;
-
-public class EventLoggerTest extends TestCase {
-
- ListAppender listAppender;
- org.apache.log4j.Logger log4;
-
- final static String EXPECTED_FILE_NAME = "EventLoggerTest.java";
-
- public EventLoggerTest(String name) {
- super(name);
- }
-
- public void setUp() throws Exception {
- super.setUp();
-
- // start from a clean slate for each test
-
- listAppender = new ListAppender();
- listAppender.extractLocationInfo = true;
- org.apache.log4j.Logger eventLogger = org.apache.log4j.Logger.getLogger("EventLogger");
- eventLogger.addAppender(listAppender);
- eventLogger.setLevel(org.apache.log4j.Level.TRACE);
- eventLogger.setAdditivity(false);
- // Items that apply to any activity
- MDC.put("ipAddress", "192.168.1.110");
- MDC.put("login", "TestUSer");
- MDC.put("hostname", "localhost");
- MDC.put("productName", "SLF4J");
- MDC.put("locale", Locale.getDefault().getDisplayName());
- MDC.put("timezone", TimeZone.getDefault().getDisplayName());
-
- }
-
- public void tearDown() throws Exception {
- super.tearDown();
- MDC.clear();
- }
-
- void verify(LoggingEvent le, String expectedMsg) {
- assertEquals(expectedMsg, le.getMessage());
- assertEquals(EXPECTED_FILE_NAME, le.getLocationInformation().getFileName());
- }
-
- public void testEventLogger() {
- EventData data[] = new EventData[2];
- data[0] = new EventData();
- data[0].setEventType("Login");
- data[0].setEventId("1");
- data[0].setEventDateTime(new Date());
- data[0].put("Userid", "TestUser");
- EventLogger.logEvent(data[0]);
-
- data[1] = new EventData();
- data[1].setEventType("Update");
- data[1].setEventId("2");
- data[1].setEventDateTime(new Date());
- data[1].put("FileName", "/etc/hosts");
- EventLogger.logEvent(data[1]);
-
- assertEquals(2, listAppender.list.size());
- for (int i = 0; i < 2; ++i) {
- LoggingEvent event = listAppender.list.get(i);
- verify(event, data[i].toXML());
- LocationInfo li = event.getLocationInformation();
- assertEquals(this.getClass().getName(), li.getClassName());
- assertEquals(event.getMDC("hostname"), "localhost");
- }
- }
-} \ No newline at end of file
diff --git a/slf4j-ext/src/test/java/org/slf4j/dummyExt/ListAppender.java b/slf4j-ext/src/test/java/org/slf4j/dummyExt/ListAppender.java
index bb7f2f2b..16194f77 100644
--- a/slf4j-ext/src/test/java/org/slf4j/dummyExt/ListAppender.java
+++ b/slf4j-ext/src/test/java/org/slf4j/dummyExt/ListAppender.java
@@ -32,7 +32,7 @@ import org.apache.log4j.spi.LoggingEvent;
public class ListAppender extends AppenderSkeleton {
- public List<LoggingEvent> list = new ArrayList<LoggingEvent>();
+ public final List<LoggingEvent> list = new ArrayList<>();
public boolean extractLocationInfo = false;
diff --git a/slf4j-ext/src/test/java/org/slf4j/dummyExt/PackageTest.java b/slf4j-ext/src/test/java/org/slf4j/dummyExt/PackageTest.java
index cee15d38..219d4357 100644
--- a/slf4j-ext/src/test/java/org/slf4j/dummyExt/PackageTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/dummyExt/PackageTest.java
@@ -24,15 +24,11 @@
*/
package org.slf4j.dummyExt;
-import junit.framework.*;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
+import org.junit.runners.Suite.SuiteClasses;
-public class PackageTest extends TestCase {
-
- public static Test suite() {
- TestSuite suite = new TestSuite();
- suite.addTestSuite(MDCStrLookupTest.class);
- suite.addTestSuite(XLoggerTest.class);
- suite.addTestSuite(EventLoggerTest.class);
- return suite;
- }
+@RunWith(Suite.class)
+@SuiteClasses({ XLoggerTest.class })
+public class PackageTest {
}
diff --git a/slf4j-ext/src/test/java/org/slf4j/dummyExt/XLoggerTest.java b/slf4j-ext/src/test/java/org/slf4j/dummyExt/XLoggerTest.java
index 33940cfc..16c1bc40 100644
--- a/slf4j-ext/src/test/java/org/slf4j/dummyExt/XLoggerTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/dummyExt/XLoggerTest.java
@@ -24,26 +24,24 @@
*/
package org.slf4j.dummyExt;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
import org.apache.log4j.spi.LocationInfo;
import org.apache.log4j.spi.LoggingEvent;
+import org.junit.Before;
+import org.junit.Test;
import org.slf4j.ext.XLogger;
import org.slf4j.ext.XLoggerFactory;
-public class XLoggerTest extends TestCase {
+public class XLoggerTest {
ListAppender listAppender;
org.apache.log4j.Logger log4jRoot;
final static String EXPECTED_FILE_NAME = "XLoggerTest.java";
- public XLoggerTest(String name) {
- super(name);
- }
-
+ @Before
public void setUp() throws Exception {
- super.setUp();
// start from a clean slate for each test
@@ -54,10 +52,6 @@ public class XLoggerTest extends TestCase {
log4jRoot.setLevel(org.apache.log4j.Level.TRACE);
}
- public void tearDown() throws Exception {
- super.tearDown();
- }
-
void verify(LoggingEvent le, String expectedMsg) {
assertEquals(expectedMsg, le.getMessage());
assertEquals(EXPECTED_FILE_NAME, le.getLocationInformation().getFileName());
@@ -74,6 +68,7 @@ public class XLoggerTest extends TestCase {
assertEquals(le.getLevel().toString(), level.toString());
}
+ @Test
public void testEntering() {
XLogger logger = XLoggerFactory.getXLogger("UnitTest");
logger.entry();
@@ -84,11 +79,12 @@ public class XLoggerTest extends TestCase {
logger.entry("a", "b", "c", "d", "e", "f");
assertEquals(6, listAppender.list.size());
- verify((LoggingEvent) listAppender.list.get(0), "entry");
- verify((LoggingEvent) listAppender.list.get(1), "entry with (1)");
- verify((LoggingEvent) listAppender.list.get(2), "entry with (test)");
+ verify(listAppender.list.get(0), "entry");
+ verify(listAppender.list.get(1), "entry with (1)");
+ verify(listAppender.list.get(2), "entry with (test)");
}
+ @Test
public void testExiting() {
XLogger logger = XLoggerFactory.getXLogger("UnitTest");
logger.exit();
@@ -96,22 +92,24 @@ public class XLoggerTest extends TestCase {
assertEquals(Boolean.FALSE, logger.exit(false));
assertEquals(3, listAppender.list.size());
- verify((LoggingEvent) listAppender.list.get(0), "exit");
- verify((LoggingEvent) listAppender.list.get(1), "exit with (0)");
- verify((LoggingEvent) listAppender.list.get(2), "exit with (false)");
+ verify(listAppender.list.get(0), "exit");
+ verify(listAppender.list.get(1), "exit with (0)");
+ verify(listAppender.list.get(2), "exit with (false)");
}
+ @Test
public void testThrowing() {
XLogger logger = XLoggerFactory.getXLogger("UnitTest");
Throwable t = new UnsupportedOperationException("Test");
assertEquals(t, logger.throwing(t));
assertEquals(t, logger.throwing(XLogger.Level.DEBUG, t));
assertEquals(2, listAppender.list.size());
- verifyWithException((LoggingEvent) listAppender.list.get(0), "throwing", t);
- LoggingEvent event = (LoggingEvent) listAppender.list.get(1);
+ verifyWithException(listAppender.list.get(0), "throwing", t);
+ LoggingEvent event = listAppender.list.get(1);
verifyWithLevelAndException(event, XLogger.Level.DEBUG, "throwing", t);
}
+ @Test
public void testCaught() {
XLogger logger = XLoggerFactory.getXLogger("UnitTest");
long x = 5;
@@ -124,11 +122,13 @@ public class XLoggerTest extends TestCase {
logger.catching(ex);
logger.catching(XLogger.Level.DEBUG, ex);
}
- verifyWithException((LoggingEvent) listAppender.list.get(0), "catching", t);
- verifyWithLevelAndException((LoggingEvent) listAppender.list.get(1), XLogger.Level.DEBUG, "catching", t);
+ verifyWithException(listAppender.list.get(0), "catching", t);
+ verifyWithLevelAndException(listAppender.list.get(1), XLogger.Level.DEBUG, "catching", t);
}
- // See http://bugzilla.slf4j.org/show_bug.cgi?id=114
+ // See http://jira.qos.ch/browse/SLF4J-105
+ // formerly http://bugzilla.slf4j.org/show_bug.cgi?id=114
+ @Test
public void testLocationExtraction_Bug114() {
XLogger logger = XLoggerFactory.getXLogger("UnitTest");
int line = 135; // requires update if line numbers change
@@ -150,6 +150,17 @@ public class XLoggerTest extends TestCase {
assertEquals(this.getClass().getName(), li.getClassName());
assertEquals("" + (line + 1), li.getLineNumber());
}
-
}
+
+ @Test
+ public void testNoDoubleSubstitution_Bug421() {
+ XLogger logger = XLoggerFactory.getXLogger("UnitTest");
+ logger.error("{},{}", "foo", "[{}]");
+ verify(listAppender.list.get(0), "foo,[{}]");
+
+ logger.error("{},{}", "[{}]", "foo");
+ verify(listAppender.list.get(1), "[{}],foo");
+ }
+
+
}
diff --git a/slf4j-ext/src/test/java/org/slf4j/instrumentation/ToStringHelperTest.java b/slf4j-ext/src/test/java/org/slf4j/instrumentation/ToStringHelperTest.java
index c21b0b83..81723c0c 100644
--- a/slf4j-ext/src/test/java/org/slf4j/instrumentation/ToStringHelperTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/instrumentation/ToStringHelperTest.java
@@ -24,10 +24,13 @@
*/
package org.slf4j.instrumentation;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
-public class ToStringHelperTest extends TestCase {
+import org.junit.Test;
+public class ToStringHelperTest {
+
+ @Test
public void testRenderer() {
assertEquals("", "null", ToStringHelper.render(null));
assertEquals("", "a", ToStringHelper.render("a"));
diff --git a/slf4j-ext/src/test/java/org/slf4j/profiler/PackageTest.java b/slf4j-ext/src/test/java/org/slf4j/profiler/PackageTest.java
index 9a634625..40b8365c 100644
--- a/slf4j-ext/src/test/java/org/slf4j/profiler/PackageTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/profiler/PackageTest.java
@@ -24,14 +24,12 @@
*/
package org.slf4j.profiler;
-import junit.framework.*;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
+import org.junit.runners.Suite.SuiteClasses;
-public class PackageTest extends TestCase {
+@RunWith(Suite.class)
+@SuiteClasses({ UtilTest.class, ProfilerTest.class })
+public class PackageTest {
- public static Test suite() {
- TestSuite suite = new TestSuite();
- suite.addTestSuite(UtilTest.class);
- suite.addTestSuite(ProfilerTest.class);
- return suite;
- }
} \ No newline at end of file
diff --git a/slf4j-ext/src/test/java/org/slf4j/profiler/ProfilerTest.java b/slf4j-ext/src/test/java/org/slf4j/profiler/ProfilerTest.java
index 2ea552be..fef09a53 100644
--- a/slf4j-ext/src/test/java/org/slf4j/profiler/ProfilerTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/profiler/ProfilerTest.java
@@ -24,19 +24,19 @@
*/
package org.slf4j.profiler;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
+import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-public class ProfilerTest extends TestCase {
+public class ProfilerTest {
Logger logger = LoggerFactory.getLogger(ProfilerTest.class);
- public void setUp() throws Exception {
- super.setUp();
- }
-
+ @Test
public void testSmoke() {
Profiler profiler = new Profiler("SMOKE");
profiler.stop();
@@ -49,6 +49,7 @@ public class ProfilerTest extends TestCase {
assertNull(profiler.getLastTimeInstrument());
}
+ @Test
public void testBasicProfiling() {
Profiler profiler = new Profiler("BAS");
@@ -80,6 +81,7 @@ public class ProfilerTest extends TestCase {
// |-- Total elapsed time [subtask] 7.321 milliseconds.
// |-- elapsed time [doZ] 3.211 milliseconds.
// |-- Total elapsed time [BAS] 30.317 milliseconds.
+ @Test
public void testNestedProfiling() {
Profiler profiler = new Profiler("BAS");
diff --git a/slf4j-ext/src/test/java/org/slf4j/profiler/SortAndPruneComposites.java b/slf4j-ext/src/test/java/org/slf4j/profiler/SortAndPruneComposites.java
index 867bb60f..b6e15088 100644
--- a/slf4j-ext/src/test/java/org/slf4j/profiler/SortAndPruneComposites.java
+++ b/slf4j-ext/src/test/java/org/slf4j/profiler/SortAndPruneComposites.java
@@ -50,7 +50,7 @@ public class SortAndPruneComposites {
int[] sortedArray = sort();
// start a new stopwatch called PRUNE_COMPOSITES
sortProfiler.start("PRUNE_COMPOSITES");
- int result[] = pruneComposites(sortedArray);
+ int[] result = pruneComposites(sortedArray);
return result;
}
@@ -63,7 +63,7 @@ public class SortAndPruneComposites {
}
int[] pruneComposites(int[] sortedArray) {
- ArrayList<Integer> primesArray = new ArrayList<Integer>();
+ ArrayList<Integer> primesArray = new ArrayList<>();
for (int i = 0; i < originalArrrayLength; i++) {
int n = sortedArray[i];
if (isPrime(n)) {
diff --git a/slf4j-ext/src/test/java/org/slf4j/profiler/UtilTest.java b/slf4j-ext/src/test/java/org/slf4j/profiler/UtilTest.java
index 601d6fb0..fc302518 100644
--- a/slf4j-ext/src/test/java/org/slf4j/profiler/UtilTest.java
+++ b/slf4j-ext/src/test/java/org/slf4j/profiler/UtilTest.java
@@ -24,22 +24,13 @@
*/
package org.slf4j.profiler;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertEquals;
-public class UtilTest extends TestCase {
+import org.junit.Test;
- public UtilTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- }
+public class UtilTest {
+ @Test
public void testSelectDurationUnitForDisplay() throws InterruptedException {
assertEquals(DurationUnit.NANOSECOND, Util.selectDurationUnitForDisplay(10));
assertEquals(DurationUnit.NANOSECOND, Util.selectDurationUnitForDisplay(9 * Util.NANOS_IN_ONE_MICROSECOND));
diff --git a/slf4j-jcl/pom.xml b/slf4j-jcl/pom.xml
deleted file mode 100755
index 48216181..00000000
--- a/slf4j-jcl/pom.xml
+++ /dev/null
@@ -1,53 +0,0 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-
- <modelVersion>4.0.0</modelVersion>
-
- <parent>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
- </parent>
-
- <artifactId>slf4j-jcl</artifactId>
- <packaging>jar</packaging>
- <name>SLF4J JCL Binding</name>
- <description>SLF4J JCL Binding</description>
-
- <url>http://www.slf4j.org</url>
-
- <dependencies>
- <dependency>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-api</artifactId>
- </dependency>
-
- <dependency>
- <groupId>commons-logging</groupId>
- <artifactId>commons-logging</artifactId>
- <version>1.1.1</version>
- </dependency>
-
- </dependencies>
-
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
-
- </plugins>
- </build>
-
-</project> \ No newline at end of file
diff --git a/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerAdapter.java b/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerAdapter.java
deleted file mode 100644
index ad075208..00000000
--- a/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerAdapter.java
+++ /dev/null
@@ -1,531 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-
-package org.slf4j.impl;
-
-import org.apache.commons.logging.Log;
-import org.slf4j.Logger;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MarkerIgnoringBase;
-import org.slf4j.helpers.MessageFormatter;
-
-/**
- * A wrapper over {@link org.apache.commons.logging.Log
- * org.apache.commons.logging.Log} in conformance with the {@link Logger}
- * interface.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public final class JCLLoggerAdapter extends MarkerIgnoringBase {
-
- private static final long serialVersionUID = 4141593417490482209L;
- final Log log;
-
- // WARN: JCLLoggerAdapter constructor should have only package access so
- // that only JCLLoggerFactory be able to create one.
- JCLLoggerAdapter(Log log, String name) {
- this.log = log;
- this.name = name;
- }
-
- /**
- * Delegates to the {@link Log#isTraceEnabled} method of the underlying
- * {@link Log} instance.
- */
- public boolean isTraceEnabled() {
- return log.isTraceEnabled();
- }
-
- //
-
- /**
- * Delegates to the {@link Log#trace(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * @param msg - the message object to be logged
- */
- public void trace(String msg) {
- log.trace(msg);
- }
-
- /**
- * Delegates to the {@link Log#trace(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level TRACE.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void trace(String format, Object arg) {
- if (log.isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log.trace(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#trace(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level TRACE.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void trace(String format, Object arg1, Object arg2) {
- if (log.isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log.trace(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#trace(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level TRACE.
- * </p>
- *
- * @param format the format string
- * @param arguments a list of 3 or more arguments
- */
- public void trace(String format, Object... arguments) {
- if (log.isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log.trace(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#trace(java.lang.Object, java.lang.Throwable)} method of
- * the underlying {@link Log} instance.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void trace(String msg, Throwable t) {
- log.trace(msg, t);
- }
-
- /**
- * Delegates to the {@link Log#isDebugEnabled} method of the underlying
- * {@link Log} instance.
- */
- public boolean isDebugEnabled() {
- return log.isDebugEnabled();
- }
-
- //
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * @param msg - the message object to be logged
- */
- public void debug(String msg) {
- log.debug(msg);
- }
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level DEBUG.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void debug(String format, Object arg) {
- if (log.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log.debug(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level DEBUG.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void debug(String format, Object arg1, Object arg2) {
- if (log.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log.debug(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level DEBUG.
- * </p>
- *
- * @param format the format string
- * @param arguments a list of 3 or more arguments
- */
- public void debug(String format, Object... arguments) {
- if (log.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log.debug(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object, java.lang.Throwable)} method of
- * the underlying {@link Log} instance.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void debug(String msg, Throwable t) {
- log.debug(msg, t);
- }
-
- /**
- * Delegates to the {@link Log#isInfoEnabled} method of the underlying
- * {@link Log} instance.
- */
- public boolean isInfoEnabled() {
- return log.isInfoEnabled();
- }
-
- /**
- * Delegates to the {@link Log#debug(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * @param msg - the message object to be logged
- */
- public void info(String msg) {
- log.info(msg);
- }
-
- /**
- * Delegates to the {@link Log#info(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level INFO.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
-
- public void info(String format, Object arg) {
- if (log.isInfoEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log.info(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#info(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level INFO.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void info(String format, Object arg1, Object arg2) {
- if (log.isInfoEnabled()) {
-
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log.info(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#info(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level INFO.
- * </p>
- *
- * @param format the format string
- * @param arguments a list of 3 or more arguments
- */
- public void info(String format, Object... arguments) {
- if (log.isInfoEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log.info(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#info(java.lang.Object, java.lang.Throwable)} method of
- * the underlying {@link Log} instance.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void info(String msg, Throwable t) {
- log.info(msg, t);
- }
-
- /**
- * Delegates to the {@link Log#isWarnEnabled} method of the underlying
- * {@link Log} instance.
- */
- public boolean isWarnEnabled() {
- return log.isWarnEnabled();
- }
-
- /**
- * Delegates to the {@link Log#warn(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * @param msg - the message object to be logged
- */
- public void warn(String msg) {
- log.warn(msg);
- }
-
- /**
- * Delegates to the {@link Log#warn(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level WARN.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void warn(String format, Object arg) {
- if (log.isWarnEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log.warn(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#warn(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level WARN.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void warn(String format, Object arg1, Object arg2) {
- if (log.isWarnEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log.warn(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#warn(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level WARN.
- * </p>
- *
- * @param format the format string
- * @param arguments a list of 3 or more arguments
- */
- public void warn(String format, Object... arguments) {
- if (log.isWarnEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log.warn(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#warn(java.lang.Object, java.lang.Throwable)} method of
- * the underlying {@link Log} instance.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
-
- public void warn(String msg, Throwable t) {
- log.warn(msg, t);
- }
-
- /**
- * Delegates to the {@link Log#isErrorEnabled} method of the underlying
- * {@link Log} instance.
- */
- public boolean isErrorEnabled() {
- return log.isErrorEnabled();
- }
-
- /**
- * Delegates to the {@link Log#error(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * @param msg - the message object to be logged
- */
- public void error(String msg) {
- log.error(msg);
- }
-
- /**
- * Delegates to the {@link Log#error(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level ERROR.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void error(String format, Object arg) {
- if (log.isErrorEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log.error(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#error(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level ERROR.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void error(String format, Object arg1, Object arg2) {
- if (log.isErrorEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log.error(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#error(java.lang.Object)} method of the underlying
- * {@link Log} instance.
- *
- * <p>
- * However, this form avoids superfluous object creation when the logger is disabled
- * for level ERROR.
- * </p>
- *
- * @param format the format string
- * @param arguments a list of 3 or more arguments
- */
- public void error(String format, Object... arguments) {
- if (log.isErrorEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log.error(ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Delegates to the {@link Log#error(java.lang.Object, java.lang.Throwable)} method of
- * the underlying {@link Log} instance.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
-
- public void error(String msg, Throwable t) {
- log.error(msg, t);
- }
-
-}
diff --git a/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerFactory.java b/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerFactory.java
deleted file mode 100644
index 77ea88ec..00000000
--- a/slf4j-jcl/src/main/java/org/slf4j/impl/JCLLoggerFactory.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
-
-import org.apache.commons.logging.LogFactory;
-import org.slf4j.ILoggerFactory;
-import org.slf4j.Logger;
-import org.slf4j.helpers.Util;
-
-/**
- * JCLLoggerFactory is an implementation of {@link ILoggerFactory} returning the
- * appropriately named {@link JCLLoggerAdapter} instance.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class JCLLoggerFactory implements ILoggerFactory {
-
- private static final String JCL_DELEGATION_LOOP_URL = "http://www.slf4j.org/codes.html#jclDelegationLoop";
-
- // check for delegation loops
- static {
- try {
- Class.forName("org.apache.commons.logging.impl.SLF4JLogFactory");
- String part1 = "Detected both jcl-over-slf4j.jar AND slf4j-jcl.jar on the class path, preempting StackOverflowError. ";
- String part2 = "See also " + JCL_DELEGATION_LOOP_URL + " for more details.";
-
- Util.report(part1);
- Util.report(part2);
- throw new IllegalStateException(part1 + part2);
- } catch (ClassNotFoundException e) {
- // this is the good case
- }
- }
-
- // key: name (String), value: a JCLLoggerAdapter;
- ConcurrentMap<String, Logger> loggerMap;
-
- public JCLLoggerFactory() {
- loggerMap = new ConcurrentHashMap<String, Logger>();
- }
-
- /*
- * (non-Javadoc)
- *
- * @see org.slf4j.ILoggerFactory#getLogger(java.lang.String)
- */
- public Logger getLogger(String name) {
- Logger slf4jLogger = loggerMap.get(name);
- if (slf4jLogger != null) {
- return slf4jLogger;
- } else {
- org.apache.commons.logging.Log jclLogger = LogFactory.getLog(name);
- Logger newInstance = new JCLLoggerAdapter(jclLogger, name);
- Logger oldInstance = loggerMap.putIfAbsent(name, newInstance);
- return oldInstance == null ? newInstance : oldInstance;
- }
- }
-}
diff --git a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-jcl/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index 580770db..00000000
--- a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Version tag used to check compatibility. The value of this field is
- * modified with each release.
- */
-
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99";
-
- // Binding specific code:
- private static final String loggerFactoryClassStr = JCLLoggerFactory.class.getName();
-
- /**
- * The ILoggerFactory instance returned by the {@link #getLoggerFactory}
- * method should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- // Binding specific code:
- loggerFactory = new JCLLoggerFactory();
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-jcl/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 1d255230..00000000
--- a/slf4j-jcl/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-
-}
diff --git a/slf4j-jcl/src/main/resources/META-INF/MANIFEST.MF b/slf4j-jcl/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index a9ee90ef..00000000
--- a/slf4j-jcl/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,10 +0,0 @@
-Implementation-Title: slf4j-jcl
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.jcl
-Bundle-Name: slf4j-jcl
-Bundle-Vendor: SLF4J.ORG
-Require-Bundle: slf4j.api
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}, org.apache.commons.logging
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-jcl/src/test/java/org/slf4j/InvocationTest.java b/slf4j-jcl/src/test/java/org/slf4j/InvocationTest.java
deleted file mode 100644
index a7035153..00000000
--- a/slf4j-jcl/src/test/java/org/slf4j/InvocationTest.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j;
-
-import java.util.logging.Level;
-
-import junit.framework.TestCase;
-
-/**
- * Test whether invoking the SLF4J API causes problems or not.
- *
- * @author Ceki Gulcu
- *
- */
-public class InvocationTest extends TestCase {
-
- Level oldLevel;
- java.util.logging.Logger root = java.util.logging.Logger.getLogger("");
-
- public InvocationTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- oldLevel = root.getLevel();
- root.setLevel(Level.OFF);
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- root.setLevel(oldLevel);
- }
-
- public void test1() {
- Logger logger = LoggerFactory.getLogger("test1");
- logger.debug("Hello world.");
- }
-
- public void test2() {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
- Exception e = new Exception("This is a test exception.");
- Logger logger = LoggerFactory.getLogger("test2");
-
- logger.debug("Hello world 1.");
- logger.debug("Hello world {}", i1);
- logger.debug("val={} val={}", i1, i2);
- logger.debug("val={} val={} val={}", new Object[] { i1, i2, i3 });
-
- logger.debug("Hello world 2", e);
- logger.info("Hello world 2.");
-
- logger.warn("Hello world 3.");
- logger.warn("Hello world 3", e);
-
- logger.error("Hello world 4.");
- logger.error("Hello world {}", new Integer(3));
- logger.error("Hello world 4.", e);
- }
-
- public void testNull() {
- Logger logger = LoggerFactory.getLogger("testNull");
- logger.debug(null);
- logger.info(null);
- logger.warn(null);
- logger.error(null);
-
- Exception e = new Exception("This is a test exception.");
- logger.debug(null, e);
- logger.info(null, e);
- logger.warn(null, e);
- logger.error(null, e);
- }
-
- public void testMarker() {
- Logger logger = LoggerFactory.getLogger("testMarker");
- Marker blue = MarkerFactory.getMarker("BLUE");
- logger.debug(blue, "hello");
- logger.info(blue, "hello");
- logger.warn(blue, "hello");
- logger.error(blue, "hello");
-
- logger.debug(blue, "hello {}", "world");
- logger.info(blue, "hello {}", "world");
- logger.warn(blue, "hello {}", "world");
- logger.error(blue, "hello {}", "world");
-
- logger.debug(blue, "hello {} and {} ", "world", "universe");
- logger.info(blue, "hello {} and {} ", "world", "universe");
- logger.warn(blue, "hello {} and {} ", "world", "universe");
- logger.error(blue, "hello {} and {} ", "world", "universe");
- }
-
- public void testMDC() {
- MDC.put("k", "v");
- assertNull(MDC.get("k"));
- MDC.remove("k");
- assertNull(MDC.get("k"));
- MDC.clear();
- }
-}
diff --git a/slf4j-jdk-platform-logging/LICENSE.txt b/slf4j-jdk-platform-logging/LICENSE.txt
new file mode 100644
index 00000000..1a3d0532
--- /dev/null
+++ b/slf4j-jdk-platform-logging/LICENSE.txt
@@ -0,0 +1,24 @@
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
+All rights reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+
+
diff --git a/slf4j-jdk-platform-logging/pom.xml b/slf4j-jdk-platform-logging/pom.xml
new file mode 100644
index 00000000..116ca976
--- /dev/null
+++ b/slf4j-jdk-platform-logging/pom.xml
@@ -0,0 +1,85 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <artifactId>slf4j-parent</artifactId>
+ <groupId>org.slf4j</groupId>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
+ </parent>
+
+ <artifactId>slf4j-jdk-platform-logging</artifactId>
+ <packaging>jar</packaging>
+ <name>SLF4J JDK Platform Logging Integration</name>
+ <description>Integrated SLF4J with the Platform Logging API added by JEP 264 in Java 9</description>
+
+ <url>https://www.slf4j.org</url>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-simple</artifactId>
+ <scope>test</scope>
+ </dependency>
+
+ </dependencies>
+
+ <build>
+ <plugins>
+ <!-- target Java 9+ -->
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <version>${maven-compiler-plugin.version}</version>
+ <executions>
+ <execution>
+ <id>default-compile</id>
+ <goals>
+ <goal>compile</goal>
+ </goals>
+ <configuration>
+ <source>9</source>
+ <target>9</target>
+ <release>9</release>
+ </configuration>
+ </execution>
+ <execution>
+ <id>default-testCompile</id>
+ <goals>
+ <goal>testCompile</goal>
+ </goals>
+ <configuration>
+ <source>9</source>
+ <target>9</target>
+ <release>9</release>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <version>${maven-surefire-plugin.version}</version>
+ <configuration>
+ <forkCount>1</forkCount>
+ <reuseForks>false</reuseForks>
+ <reportFormat>plain</reportFormat>
+ <trimStackTrace>false</trimStackTrace>
+ </configuration>
+ </plugin>
+
+
+ </plugins>
+ </build>
+
+</project>
diff --git a/slf4j-jdk-platform-logging/src/main/java/module-info.java b/slf4j-jdk-platform-logging/src/main/java/module-info.java
new file mode 100644
index 00000000..271ecb20
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/main/java/module-info.java
@@ -0,0 +1,28 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+module org.slf4j.jdk.platform.logging {
+ requires org.slf4j;
+ provides java.lang.System.LoggerFinder with org.slf4j.jdk.platform.logging.SLF4JSystemLoggerFinder;
+}
diff --git a/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLogger.java b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLogger.java
new file mode 100644
index 00000000..194436d7
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLogger.java
@@ -0,0 +1,181 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jdk.platform.logging;
+
+import static java.util.Objects.requireNonNull;
+
+import java.text.MessageFormat;
+import java.util.MissingResourceException;
+import java.util.ResourceBundle;
+
+import org.slf4j.Logger;
+import org.slf4j.helpers.Reporter;
+import org.slf4j.spi.CallerBoundaryAware;
+import org.slf4j.spi.LoggingEventBuilder;
+
+/**
+ * Adapts {@link Logger} to {@link System.Logger}.
+ * @since 2.0.0
+ */
+class SLF4JPlatformLogger implements System.Logger {
+
+ static private final String PRESUMED_CALLER_BOUNDARY = System.Logger.class.getName();
+
+ private final Logger slf4jLogger;
+
+ public SLF4JPlatformLogger(Logger logger) {
+ this.slf4jLogger = requireNonNull(logger);
+ }
+
+ @Override
+ public String getName() {
+ return slf4jLogger.getName();
+ }
+
+ // The fact that non loggable levels (in java.lang.System.Logger.Level)
+ // such as ALL and OFF leak into the public interface is quite a pity.
+
+ @Override
+ public boolean isLoggable(Level jplLevel) {
+ if (jplLevel == Level.ALL)
+ return true;
+ if (jplLevel == Level.OFF)
+ return true;
+
+ org.slf4j.event.Level slf4jLevel = jplLevelToSLF4JLevel(jplLevel);
+
+ return slf4jLogger.isEnabledForLevel(slf4jLevel);
+ }
+
+
+ /**
+ * Transform a {@link Level} to {@link org.slf4j.event.Level}.
+ *
+ * This method assumes that Level.ALL or Level.OFF never reach this method.
+ *
+ * @param jplLevel
+ * @return
+ */
+ private org.slf4j.event.Level jplLevelToSLF4JLevel(Level jplLevel) {
+ switch (jplLevel) {
+ case TRACE:
+ return org.slf4j.event.Level.TRACE;
+ case DEBUG:
+ return org.slf4j.event.Level.DEBUG;
+ case INFO:
+ return org.slf4j.event.Level.INFO;
+ case WARNING:
+ return org.slf4j.event.Level.WARN;
+ case ERROR:
+ return org.slf4j.event.Level.ERROR;
+ default:
+ reportUnknownLevel(jplLevel);
+ return null;
+ }
+ }
+
+ @Override
+ public void log(Level jplLevel, ResourceBundle bundle, String msg, Throwable thrown) {
+ log(jplLevel, bundle, msg, thrown, (Object[]) null);
+ }
+
+ @Override
+ public void log(Level jplLevel, ResourceBundle bundle, String format, Object... params) {
+ log(jplLevel, bundle, format, null, params);
+ }
+
+ /**
+ * Single point of processing taking all possible parameters.
+ *
+ * @param jplLevel
+ * @param bundle
+ * @param msg
+ * @param thrown
+ * @param params
+ */
+ private void log(Level jplLevel, ResourceBundle bundle, String msg, Throwable thrown, Object... params) {
+ if (jplLevel == Level.OFF)
+ return;
+
+ if (jplLevel == Level.ALL) {
+ performLog(org.slf4j.event.Level.TRACE, bundle, msg, thrown, params);
+ return;
+ }
+
+ org.slf4j.event.Level slf4jLevel = jplLevelToSLF4JLevel(jplLevel);
+ boolean isEnabled = slf4jLogger.isEnabledForLevel(slf4jLevel);
+
+ if (isEnabled) {
+ performLog(slf4jLevel, bundle, msg, thrown, params);
+ }
+ }
+
+ private void performLog(org.slf4j.event.Level slf4jLevel, ResourceBundle bundle, String msg, Throwable thrown, Object... params) {
+ String message = getResourceStringOrMessage(bundle, msg);
+ LoggingEventBuilder leb = slf4jLogger.makeLoggingEventBuilder(slf4jLevel);
+ if (thrown != null) {
+ leb = leb.setCause(thrown);
+ }
+ if (params != null && params.length > 0) {
+ // add the arguments to the logging event for possible processing by the backend
+ for (Object p : params) {
+ leb = leb.addArgument(p);
+ }
+ // The JDK uses a different formatting convention. We must invoke it now.
+ message = MessageFormat.format(message, params);
+ }
+ if (leb instanceof CallerBoundaryAware) {
+ CallerBoundaryAware cba = (CallerBoundaryAware) leb;
+ cba.setCallerBoundary(PRESUMED_CALLER_BOUNDARY);
+ }
+ leb.log(message);
+ }
+
+ private void reportUnknownLevel(Level jplLevel) {
+ String message = "Unknown log level [" + jplLevel + "]";
+ IllegalArgumentException iae = new IllegalArgumentException(message);
+ Reporter.error("Unsupported log level", iae);
+ }
+
+ private static String getResourceStringOrMessage(ResourceBundle bundle, String msg) {
+ if (bundle == null || msg == null)
+ return msg;
+ // ResourceBundle::getString throws:
+ //
+ // * NullPointerException for null keys
+ // * ClassCastException if the message is no string
+ // * MissingResourceException if there is no message for the key
+ //
+ // Handle all of these cases here to avoid log-related exceptions from crashing the JVM.
+ try {
+ return bundle.getString(msg);
+ } catch (MissingResourceException ex) {
+ return msg;
+ } catch (ClassCastException ex) {
+ return bundle.getObject(msg).toString();
+ }
+ }
+
+}
diff --git a/slf4j-ext/src/main/java/org/slf4j/ext/EventLogger.java b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLoggerFactory.java
index a72e656e..f31ac7a8 100755..100644
--- a/slf4j-ext/src/main/java/org/slf4j/ext/EventLogger.java
+++ b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JPlatformLoggerFactory.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2021 QOS.ch
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,43 +22,38 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.ext;
+package org.slf4j.jdk.platform.logging;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentMap;
+
+import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-import org.slf4j.Marker;
-import org.slf4j.MarkerFactory;
-import org.slf4j.spi.LocationAwareLogger;
/**
- * Simple Logger used to log events. All events are directed to a logger named "EventLogger"
- * with a level of INFO and with an Event marker.
+ * Manages instances of {@link SLF4JPlatformLogger}.
+ *
+ * @since 1.3.0
+ * @author Ceki
*
- * @author Ralph Goers
*/
-public class EventLogger {
-
- private static final String FQCN = EventLogger.class.getName();
-
- static Marker EVENT_MARKER = MarkerFactory.getMarker("EVENT");
-
- private static LoggerWrapper eventLogger = new LoggerWrapper(LoggerFactory.getLogger("EventLogger"), FQCN);
-
- /**
- * There can only be a single EventLogger.
- */
- private EventLogger() {
- }
-
+public class SLF4JPlatformLoggerFactory {
+ ConcurrentMap<String, SLF4JPlatformLogger> loggerMap = new ConcurrentHashMap<>();
+
/**
- * Logs the event.
- *
- * @param data The EventData.
+ * Return an appropriate {@link SLF4JPlatformLogger} instance by name.
*/
- public static void logEvent(EventData data) {
- if (eventLogger.instanceofLAL) {
- ((LocationAwareLogger) eventLogger.logger).log(EVENT_MARKER, FQCN, LocationAwareLogger.INFO_INT, data.toXML(), new Object[] { data }, null);
+ public SLF4JPlatformLogger getLogger(String loggerName) {
+
+
+ SLF4JPlatformLogger spla = loggerMap.get(loggerName);
+ if (spla != null) {
+ return spla;
} else {
- eventLogger.logger.info(EVENT_MARKER, data.toXML(), data);
+ Logger slf4jLogger = LoggerFactory.getLogger(loggerName);
+ SLF4JPlatformLogger newInstance = new SLF4JPlatformLogger(slf4jLogger);
+ SLF4JPlatformLogger oldInstance = loggerMap.putIfAbsent(loggerName, newInstance);
+ return oldInstance == null ? newInstance : oldInstance;
}
}
}
diff --git a/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JSystemLoggerFinder.java b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JSystemLoggerFinder.java
new file mode 100644
index 00000000..a8622428
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/main/java/org/slf4j/jdk/platform/logging/SLF4JSystemLoggerFinder.java
@@ -0,0 +1,59 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jdk.platform.logging;
+
+/**
+ * Uses {@link SLF4JPlatformLoggerFactory#getLogger(String)} to get a logger
+ * that is adapted for {@link System.Logger}.
+ *
+ * @since 2.0.0
+ */
+public class SLF4JSystemLoggerFinder extends System.LoggerFinder {
+
+ final SLF4JPlatformLoggerFactory platformLoggerFactory = new SLF4JPlatformLoggerFactory();
+
+ @Override
+ public System.Logger getLogger(String name, Module module) {
+ // JEP 264[1], which introduced the Platform Logging API,
+ // contains the following note:
+ //
+ // > An implementation of the LoggerFinder service should make it
+ // > possible to distinguish system loggers (used by system classes
+ // > from the Bootstrap Class Loader (BCL)) and application loggers
+ // > (created by an application for its own usage). This distinction
+ // > is important for platform security. The creator of a logger can
+ // > pass the class or module for which the logger is created to the
+ // > LoggerFinder so that the LoggerFinder can figure out which kind
+ // > of logger to return.
+ //
+ // If backends support this distinction and once `LoggerFactory`'s API
+ // is updated to forward a module, we should do that here.
+ //
+ // [1] https://openjdk.java.net/jeps/264
+ SLF4JPlatformLogger adapter = platformLoggerFactory.getLogger(name);
+ return adapter;
+ }
+
+} \ No newline at end of file
diff --git a/slf4j-jdk-platform-logging/src/main/resources/META-INF/services/java.lang.System$LoggerFinder b/slf4j-jdk-platform-logging/src/main/resources/META-INF/services/java.lang.System$LoggerFinder
new file mode 100644
index 00000000..06845269
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/main/resources/META-INF/services/java.lang.System$LoggerFinder
@@ -0,0 +1 @@
+org.slf4j.jdk.platform.logging.SLF4JSystemLoggerFinder
diff --git a/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/SLF4JPlatformLoggingTest.java b/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/SLF4JPlatformLoggingTest.java
new file mode 100644
index 00000000..7a662b96
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/SLF4JPlatformLoggingTest.java
@@ -0,0 +1,119 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jdk.platform.logging.test;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.io.IOException;
+import java.io.PrintStream;
+import java.lang.System.Logger;
+import java.lang.System.Logger.Level;
+import java.lang.System.LoggerFinder;
+import java.util.List;
+import java.util.Random;
+
+import org.junit.After;
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+/**
+ * The present test is fragile in the sense that it sets up SimpleLogger
+ * with a StringPrintStream and reverts to the old stream when done.
+ *
+ * Any tests running simultaneously (and using SimpleLogger) will be affected
+ * by this. Moreover, since SimpleLogger is initialized by the call to LoggerFactory
+ * and tests also using LoggerFactory will also be affected.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ *
+ */
+public class SLF4JPlatformLoggingTest {
+
+ static final String PREFIX = "org.slf4j.simpleLogger.";
+ static final String SIMPLE_LOGGER_FILE_PROPERTY = PREFIX + "logFile";
+ static final String SIMPLE_LOGGER_THREAD_NAME_PROPERTY = PREFIX + "showThreadName";
+
+ static final String EXPECTED_FINDER_CLASS = "org.slf4j.jdk.platform.logging.SLF4JSystemLoggerFinder";
+
+ static int diff = new Random().nextInt(100*1000*1000);
+
+ static final PrintStream oldErr = System.err;
+ static StringPrintStream SPS = new StringPrintStream(oldErr, false);
+
+ @BeforeClass
+ static public void beforeClass() throws Exception {
+ System.setErr(SPS);
+ //System.setProperty(SIMPLE_LOGGER_FILE_PROPERTY, targetFile);
+ System.setProperty(SIMPLE_LOGGER_THREAD_NAME_PROPERTY, "false");
+ }
+
+ @AfterClass
+ static public void afterClass() {
+ System.setErr(oldErr);
+ System.clearProperty(SIMPLE_LOGGER_THREAD_NAME_PROPERTY);
+ }
+
+ @After
+ public void tearDown() {
+ SPS.stringList.clear();
+ }
+
+ @Test
+ public void smoke() throws IOException {
+ LoggerFinder finder = System.LoggerFinder.getLoggerFinder();
+ assertEquals(EXPECTED_FINDER_CLASS, finder.getClass().getName());
+ Logger systemLogger = finder.getLogger("smoke", null);
+ systemLogger.log(Level.INFO, "hello");
+ systemLogger.log(Level.INFO, "hello {0}", "world");
+
+ List<String> results = SPS.stringList;
+ assertEquals(2, results.size());
+ assertEquals("INFO smoke - hello", results.get(0));
+ assertEquals("INFO smoke - hello world", results.get(1));
+ }
+
+ @Test
+ public void throwTest() throws IOException {
+ LoggerFinder finder = System.LoggerFinder.getLoggerFinder();
+ assertEquals(EXPECTED_FINDER_CLASS, finder.getClass().getName());
+
+ Logger systemLogger = finder.getLogger("throwTest", null);
+ systemLogger.log(Level.INFO, "we have a problem", new Exception());
+
+ List<String> results = SPS.stringList;
+ //INFO throwTest - a problem
+ //java.lang.Exception
+ // at org.slf4j.jdk.platform.logging/org.slf4j.jdk.platform.logging.SLF4JPlatformLoggingTest.throwTest(SLF4JPlatformLoggingTest.java:92)
+
+ assertEquals("INFO throwTest - we have a problem", results.get(0));
+ assertEquals(Exception.class.getName(), results.get(1));
+ assertTrue(results.get(2).contains("at "));
+ assertTrue(results.get(2).contains(this.getClass().getName()));
+ }
+
+
+}
diff --git a/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/StringPrintStream.java b/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/StringPrintStream.java
new file mode 100644
index 00000000..b51e1cd2
--- /dev/null
+++ b/slf4j-jdk-platform-logging/src/test/java/org/slf4j/jdk/platform/logging/test/StringPrintStream.java
@@ -0,0 +1,67 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jdk.platform.logging.test;
+
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+public class StringPrintStream extends PrintStream {
+
+ public static final String LINE_SEP = System.getProperty("line.separator");
+ PrintStream other;
+ boolean duplicate = false;
+
+ public List<String> stringList = Collections.synchronizedList(new ArrayList<String>());
+
+ public StringPrintStream(PrintStream ps, boolean duplicate) {
+ super(ps);
+ other = ps;
+ this.duplicate = duplicate;
+ }
+
+ public StringPrintStream(PrintStream ps) {
+ this(ps, false);
+ }
+
+ public void print(String s) {
+ if (duplicate)
+ other.print(s);
+ stringList.add(s);
+ }
+
+ public void println(String s) {
+ if (duplicate)
+ other.println(s);
+ stringList.add(s);
+ }
+
+ public void println(Object o) {
+ if (duplicate)
+ other.println(o);
+ stringList.add(o.toString());
+ }
+} \ No newline at end of file
diff --git a/slf4j-jdk14/LICENSE.txt b/slf4j-jdk14/LICENSE.txt
index 508a2728..e4079f54 100644
--- a/slf4j-jdk14/LICENSE.txt
+++ b/slf4j-jdk14/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2023 QOS.ch
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-jdk14/pom.xml b/slf4j-jdk14/pom.xml
index 16d4fa79..8d677685 100755
--- a/slf4j-jdk14/pom.xml
+++ b/slf4j-jdk14/pom.xml
@@ -1,23 +1,27 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-jdk14</artifactId>
-
<packaging>jar</packaging>
- <name>SLF4J JDK14 Binding</name>
- <description>SLF4J JDK14 Binding</description>
+ <name>SLF4J JDK14 Provider</name>
+ <description>SLF4J JDK14 Provider</description>
<url>http://www.slf4j.org</url>
+ <properties>
+ <module-name>org.slf4j.jul</module-name>
+ <slf4j.provider.implementation>org.slf4j.jul.JULServiceProvider</slf4j.provider.implementation>
+ <slf4j.provider.type>jul</slf4j.provider.type>
+ </properties>
<dependencies>
<dependency>
@@ -34,23 +38,4 @@
</dependency>
</dependencies>
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
- </plugins>
- </build>
-
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerAdapter.java b/slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerAdapter.java
deleted file mode 100755
index 2de8e3e5..00000000
--- a/slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerAdapter.java
+++ /dev/null
@@ -1,651 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import java.util.logging.Level;
-import java.util.logging.LogRecord;
-
-import org.slf4j.Logger;
-import org.slf4j.Marker;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MarkerIgnoringBase;
-import org.slf4j.helpers.MessageFormatter;
-import org.slf4j.spi.LocationAwareLogger;
-
-/**
- * A wrapper over {@link java.util.logging.Logger java.util.logging.Logger} in
- * conformity with the {@link Logger} interface. Note that the logging levels
- * mentioned in this class refer to those defined in the java.util.logging
- * package.
- *
- * @author Ceki G&uuml;lc&uuml;
- * @author Peter Royal
- */
-public final class JDK14LoggerAdapter extends MarkerIgnoringBase implements LocationAwareLogger {
-
- private static final long serialVersionUID = -8053026990503422791L;
-
- transient final java.util.logging.Logger logger;
-
- // WARN: JDK14LoggerAdapter constructor should have only package access so
- // that only JDK14LoggerFactory be able to create one.
- JDK14LoggerAdapter(java.util.logging.Logger logger) {
- this.logger = logger;
- this.name = logger.getName();
- }
-
- /**
- * Is this logger instance enabled for the FINEST level?
- *
- * @return True if this Logger is enabled for level FINEST, false otherwise.
- */
- public boolean isTraceEnabled() {
- return logger.isLoggable(Level.FINEST);
- }
-
- /**
- * Log a message object at level FINEST.
- *
- * @param msg
- * - the message object to be logged
- */
- public void trace(String msg) {
- if (logger.isLoggable(Level.FINEST)) {
- log(SELF, Level.FINEST, msg, null);
- }
- }
-
- /**
- * Log a message at level FINEST according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level FINEST.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void trace(String format, Object arg) {
- if (logger.isLoggable(Level.FINEST)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log(SELF, Level.FINEST, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level FINEST according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the FINEST level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void trace(String format, Object arg1, Object arg2) {
- if (logger.isLoggable(Level.FINEST)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log(SELF, Level.FINEST, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level FINEST according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the FINEST level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void trace(String format, Object... argArray) {
- if (logger.isLoggable(Level.FINEST)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- log(SELF, Level.FINEST, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at level FINEST with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void trace(String msg, Throwable t) {
- if (logger.isLoggable(Level.FINEST)) {
- log(SELF, Level.FINEST, msg, t);
- }
- }
-
- /**
- * Is this logger instance enabled for the FINE level?
- *
- * @return True if this Logger is enabled for level FINE, false otherwise.
- */
- public boolean isDebugEnabled() {
- return logger.isLoggable(Level.FINE);
- }
-
- /**
- * Log a message object at level FINE.
- *
- * @param msg
- * - the message object to be logged
- */
- public void debug(String msg) {
- if (logger.isLoggable(Level.FINE)) {
- log(SELF, Level.FINE, msg, null);
- }
- }
-
- /**
- * Log a message at level FINE according to the specified format and argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level FINE.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void debug(String format, Object arg) {
- if (logger.isLoggable(Level.FINE)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log(SELF, Level.FINE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level FINE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the FINE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void debug(String format, Object arg1, Object arg2) {
- if (logger.isLoggable(Level.FINE)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log(SELF, Level.FINE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level FINE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the FINE level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void debug(String format, Object... argArray) {
- if (logger.isLoggable(Level.FINE)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- log(SELF, Level.FINE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at level FINE with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void debug(String msg, Throwable t) {
- if (logger.isLoggable(Level.FINE)) {
- log(SELF, Level.FINE, msg, t);
- }
- }
-
- /**
- * Is this logger instance enabled for the INFO level?
- *
- * @return True if this Logger is enabled for the INFO level, false otherwise.
- */
- public boolean isInfoEnabled() {
- return logger.isLoggable(Level.INFO);
- }
-
- /**
- * Log a message object at the INFO level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void info(String msg) {
- if (logger.isLoggable(Level.INFO)) {
- log(SELF, Level.INFO, msg, null);
- }
- }
-
- /**
- * Log a message at level INFO according to the specified format and argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void info(String format, Object arg) {
- if (logger.isLoggable(Level.INFO)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log(SELF, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the INFO level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void info(String format, Object arg1, Object arg2) {
- if (logger.isLoggable(Level.INFO)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log(SELF, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level INFO according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void info(String format, Object... argArray) {
- if (logger.isLoggable(Level.INFO)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- log(SELF, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the INFO level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void info(String msg, Throwable t) {
- if (logger.isLoggable(Level.INFO)) {
- log(SELF, Level.INFO, msg, t);
- }
- }
-
- /**
- * Is this logger instance enabled for the WARNING level?
- *
- * @return True if this Logger is enabled for the WARNING level, false
- * otherwise.
- */
- public boolean isWarnEnabled() {
- return logger.isLoggable(Level.WARNING);
- }
-
- /**
- * Log a message object at the WARNING level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void warn(String msg) {
- if (logger.isLoggable(Level.WARNING)) {
- log(SELF, Level.WARNING, msg, null);
- }
- }
-
- /**
- * Log a message at the WARNING level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARNING level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void warn(String format, Object arg) {
- if (logger.isLoggable(Level.WARNING)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log(SELF, Level.WARNING, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the WARNING level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARNING level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void warn(String format, Object arg1, Object arg2) {
- if (logger.isLoggable(Level.WARNING)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log(SELF, Level.WARNING, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level WARNING according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARNING level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void warn(String format, Object... argArray) {
- if (logger.isLoggable(Level.WARNING)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- log(SELF, Level.WARNING, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the WARNING level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void warn(String msg, Throwable t) {
- if (logger.isLoggable(Level.WARNING)) {
- log(SELF, Level.WARNING, msg, t);
- }
- }
-
- /**
- * Is this logger instance enabled for level SEVERE?
- *
- * @return True if this Logger is enabled for level SEVERE, false otherwise.
- */
- public boolean isErrorEnabled() {
- return logger.isLoggable(Level.SEVERE);
- }
-
- /**
- * Log a message object at the SEVERE level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void error(String msg) {
- if (logger.isLoggable(Level.SEVERE)) {
- log(SELF, Level.SEVERE, msg, null);
- }
- }
-
- /**
- * Log a message at the SEVERE level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the SEVERE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void error(String format, Object arg) {
- if (logger.isLoggable(Level.SEVERE)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- log(SELF, Level.SEVERE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the SEVERE level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the SEVERE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void error(String format, Object arg1, Object arg2) {
- if (logger.isLoggable(Level.SEVERE)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- log(SELF, Level.SEVERE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level SEVERE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the SEVERE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arguments
- * an array of arguments
- */
- public void error(String format, Object... arguments) {
- if (logger.isLoggable(Level.SEVERE)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- log(SELF, Level.SEVERE, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the SEVERE level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void error(String msg, Throwable t) {
- if (logger.isLoggable(Level.SEVERE)) {
- log(SELF, Level.SEVERE, msg, t);
- }
- }
-
- /**
- * Log the message at the specified level with the specified throwable if any.
- * This method creates a LogRecord and fills in caller date before calling
- * this instance's JDK14 logger.
- *
- * See bug report #13 for more details.
- *
- * @param level
- * @param msg
- * @param t
- */
- private void log(String callerFQCN, Level level, String msg, Throwable t) {
- // millis and thread are filled by the constructor
- LogRecord record = new LogRecord(level, msg);
- record.setLoggerName(getName());
- record.setThrown(t);
- fillCallerData(callerFQCN, record);
- logger.log(record);
-
- }
-
- static String SELF = JDK14LoggerAdapter.class.getName();
- static String SUPER = MarkerIgnoringBase.class.getName();
-
- /**
- * Fill in caller data if possible.
- *
- * @param record
- * The record to update
- */
- final private void fillCallerData(String callerFQCN, LogRecord record) {
- StackTraceElement[] steArray = new Throwable().getStackTrace();
-
- int selfIndex = -1;
- for (int i = 0; i < steArray.length; i++) {
- final String className = steArray[i].getClassName();
- if (className.equals(callerFQCN) || className.equals(SUPER)) {
- selfIndex = i;
- break;
- }
- }
-
- int found = -1;
- for (int i = selfIndex + 1; i < steArray.length; i++) {
- final String className = steArray[i].getClassName();
- if (!(className.equals(callerFQCN) || className.equals(SUPER))) {
- found = i;
- break;
- }
- }
-
- if (found != -1) {
- StackTraceElement ste = steArray[found];
- // setting the class name has the side effect of setting
- // the needToInferCaller variable to false.
- record.setSourceClassName(ste.getClassName());
- record.setSourceMethodName(ste.getMethodName());
- }
- }
-
- public void log(Marker marker, String callerFQCN, int level, String message, Object[] argArray, Throwable t) {
- Level julLevel;
- switch (level) {
- case LocationAwareLogger.TRACE_INT:
- julLevel = Level.FINEST;
- break;
- case LocationAwareLogger.DEBUG_INT:
- julLevel = Level.FINE;
- break;
- case LocationAwareLogger.INFO_INT:
- julLevel = Level.INFO;
- break;
- case LocationAwareLogger.WARN_INT:
- julLevel = Level.WARNING;
- break;
- case LocationAwareLogger.ERROR_INT:
- julLevel = Level.SEVERE;
- break;
- default:
- throw new IllegalStateException("Level number " + level + " is not recognized.");
- }
- // the logger.isLoggable check avoids the unconditional
- // construction of location data for disabled log
- // statements. As of 2008-07-31, callers of this method
- // do not perform this check. See also
- // http://bugzilla.slf4j.org/show_bug.cgi?id=90
- if (logger.isLoggable(julLevel)) {
- log(callerFQCN, julLevel, message, t);
- }
- }
-}
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index e532be61..00000000
--- a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- *
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled against.
- * The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
- private static final String loggerFactoryClassStr = org.slf4j.impl.JDK14LoggerFactory.class.getName();
-
- /** The ILoggerFactory instance returned by the {@link #getLoggerFactory} method
- * should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- // Note: JCL gets substituted at build time by an appropriate Ant task
- loggerFactory = new org.slf4j.impl.JDK14LoggerFactory();
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMDCBinder.java
deleted file mode 100644
index bff523db..00000000
--- a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.helpers.BasicMDCAdapter;
-import org.slf4j.spi.MDCAdapter;
-
-/**
- * This implementation is bound to {@link BasicMDCAdapter}.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMDCAdapter}.
- */
- public MDCAdapter getMDCA() {
- // note that this method is invoked only from within the static initializer of
- // the org.slf4j.MDC class.
- return new BasicMDCAdapter();
- }
-
- public String getMDCAdapterClassStr() {
- return BasicMDCAdapter.class.getName();
- }
-}
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 1d255230..00000000
--- a/slf4j-jdk14/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-
-}
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerAdapter.java b/slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerAdapter.java
new file mode 100755
index 00000000..dbc52da5
--- /dev/null
+++ b/slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerAdapter.java
@@ -0,0 +1,298 @@
+/**
+ * Copyright (c) 2004-2011 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jul;
+
+import java.util.logging.Level;
+import java.util.logging.LogRecord;
+
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+import org.slf4j.event.EventConstants;
+import org.slf4j.event.LoggingEvent;
+import org.slf4j.helpers.AbstractLogger;
+import org.slf4j.helpers.FormattingTuple;
+import org.slf4j.helpers.LegacyAbstractLogger;
+import org.slf4j.helpers.MessageFormatter;
+import org.slf4j.helpers.NormalizedParameters;
+import org.slf4j.helpers.SubstituteLogger;
+import org.slf4j.spi.DefaultLoggingEventBuilder;
+import org.slf4j.spi.LocationAwareLogger;
+
+/**
+ * A wrapper over {@link java.util.logging.Logger java.util.logging.Logger} in
+ * conformity with the {@link Logger} interface. Note that the logging levels
+ * mentioned in this class refer to those defined in the java.util.logging
+ * package.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @author Peter Royal
+ */
+public final class JDK14LoggerAdapter extends LegacyAbstractLogger implements LocationAwareLogger {
+
+ private static final long serialVersionUID = -8053026990503422791L;
+
+ transient final java.util.logging.Logger logger;
+
+ // WARN: JDK14LoggerAdapter constructor should have only package access so
+ // that only JDK14LoggerFactory be able to create one.
+ JDK14LoggerAdapter(java.util.logging.Logger logger) {
+ this.logger = logger;
+ this.name = logger.getName();
+ }
+
+ /**
+ * Is this logger instance enabled for the FINEST level?
+ *
+ * @return True if this Logger is enabled for level FINEST, false otherwise.
+ */
+ public boolean isTraceEnabled() {
+ return logger.isLoggable(Level.FINEST);
+ }
+
+ /**
+ * Is this logger instance enabled for the FINE level?
+ *
+ * @return True if this Logger is enabled for level FINE, false otherwise.
+ */
+ public boolean isDebugEnabled() {
+ return logger.isLoggable(Level.FINE);
+ }
+
+ /**
+ * Is this logger instance enabled for the INFO level?
+ *
+ * @return True if this Logger is enabled for the INFO level, false otherwise.
+ */
+ public boolean isInfoEnabled() {
+ return logger.isLoggable(Level.INFO);
+ }
+
+ /**
+ * Is this logger instance enabled for the WARNING level?
+ *
+ * @return True if this Logger is enabled for the WARNING level, false
+ * otherwise.
+ */
+ public boolean isWarnEnabled() {
+ return logger.isLoggable(Level.WARNING);
+ }
+
+ /**
+ * Is this logger instance enabled for level SEVERE?
+ *
+ * @return True if this Logger is enabled for level SEVERE, false otherwise.
+ */
+ public boolean isErrorEnabled() {
+ return logger.isLoggable(Level.SEVERE);
+ }
+
+ // /**
+ // * Log the message at the specified level with the specified throwable if any.
+ // * This method creates a LogRecord and fills in caller date before calling
+ // * this instance's JDK14 logger.
+ // *
+ // * See bug report #13 for more details.
+ // *
+ // * @param level
+ // * @param msg
+ // * @param t
+ // */
+ // private void log(String callerFQCN, Level level, String msg, Throwable t) {
+ // // millis and thread are filled by the constructor
+ // LogRecord record = new LogRecord(level, msg);
+ // record.setLoggerName(getName());
+ // record.setThrown(t);
+ // // Note: parameters in record are not set because SLF4J only
+ // // supports a single formatting style
+ // fillCallerData(callerFQCN, record);
+ // logger.log(record);
+ // }
+
+ /**
+ * Log the message at the specified level with the specified throwable if any.
+ * This method creates a LogRecord and fills in caller date before calling this
+ * instance's JDK14 logger.
+ */
+ @Override
+ protected void handleNormalizedLoggingCall(org.slf4j.event.Level level, Marker marker, String msg, Object[] args, Throwable throwable) {
+ innerNormalizedLoggingCallHandler(getFullyQualifiedCallerName(), level, marker, msg, args, throwable);
+ }
+
+ private void innerNormalizedLoggingCallHandler(String fqcn, org.slf4j.event.Level level, Marker marker, String msg, Object[] args, Throwable throwable) {
+ // millis and thread are filled by the constructor
+ Level julLevel = slf4jLevelToJULLevel(level);
+ String formattedMessage = MessageFormatter.basicArrayFormat(msg, args);
+ LogRecord record = new LogRecord(julLevel, formattedMessage);
+
+ // https://jira.qos.ch/browse/SLF4J-13
+ record.setLoggerName(getName());
+ record.setThrown(throwable);
+ // Note: parameters in record are not set because SLF4J only
+ // supports a single formatting style
+ // See also https://jira.qos.ch/browse/SLF4J-10
+ fillCallerData(fqcn, record);
+ logger.log(record);
+ }
+
+ @Override
+ protected String getFullyQualifiedCallerName() {
+ return SELF;
+ }
+
+ @Override
+ public void log(Marker marker, String callerFQCN, int slf4jLevelInt, String message, Object[] arguments, Throwable throwable) {
+
+ org.slf4j.event.Level slf4jLevel = org.slf4j.event.Level.intToLevel(slf4jLevelInt);
+ Level julLevel = slf4jLevelIntToJULLevel(slf4jLevelInt);
+
+ if (logger.isLoggable(julLevel)) {
+ NormalizedParameters np = NormalizedParameters.normalize(message, arguments, throwable);
+ innerNormalizedLoggingCallHandler(callerFQCN, slf4jLevel, marker, np.getMessage(), np.getArguments(), np.getThrowable());
+ }
+ }
+
+ /**
+ * Fill in caller data if possible.
+ *
+ * @param record The record to update
+ */
+ final private void fillCallerData(String callerFQCN, LogRecord record) {
+ StackTraceElement[] steArray = new Throwable().getStackTrace();
+
+ int selfIndex = -1;
+ for (int i = 0; i < steArray.length; i++) {
+ final String className = steArray[i].getClassName();
+
+ if (barrierMatch(callerFQCN, className)) {
+ selfIndex = i;
+ break;
+ }
+ }
+
+ int found = -1;
+ for (int i = selfIndex + 1; i < steArray.length; i++) {
+ final String className = steArray[i].getClassName();
+ if (!(barrierMatch(callerFQCN, className))) {
+ found = i;
+ break;
+ }
+ }
+
+ if (found != -1) {
+ StackTraceElement ste = steArray[found];
+ // setting the class name has the side effect of setting
+ // the needToInferCaller variable to false.
+ record.setSourceClassName(ste.getClassName());
+ record.setSourceMethodName(ste.getMethodName());
+ }
+ }
+
+ static String SELF = JDK14LoggerAdapter.class.getName();
+
+ static String SUPER = LegacyAbstractLogger.class.getName();
+ static String SUPER_OF_SUPER = AbstractLogger.class.getName();
+ static String SUBSTITUE = SubstituteLogger.class.getName();
+ static String FLUENT = DefaultLoggingEventBuilder.class.getName();
+
+ static String[] BARRIER_CLASSES = new String[] { SUPER_OF_SUPER, SUPER, SELF, SUBSTITUE, FLUENT };
+
+ private boolean barrierMatch(String callerFQCN, String candidateClassName) {
+ if (candidateClassName.equals(callerFQCN))
+ return true;
+ for (String barrierClassName : BARRIER_CLASSES) {
+ if (barrierClassName.equals(candidateClassName)) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ private static Level slf4jLevelIntToJULLevel(int levelInt) {
+ org.slf4j.event.Level slf4jLevel = org.slf4j.event.Level.intToLevel(levelInt);
+ return slf4jLevelToJULLevel(slf4jLevel);
+ }
+
+ private static Level slf4jLevelToJULLevel(org.slf4j.event.Level slf4jLevel) {
+ Level julLevel;
+ switch (slf4jLevel) {
+ case TRACE:
+ julLevel = Level.FINEST;
+ break;
+ case DEBUG:
+ julLevel = Level.FINE;
+ break;
+ case INFO:
+ julLevel = Level.INFO;
+ break;
+ case WARN:
+ julLevel = Level.WARNING;
+ break;
+ case ERROR:
+ julLevel = Level.SEVERE;
+ break;
+ default:
+ throw new IllegalStateException("Level " + slf4jLevel + " is not recognized.");
+ }
+ return julLevel;
+ }
+
+ /**
+ * @since 1.7.15
+ */
+ public void log(LoggingEvent event) {
+ // assumes that the invocation is made from a substitute logger
+ // this assumption might change in the future with the advent of a fluent API
+ Level julLevel = slf4jLevelToJULLevel(event.getLevel());
+ if (logger.isLoggable(julLevel)) {
+ LogRecord record = eventToRecord(event, julLevel);
+ logger.log(record);
+ }
+ }
+
+ private LogRecord eventToRecord(LoggingEvent event, Level julLevel) {
+ String format = event.getMessage();
+ Object[] arguments = event.getArgumentArray();
+ FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
+ if (ft.getThrowable() != null && event.getThrowable() != null) {
+ throw new IllegalArgumentException("both last element in argument array and last argument are of type Throwable");
+ }
+
+ Throwable t = event.getThrowable();
+ if (ft.getThrowable() != null) {
+ t = ft.getThrowable();
+ throw new IllegalStateException("fix above code");
+ }
+
+ LogRecord record = new LogRecord(julLevel, ft.getMessage());
+ record.setLoggerName(event.getLoggerName());
+ record.setMillis(event.getTimeStamp());
+ record.setSourceClassName(EventConstants.NA_SUBST);
+ record.setSourceMethodName(EventConstants.NA_SUBST);
+
+ record.setThrown(t);
+ return record;
+ }
+
+}
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerFactory.java b/slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerFactory.java
index f251d987..bd314e0c 100644
--- a/slf4j-jdk14/src/main/java/org/slf4j/impl/JDK14LoggerFactory.java
+++ b/slf4j-jdk14/src/main/java/org/slf4j/jul/JDK14LoggerFactory.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.jul;
import org.slf4j.Logger;
import org.slf4j.ILoggerFactory;
@@ -41,8 +41,17 @@ public class JDK14LoggerFactory implements ILoggerFactory {
// key: name (String), value: a JDK14LoggerAdapter;
ConcurrentMap<String, Logger> loggerMap;
+ /**
+ * the root logger is called "" in JUL
+ */
+ private static String JUL_ROOT_LOGGER_NAME = "";
+
public JDK14LoggerFactory() {
- loggerMap = new ConcurrentHashMap<String, Logger>();
+ loggerMap = new ConcurrentHashMap<>();
+ // ensure jul initialization. see SLF4J-359
+ // note that call to java.util.logging.LogManager.getLogManager() fails on the Google App Engine platform. See
+ // SLF4J-363
+ java.util.logging.Logger.getLogger("");
}
/*
@@ -53,7 +62,7 @@ public class JDK14LoggerFactory implements ILoggerFactory {
public Logger getLogger(String name) {
// the root logger is called "" in JUL
if (name.equalsIgnoreCase(Logger.ROOT_LOGGER_NAME)) {
- name = "";
+ name = JUL_ROOT_LOGGER_NAME;
}
Logger slf4jLogger = loggerMap.get(name);
diff --git a/slf4j-jdk14/src/main/java/org/slf4j/jul/JULServiceProvider.java b/slf4j-jdk14/src/main/java/org/slf4j/jul/JULServiceProvider.java
new file mode 100755
index 00000000..5e9a74ed
--- /dev/null
+++ b/slf4j-jdk14/src/main/java/org/slf4j/jul/JULServiceProvider.java
@@ -0,0 +1,48 @@
+package org.slf4j.jul;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.helpers.BasicMDCAdapter;
+import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class JULServiceProvider implements SLF4JServiceProvider {
+
+ /**
+ * Declare the version of the SLF4J API this implementation is compiled
+ * against. The value of this field is modified with each major release.
+ */
+ // to avoid constant folding by the compiler, this field must *not* be final
+ public static String REQUESTED_API_VERSION = "2.0.99"; // !final
+
+ private ILoggerFactory loggerFactory;
+ private IMarkerFactory markerFactory;
+ private MDCAdapter mdcAdapter;
+
+ @Override
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return REQUESTED_API_VERSION;
+ }
+
+ @Override
+ public void initialize() {
+ loggerFactory = new JDK14LoggerFactory();
+ markerFactory = new BasicMarkerFactory();
+ mdcAdapter = new BasicMDCAdapter();
+ }
+}
diff --git a/slf4j-jdk14/src/main/java9/module-info.java b/slf4j-jdk14/src/main/java9/module-info.java
new file mode 100755
index 00000000..5fdbdcf1
--- /dev/null
+++ b/slf4j-jdk14/src/main/java9/module-info.java
@@ -0,0 +1,9 @@
+module org.slf4j.jul {
+ requires org.slf4j;
+ requires java.logging;
+ provides org.slf4j.spi.SLF4JServiceProvider with org.slf4j.jul.JULServiceProvider;
+
+ exports org.slf4j.jul;
+ opens org.slf4j.jul to org.slf4j;
+}
+
diff --git a/slf4j-jdk14/src/main/resources/META-INF/MANIFEST.MF b/slf4j-jdk14/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index bab3c6fe..00000000
--- a/slf4j-jdk14/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,9 +0,0 @@
-Implementation-Title: slf4j-jdk14
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.jdk14
-Bundle-Name: slf4j-jdk14
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-jdk14/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider b/slf4j-jdk14/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
new file mode 100755
index 00000000..8d062b2f
--- /dev/null
+++ b/slf4j-jdk14/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
@@ -0,0 +1 @@
+org.slf4j.jul.JULServiceProvider \ No newline at end of file
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/impl/PerfTest.java b/slf4j-jdk14/src/test/java/org/slf4j/impl/PerfTest.java
deleted file mode 100644
index 3b77ab96..00000000
--- a/slf4j-jdk14/src/test/java/org/slf4j/impl/PerfTest.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import junit.framework.TestCase;
-
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.BogoPerf;
-
-public class PerfTest extends TestCase {
-
- static long REFERENCE_BIPS = 9000;
-
- public PerfTest(String name) {
- super(name);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- }
-
- public void testBug72() {
-
- int LEN = 1000 * 1000 * 10;
- debugLoop(LEN); // warm up
- double avg = debugLoop(LEN);
- long referencePerf = 93;
- BogoPerf.assertDuration(avg, referencePerf, REFERENCE_BIPS);
-
- // when the code is guarded by a logger.isLoggable condition,
- // duration is about 16 *micro*seconds for 1000 iterations
- // when it is not guarded the figure is 90 milliseconds,
- // i.e a ration of 1 to 5000
- }
-
- double debugLoop(int len) {
- Logger logger = LoggerFactory.getLogger(PerfTest.class);
- long start = System.currentTimeMillis();
- for (int i = 0; i < len; i++) {
- logger.debug("hello");
- }
-
- long end = System.currentTimeMillis();
-
- long duration = end - start;
- return duration;
- }
-
-}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/issue/CallerInfoTest.java b/slf4j-jdk14/src/test/java/org/slf4j/issue/CallerInfoTest.java
new file mode 100755
index 00000000..a94d4631
--- /dev/null
+++ b/slf4j-jdk14/src/test/java/org/slf4j/issue/CallerInfoTest.java
@@ -0,0 +1,122 @@
+package org.slf4j.issue;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.util.List;
+import java.util.concurrent.LinkedBlockingQueue;
+import java.util.logging.Handler;
+import java.util.logging.Level;
+import java.util.logging.LogRecord;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.event.EventConstants;
+import org.slf4j.event.SubstituteLoggingEvent;
+import org.slf4j.helpers.SubstituteLogger;
+import org.slf4j.helpers.SubstituteServiceProvider;
+import org.slf4j.jul.ListHandler;
+
+public class CallerInfoTest {
+ Level oldLevel;
+ java.util.logging.Logger root = java.util.logging.Logger.getLogger("");
+
+ ListHandler listHandler = new ListHandler();
+
+ @Before
+ public void setUp() throws Exception {
+ oldLevel = root.getLevel();
+ root.setLevel(Level.FINE);
+ // removeAllHandlers(root);
+ root.addHandler(listHandler);
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ root.setLevel(oldLevel);
+ removeListHandlers(root);
+ }
+
+ void removeListHandlers(java.util.logging.Logger logger) {
+ Handler[] handlers = logger.getHandlers();
+ for (Handler h : handlers) {
+ if (h instanceof ListHandler)
+ logger.removeHandler(h);
+ }
+ }
+
+ @Test
+ public void testCallerInfo() {
+ Logger logger = LoggerFactory.getLogger("bla");
+ logger.debug("hello");
+
+ List<LogRecord> recordList = listHandler.recordList;
+
+ assertEquals(1, recordList.size());
+
+ LogRecord logRecod = recordList.get(0);
+ assertEquals(this.getClass().getName(), logRecod.getSourceClassName());
+ }
+
+ // Do we preserve location info using fluent API?
+ // See https://jira.qos.ch/browse/SLF4J-511
+
+ @Test
+ public void testCallerInfoWithFluentAPI() {
+ Logger logger = LoggerFactory.getLogger("bla");
+ logger.atDebug().log("hello");
+
+ List<LogRecord> recordList = listHandler.recordList;
+
+ assertEquals(1, recordList.size());
+
+ LogRecord logRecod = recordList.get(0);
+ assertEquals(this.getClass().getName(), logRecod.getSourceClassName());
+ }
+
+ @Test
+ public void testPostInitializationCallerInfoWithSubstituteLogger() {
+ Logger logger = LoggerFactory.getLogger("bla");
+ SubstituteLogger substituteLogger = new SubstituteLogger("bla", null, false);
+ substituteLogger.setDelegate(logger);
+ substituteLogger.debug("hello");
+
+ List<LogRecord> recordList = listHandler.recordList;
+
+ assertEquals(1, recordList.size());
+
+ LogRecord logRecod = recordList.get(0);
+ assertEquals(CallerInfoTest.class.getName(), logRecod.getSourceClassName());
+ }
+
+ // In this case we KNOW that we CANNOT KNOW the caller
+ @Test
+ public void testIntraInitializationCallerInfoWithSubstituteLogger() throws InterruptedException {
+ SubstituteServiceProvider substituteServiceProvider = new SubstituteServiceProvider();
+ String loggerName = "bkla";
+ substituteServiceProvider.getLoggerFactory().getLogger(loggerName);
+ SubstituteLogger substituteLogger = substituteServiceProvider.getSubstituteLoggerFactory().getLoggers().get(0);
+ assertEquals(loggerName, substituteLogger.getName());
+
+ substituteLogger.debug("jello");
+ Logger logger = LoggerFactory.getLogger(loggerName);
+ substituteLogger.setDelegate(logger);
+
+ final LinkedBlockingQueue<SubstituteLoggingEvent> queue = substituteServiceProvider.getSubstituteLoggerFactory().getEventQueue();
+
+ SubstituteLoggingEvent substituteLoggingEvent = queue.take();
+ assertTrue(substituteLogger.isDelegateEventAware());
+ substituteLogger.log(substituteLoggingEvent);
+
+ List<LogRecord> recordList = listHandler.recordList;
+
+ assertEquals(1, recordList.size());
+
+ LogRecord logRecod = recordList.get(0);
+ assertEquals(EventConstants.NA_SUBST, logRecod.getSourceClassName());
+ }
+
+}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/issue/LoggerSerializationTest.java b/slf4j-jdk14/src/test/java/org/slf4j/issue/LoggerSerializationTest.java
index bb9b8745..a8139d85 100644
--- a/slf4j-jdk14/src/test/java/org/slf4j/issue/LoggerSerializationTest.java
+++ b/slf4j-jdk14/src/test/java/org/slf4j/issue/LoggerSerializationTest.java
@@ -32,22 +32,22 @@ import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
-import junit.framework.Assert;
+import static org.junit.Assert.assertNotNull;
-import junit.framework.TestCase;
+import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
- * See http://bugzilla.slf4j.org/show_bug.cgi?id=261
+ * See http://jira.qos.ch/browse/SLF4J-252
* @author Thorbjorn Ravn Andersen
*/
-public class LoggerSerializationTest extends TestCase {
+public class LoggerSerializationTest {
static class LoggerHolder implements Serializable {
private static final long serialVersionUID = 1L;
- private Logger log = LoggerFactory.getLogger(LoggerHolder.class);
+ private final Logger log = LoggerFactory.getLogger(LoggerHolder.class);
public String toString() {
return "log=" + getLog();
@@ -58,6 +58,7 @@ public class LoggerSerializationTest extends TestCase {
}
}
+ @Test
public void testCanLoggerBeSerialized() throws IOException, ClassNotFoundException {
LoggerHolder lh1 = new LoggerHolder();
@@ -75,8 +76,8 @@ public class LoggerSerializationTest extends TestCase {
ObjectInputStream in = new ObjectInputStream(is);
LoggerHolder lh2 = (LoggerHolder) in.readObject();
- Assert.assertNotNull(lh2);
- Assert.assertNotNull(lh2.getLog());
+ assertNotNull(lh2);
+ assertNotNull(lh2.getLog());
lh2.getLog().info("You must see this message as a log message");
}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/jul/CountingHandler.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/CountingHandler.java
new file mode 100644
index 00000000..ea31174b
--- /dev/null
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/CountingHandler.java
@@ -0,0 +1,24 @@
+package org.slf4j.jul;
+
+import java.util.concurrent.atomic.AtomicLong;
+import java.util.logging.Handler;
+import java.util.logging.LogRecord;
+
+public class CountingHandler extends Handler {
+
+ final AtomicLong eventCount = new AtomicLong(0);
+
+ @Override
+ public void publish(LogRecord record) {
+ eventCount.getAndIncrement();
+ }
+
+ @Override
+ public void flush() {
+ }
+
+ @Override
+ public void close() throws SecurityException {
+ }
+
+}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/jul/FluentApiInvocationTest.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/FluentApiInvocationTest.java
new file mode 100755
index 00000000..dc37ac21
--- /dev/null
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/FluentApiInvocationTest.java
@@ -0,0 +1,144 @@
+package org.slf4j.jul;
+
+import static org.junit.Assert.assertEquals;
+
+import java.util.function.Supplier;
+import java.util.logging.Handler;
+import java.util.logging.Level;
+import java.util.logging.LogRecord;
+
+import org.junit.After;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class FluentApiInvocationTest {
+
+ ListHandler listHandler = new ListHandler();
+ java.util.logging.Logger root = java.util.logging.Logger.getLogger("");
+ Level oldLevel;
+ Logger logger = LoggerFactory.getLogger(this.getClass());
+
+ @Before
+ public void setUp() throws Exception {
+ oldLevel = root.getLevel();
+ root.setLevel(Level.FINE);
+ // removeAllHandlers(root);
+ root.addHandler(listHandler);
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ root.setLevel(oldLevel);
+ removeListHandlers(root);
+ }
+
+ void removeListHandlers(java.util.logging.Logger logger) {
+ Handler[] handlers = logger.getHandlers();
+ for (Handler h : handlers) {
+ if (h instanceof ListHandler)
+ logger.removeHandler(h);
+ }
+ }
+
+ @Test
+ public void singleMessage() {
+ String msg = "Hello world.";
+ logger.atDebug().log(msg);
+ assertLogMessage(msg, 0);
+ }
+
+ @Test
+ public void messageWithArguments() {
+ String msg = "Hello {}.";
+ logger.atDebug().addArgument("world").log(msg);
+ assertLogMessage("Hello world.", 0);
+ }
+
+ @Test
+ public void messageWithTwoArguments() {
+ int old = 15;
+ int t = 16;
+
+ {
+ String msg = "Temperature set to {}. Old temperature was {}.";
+ logger.atDebug().addArgument(t).addArgument(old).log(msg);
+ assertLogMessage("Temperature set to 16. Old temperature was 15.", 0);
+ }
+
+ {
+ String msg = "Temperature set to {}. Old temperature was {}.";
+ logger.atDebug().log(msg, t, old);
+ assertLogMessage("Temperature set to 16. Old temperature was 15.", 0);
+ }
+
+ {
+ String msg = "Temperature set to {}. Old temperature was {}.";
+ logger.atDebug().addArgument(t).log(msg, old);
+ assertLogMessage("Temperature set to 16. Old temperature was 15.", 0);
+ }
+
+ {
+ String msg = "Temperature set to {}. Old temperature was {}.";
+ logger.atDebug().addArgument(() -> t16()).log(msg, old);
+ assertLogMessage("Temperature set to 16. Old temperature was 15.", 0);
+ }
+ }
+
+ @Test
+ public void supplierArguments() {
+ Supplier<String> stringSupplier = () -> "world";
+ logger.atInfo().addArgument(stringSupplier).log("hello {}");
+ assertLogMessage("hello world", 0);
+ }
+
+ public int t16() {
+ return 16;
+ }
+
+ @Test
+ public void messageWithThrowable() {
+ String msg = "Hello world.";
+ Throwable t = new IllegalStateException();
+ logger.atDebug().setCause(t).log(msg);
+ assertLogMessage("Hello world.", 0);
+ assertThrowable(t, 0);
+ }
+
+ @Test
+ public void messageWithArgumentsAndThrowable() {
+ String msg = "Hello {}.";
+ Throwable t = new IllegalStateException();
+
+ logger.atDebug().setCause(t).addArgument("world").log(msg);
+ assertLogMessage("Hello world.", 0);
+ assertThrowable(t, 0);
+ }
+
+ @Test
+ public void messageWithKeyValuePair() {
+ String msg = "Hello world.";
+ logger.atDebug().addKeyValue("k", "v").log(msg);
+ assertLogMessage("k=v Hello world.", 0);
+
+ int oldT = 15;
+ int newT = 16;
+ logger.atDebug().addKeyValue("oldT", oldT).addKeyValue("newT", newT).log("Temperature changed.");
+ assertLogMessage("oldT=15 newT=16 Temperature changed.", 1);
+
+ }
+
+ private void assertLogMessage(String expected, int index) {
+ LogRecord logRecord = listHandler.recordList.get(index);
+ Assert.assertNotNull(logRecord);
+ assertEquals(expected, logRecord.getMessage());
+ }
+
+ private void assertThrowable(Throwable expected, int index) {
+ LogRecord logRecord = listHandler.recordList.get(index);
+ Assert.assertNotNull(logRecord);
+ assertEquals(expected, logRecord.getThrown());
+ }
+}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/InvocationTest.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/InvocationTest.java
index da76fab3..22669c2b 100755
--- a/slf4j-jdk14/src/test/java/org/slf4j/InvocationTest.java
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/InvocationTest.java
@@ -22,21 +22,20 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.jul;
import org.junit.After;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
+import org.slf4j.*;
-import java.util.ArrayList;
-import java.util.List;
import java.util.logging.Handler;
import java.util.logging.Level;
import java.util.logging.LogRecord;
-import static junit.framework.Assert.assertNotNull;
-import static junit.framework.Assert.assertNull;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.fail;
@@ -66,8 +65,16 @@ public class InvocationTest {
removeListHandlers(root);
}
+ void removeListHandlers(java.util.logging.Logger logger) {
+ Handler[] handlers = logger.getHandlers();
+ for (Handler h : handlers) {
+ if (h instanceof ListHandler)
+ logger.removeHandler(h);
+ }
+ }
+
@Test
- public void test1() {
+ public void smoke() {
Logger logger = LoggerFactory.getLogger("test1");
logger.debug("Hello world.");
assertLogMessage("Hello world.", 0);
@@ -75,9 +82,9 @@ public class InvocationTest {
@Test
public void verifyMessageFormatting() {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
+ Integer i1 = Integer.valueOf(1);
+ Integer i2 = Integer.valueOf(2);
+ Integer i3 = Integer.valueOf(3);
Exception e = new Exception("This is a test exception.");
Logger logger = LoggerFactory.getLogger("test2");
@@ -103,7 +110,7 @@ public class InvocationTest {
logger.warn("Hello world 3", e);
logger.error("Hello world 4.");
- logger.error("Hello world {}", new Integer(3));
+ logger.error("Hello world {}", Integer.valueOf(3));
logger.error("Hello world 4.", e);
}
@@ -175,29 +182,4 @@ public class InvocationTest {
assertEquals(exceptionType, logRecord.getThrown().getClass());
}
- void removeListHandlers(java.util.logging.Logger logger) {
- Handler[] handlers = logger.getHandlers();
- for (Handler h : handlers) {
- if (h instanceof ListHandler)
- logger.removeHandler(h);
- }
- }
-
- static private class ListHandler extends java.util.logging.Handler {
-
- List<LogRecord> recordList = new ArrayList<LogRecord>();
-
- @Override
- public void publish(LogRecord record) {
- recordList.add(record);
- }
-
- @Override
- public void flush() {
- }
-
- @Override
- public void close() throws SecurityException {
- }
- }
}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/impl/JDK14AdapterLoggerNameTest.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14AdapterLoggerNameTest.java
index e3cbbd25..8b263c58 100644
--- a/slf4j-jdk14/src/test/java/org/slf4j/impl/JDK14AdapterLoggerNameTest.java
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14AdapterLoggerNameTest.java
@@ -22,48 +22,63 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.jul;
+import static org.junit.Assert.assertNotNull;
+
+import java.util.Random;
import java.util.logging.Handler;
import java.util.logging.LogRecord;
import java.util.logging.Logger;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
-public class JDK14AdapterLoggerNameTest extends TestCase {
+public class JDK14AdapterLoggerNameTest {
private MockHandler mockHandler;
+ static Random random = new Random(System.currentTimeMillis());
+ long diff = random.nextInt(10000);
+ String loggerName = "JDK14AdapterLoggerNameTest" + diff;
- protected void setUp() throws Exception {
- super.setUp();
- Logger logger = Logger.getLogger("TEST");
- mockHandler = new MockHandler();
- removeHandlers(logger);
- logger.addHandler(mockHandler);
+ Logger logger = Logger.getLogger(loggerName);
+
+ @Before
+ public void setUp() throws Exception {
+ Logger logger = Logger.getLogger(loggerName);
+ addMockHandler(logger);
}
- protected void tearDown() throws Exception {
- removeHandlers(Logger.getLogger("TEST"));
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
+ removeHandlers(Logger.getLogger(loggerName));
}
- public void testLoggerNameusingJdkLogging() throws Exception {
- Logger.getLogger("TEST").info("test message");
+ @Test
+ public void testLoggerNameUsingJdkLogging() throws Exception {
+ logger.info("test message");
assertCorrectLoggerName();
-
}
+ @Test
public void testLoggerNameUsingSlf4j() throws Exception {
JDK14LoggerFactory factory = new JDK14LoggerFactory();
- org.slf4j.Logger logger = factory.getLogger("TEST");
+ org.slf4j.Logger logger = factory.getLogger(loggerName);
logger.info("test message");
assertCorrectLoggerName();
}
+ private void addMockHandler(Logger logger) {
+ mockHandler = new MockHandler();
+ removeHandlers(logger);
+ logger.addHandler(mockHandler);
+ }
+
private void removeHandlers(Logger logger) {
logger.setUseParentHandlers(false);
Handler[] handlers = logger.getHandlers();
- for (int i = 0; i < handlers.length; i++) {
- logger.removeHandler(handlers[i]);
+ for (Handler handler : handlers) {
+ logger.removeHandler(handler);
}
}
@@ -72,7 +87,7 @@ public class JDK14AdapterLoggerNameTest extends TestCase {
assertNotNull("missing logger name", mockHandler.record.getLoggerName());
}
- private class MockHandler extends java.util.logging.Handler {
+ private static class MockHandler extends java.util.logging.Handler {
public LogRecord record;
public void close() throws SecurityException {
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14MultithreadedInitializationTest.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14MultithreadedInitializationTest.java
new file mode 100644
index 00000000..3211f901
--- /dev/null
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/JDK14MultithreadedInitializationTest.java
@@ -0,0 +1,77 @@
+/**
+ * Copyright (c) 2004-2016 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.jul;
+
+import static org.junit.Assert.fail;
+
+import java.util.logging.Handler;
+
+import org.junit.After;
+import org.junit.Before;
+import org.slf4j.testHarness.MultithreadedInitializationTest;
+
+public class JDK14MultithreadedInitializationTest extends MultithreadedInitializationTest {
+
+ java.util.logging.Logger julRootLogger = java.util.logging.Logger.getLogger("");
+ java.util.logging.Logger julOrgLogger = java.util.logging.Logger.getLogger("org");
+
+ @Before
+ public void addRecordingHandler() {
+ System.out.println("THREAD_COUNT=" + THREAD_COUNT);
+ removeAllHandlers(julRootLogger);
+ removeAllHandlers(julOrgLogger);
+ julOrgLogger.addHandler(new CountingHandler());
+ }
+
+ private void removeAllHandlers(java.util.logging.Logger logger) {
+ Handler[] handlers = logger.getHandlers();
+ for (Handler handler : handlers) {
+ logger.removeHandler(handler);
+ }
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ removeAllHandlers(julOrgLogger);
+ }
+
+ protected long getRecordedEventCount() {
+ CountingHandler ra = findRecordingHandler();
+ if (ra == null) {
+ fail("failed to fing RecordingHandler");
+ }
+ return ra.eventCount.get();
+ }
+
+ private CountingHandler findRecordingHandler() {
+ Handler[] handlers = julOrgLogger.getHandlers();
+ for (Handler h : handlers) {
+ if (h instanceof CountingHandler)
+ return (CountingHandler) h;
+ }
+ return null;
+ }
+
+}
diff --git a/slf4j-jdk14/src/test/java/org/slf4j/jul/ListHandler.java b/slf4j-jdk14/src/test/java/org/slf4j/jul/ListHandler.java
new file mode 100755
index 00000000..d1ac5f49
--- /dev/null
+++ b/slf4j-jdk14/src/test/java/org/slf4j/jul/ListHandler.java
@@ -0,0 +1,23 @@
+package org.slf4j.jul;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.logging.LogRecord;
+
+public class ListHandler extends java.util.logging.Handler {
+
+ public List<LogRecord> recordList = new ArrayList<>();
+
+ @Override
+ public void publish(LogRecord record) {
+ recordList.add(record);
+ }
+
+ @Override
+ public void flush() {
+ }
+
+ @Override
+ public void close() throws SecurityException {
+ }
+} \ No newline at end of file
diff --git a/slf4j-log4j12/LICENSE.txt b/slf4j-log4j12/LICENSE.txt
index 508a2728..e4079f54 100644
--- a/slf4j-log4j12/LICENSE.txt
+++ b/slf4j-log4j12/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2023 QOS.ch
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-log4j12/pom.xml b/slf4j-log4j12/pom.xml
index d7aad90f..8ba89b56 100755
--- a/slf4j-log4j12/pom.xml
+++ b/slf4j-log4j12/pom.xml
@@ -1,53 +1,32 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
-
+
<artifactId>slf4j-log4j12</artifactId>
-
- <packaging>jar</packaging>
- <name>SLF4J LOG4J-12 Binding</name>
- <description>SLF4J LOG4J-12 Binding</description>
+ <packaging>pom</packaging>
+
+ <name>SLF4J LOG4J-12 Binding relocated</name>
+ <description>SLF4J LOG4J-12 relocated to slf4j-reload4j</description>
<url>http://www.slf4j.org</url>
- <dependencies>
- <dependency>
+ <distributionManagement>
+ <relocation>
<groupId>org.slf4j</groupId>
- <artifactId>slf4j-api</artifactId>
- </dependency>
-
- <dependency>
- <groupId>log4j</groupId>
- <artifactId>log4j</artifactId>
- </dependency>
- </dependencies>
+ <artifactId>slf4j-reload4j</artifactId>
+ <version>2.0.12</version>
+ </relocation>
+ </distributionManagement>
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
- </plugins>
- </build>
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerAdapter.java b/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerAdapter.java
deleted file mode 100755
index 08d3ea0e..00000000
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerAdapter.java
+++ /dev/null
@@ -1,598 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import java.io.Serializable;
-
-import org.apache.log4j.Level;
-import org.slf4j.Logger;
-import org.slf4j.Marker;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MarkerIgnoringBase;
-import org.slf4j.helpers.MessageFormatter;
-import org.slf4j.spi.LocationAwareLogger;
-
-/**
- * A wrapper over {@link org.apache.log4j.Logger org.apache.log4j.Logger} in
- * conforming to the {@link Logger} interface.
- *
- * <p>
- * Note that the logging levels mentioned in this class refer to those defined
- * in the <a
- * href="http://logging.apache.org/log4j/docs/api/org/apache/log4j/Level.html">
- * <code>org.apache.log4j.Level</code></a> class.
- *
- * <p>
- * The TRACE level was introduced in log4j version 1.2.12. In order to avoid
- * crashing the host application, in the case the log4j version in use predates
- * 1.2.12, the TRACE level will be mapped as DEBUG. See also <a
- * href="http://bugzilla.slf4j.org/show_bug.cgi?id=68">bug 68</a>.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public final class Log4jLoggerAdapter extends MarkerIgnoringBase implements LocationAwareLogger, Serializable {
-
- private static final long serialVersionUID = 6182834493563598289L;
-
- final transient org.apache.log4j.Logger logger;
-
- /**
- * Following the pattern discussed in pages 162 through 168 of "The complete
- * log4j manual".
- */
- final static String FQCN = Log4jLoggerAdapter.class.getName();
-
- // Does the log4j version in use recognize the TRACE level?
- // The trace level was introduced in log4j 1.2.12.
- final boolean traceCapable;
-
- // WARN: Log4jLoggerAdapter constructor should have only package access so
- // that
- // only Log4jLoggerFactory be able to create one.
- Log4jLoggerAdapter(org.apache.log4j.Logger logger) {
- this.logger = logger;
- this.name = logger.getName();
- traceCapable = isTraceCapable();
- }
-
- private boolean isTraceCapable() {
- try {
- logger.isTraceEnabled();
- return true;
- } catch (NoSuchMethodError e) {
- return false;
- }
- }
-
- /**
- * Is this logger instance enabled for the TRACE level?
- *
- * @return True if this Logger is enabled for level TRACE, false otherwise.
- */
- public boolean isTraceEnabled() {
- if (traceCapable) {
- return logger.isTraceEnabled();
- } else {
- return logger.isDebugEnabled();
- }
- }
-
- /**
- * Log a message object at level TRACE.
- *
- * @param msg
- * - the message object to be logged
- */
- public void trace(String msg) {
- logger.log(FQCN, traceCapable ? Level.TRACE : Level.DEBUG, msg, null);
- }
-
- /**
- * Log a message at level TRACE according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level TRACE.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void trace(String format, Object arg) {
- if (isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- logger.log(FQCN, traceCapable ? Level.TRACE : Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level TRACE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the TRACE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void trace(String format, Object arg1, Object arg2) {
- if (isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- logger.log(FQCN, traceCapable ? Level.TRACE : Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level TRACE according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the TRACE level.
- * </p>
- *
- * @param format
- * the format string
- * @param arguments
- * an array of arguments
- */
- public void trace(String format, Object... arguments) {
- if (isTraceEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- logger.log(FQCN, traceCapable ? Level.TRACE : Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at level TRACE with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void trace(String msg, Throwable t) {
- logger.log(FQCN, traceCapable ? Level.TRACE : Level.DEBUG, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the DEBUG level?
- *
- * @return True if this Logger is enabled for level DEBUG, false otherwise.
- */
- public boolean isDebugEnabled() {
- return logger.isDebugEnabled();
- }
-
- /**
- * Log a message object at level DEBUG.
- *
- * @param msg
- * - the message object to be logged
- */
- public void debug(String msg) {
- logger.log(FQCN, Level.DEBUG, msg, null);
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for level DEBUG.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void debug(String format, Object arg) {
- if (logger.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- logger.log(FQCN, Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the DEBUG level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void debug(String format, Object arg1, Object arg2) {
- if (logger.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- logger.log(FQCN, Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level DEBUG according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the DEBUG level.
- * </p>
- *
- * @param format
- * the format string
- * @param arguments an array of arguments
- */
- public void debug(String format, Object... arguments) {
- if (logger.isDebugEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, arguments);
- logger.log(FQCN, Level.DEBUG, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at level DEBUG with an accompanying message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void debug(String msg, Throwable t) {
- logger.log(FQCN, Level.DEBUG, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the INFO level?
- *
- * @return True if this Logger is enabled for the INFO level, false otherwise.
- */
- public boolean isInfoEnabled() {
- return logger.isInfoEnabled();
- }
-
- /**
- * Log a message object at the INFO level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void info(String msg) {
- logger.log(FQCN, Level.INFO, msg, null);
- }
-
- /**
- * Log a message at level INFO according to the specified format and argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void info(String format, Object arg) {
- if (logger.isInfoEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- logger.log(FQCN, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the INFO level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void info(String format, Object arg1, Object arg2) {
- if (logger.isInfoEnabled()) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- logger.log(FQCN, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level INFO according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the INFO level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void info(String format, Object... argArray) {
- if (logger.isInfoEnabled()) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- logger.log(FQCN, Level.INFO, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the INFO level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void info(String msg, Throwable t) {
- logger.log(FQCN, Level.INFO, msg, t);
- }
-
- /**
- * Is this logger instance enabled for the WARN level?
- *
- * @return True if this Logger is enabled for the WARN level, false otherwise.
- */
- public boolean isWarnEnabled() {
- return logger.isEnabledFor(Level.WARN);
- }
-
- /**
- * Log a message object at the WARN level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void warn(String msg) {
- logger.log(FQCN, Level.WARN, msg, null);
- }
-
- /**
- * Log a message at the WARN level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void warn(String format, Object arg) {
- if (logger.isEnabledFor(Level.WARN)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- logger.log(FQCN, Level.WARN, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the WARN level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void warn(String format, Object arg1, Object arg2) {
- if (logger.isEnabledFor(Level.WARN)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- logger.log(FQCN, Level.WARN, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level WARN according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the WARN level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void warn(String format, Object... argArray) {
- if (logger.isEnabledFor(Level.WARN)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- logger.log(FQCN, Level.WARN, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the WARN level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void warn(String msg, Throwable t) {
- logger.log(FQCN, Level.WARN, msg, t);
- }
-
- /**
- * Is this logger instance enabled for level ERROR?
- *
- * @return True if this Logger is enabled for level ERROR, false otherwise.
- */
- public boolean isErrorEnabled() {
- return logger.isEnabledFor(Level.ERROR);
- }
-
- /**
- * Log a message object at the ERROR level.
- *
- * @param msg
- * - the message object to be logged
- */
- public void error(String msg) {
- logger.log(FQCN, Level.ERROR, msg, null);
- }
-
- /**
- * Log a message at the ERROR level according to the specified format and
- * argument.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg
- * the argument
- */
- public void error(String format, Object arg) {
- if (logger.isEnabledFor(Level.ERROR)) {
- FormattingTuple ft = MessageFormatter.format(format, arg);
- logger.log(FQCN, Level.ERROR, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at the ERROR level according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param arg1
- * the first argument
- * @param arg2
- * the second argument
- */
- public void error(String format, Object arg1, Object arg2) {
- if (logger.isEnabledFor(Level.ERROR)) {
- FormattingTuple ft = MessageFormatter.format(format, arg1, arg2);
- logger.log(FQCN, Level.ERROR, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log a message at level ERROR according to the specified format and
- * arguments.
- *
- * <p>
- * This form avoids superfluous object creation when the logger is disabled
- * for the ERROR level.
- * </p>
- *
- * @param format
- * the format string
- * @param argArray
- * an array of arguments
- */
- public void error(String format, Object... argArray) {
- if (logger.isEnabledFor(Level.ERROR)) {
- FormattingTuple ft = MessageFormatter.arrayFormat(format, argArray);
- logger.log(FQCN, Level.ERROR, ft.getMessage(), ft.getThrowable());
- }
- }
-
- /**
- * Log an exception (throwable) at the ERROR level with an accompanying
- * message.
- *
- * @param msg
- * the message accompanying the exception
- * @param t
- * the exception (throwable) to log
- */
- public void error(String msg, Throwable t) {
- logger.log(FQCN, Level.ERROR, msg, t);
- }
-
- public void log(Marker marker, String callerFQCN, int level, String msg, Object[] argArray, Throwable t) {
- Level log4jLevel;
- switch (level) {
- case LocationAwareLogger.TRACE_INT:
- log4jLevel = traceCapable ? Level.TRACE : Level.DEBUG;
- break;
- case LocationAwareLogger.DEBUG_INT:
- log4jLevel = Level.DEBUG;
- break;
- case LocationAwareLogger.INFO_INT:
- log4jLevel = Level.INFO;
- break;
- case LocationAwareLogger.WARN_INT:
- log4jLevel = Level.WARN;
- break;
- case LocationAwareLogger.ERROR_INT:
- log4jLevel = Level.ERROR;
- break;
- default:
- throw new IllegalStateException("Level number " + level + " is not recognized.");
- }
- logger.log(callerFQCN, log4jLevel, msg, t);
- }
-
-}
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index 081f28a6..00000000
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.apache.log4j.Level;
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.Util;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- *
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled
- * against. The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
- private static final String loggerFactoryClassStr = Log4jLoggerFactory.class.getName();
-
- /**
- * The ILoggerFactory instance returned by the {@link #getLoggerFactory}
- * method should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- loggerFactory = new Log4jLoggerFactory();
- try {
- @SuppressWarnings("unused")
- Level level = Level.TRACE;
- } catch (NoSuchFieldError nsfe) {
- Util.report("This version of SLF4J requires log4j version 1.2.12 or later. See also http://www.slf4j.org/codes.html#log4j_version");
- }
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 1d255230..00000000
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-
-}
diff --git a/slf4j-log4j12/src/main/resources/META-INF/MANIFEST.MF b/slf4j-log4j12/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 23a42952..00000000
--- a/slf4j-log4j12/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,9 +0,0 @@
-Implementation-Title: slf4j-log4j12
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.log4j12
-Bundle-Name: slf4j-log4j12
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}, org.apache.log4j
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-migrator/LICENSE.txt b/slf4j-migrator/LICENSE.txt
new file mode 100644
index 00000000..1a3d0532
--- /dev/null
+++ b/slf4j-migrator/LICENSE.txt
@@ -0,0 +1,24 @@
+Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
+All rights reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+
+
diff --git a/slf4j-migrator/pom.xml b/slf4j-migrator/pom.xml
index 33ad8e98..98ef9ddb 100755
--- a/slf4j-migrator/pom.xml
+++ b/slf4j-migrator/pom.xml
@@ -1,14 +1,14 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-migrator</artifactId>
@@ -17,30 +17,23 @@
<name>SLF4J Migrator</name>
<description>SLF4J Migrator</description>
-
<build>
<plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-compiler-plugin</artifactId>
- <configuration>
- <source>${required.jdk.version}</source>
- <target>${required.jdk.version}</target>
- </configuration>
- </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
+ <version>${maven-jar-plugin.version}</version>
<configuration>
<archive>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ <manifest>
+ <mainClass>org.slf4j.migrator.Main</mainClass>
+ </manifest>
</archive>
</configuration>
</plugin>
</plugins>
-
</build>
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/FileSelector.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/FileSelector.java
index 71af29bd..0e8d13c8 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/FileSelector.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/FileSelector.java
@@ -32,7 +32,7 @@ import org.slf4j.migrator.internal.ProgressListener;
public class FileSelector {
- private List<File> javaFileList = new ArrayList<File>();
+ private final List<File> javaFileList = new ArrayList<>();
ProgressListener pl;
@@ -54,8 +54,8 @@ public class FileSelector {
pl.onDirectory(file);
File[] files = file.listFiles();
if (files != null) {
- for (int i = 0; i < files.length; i++) {
- selectFiles(files[i]);
+ for (File value : files) {
+ selectFiles(value);
}
}
} else {
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/InplaceFileConverter.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/InplaceFileConverter.java
index d4bf3e63..cecb1be8 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/InplaceFileConverter.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/InplaceFileConverter.java
@@ -102,8 +102,8 @@ public class InplaceFileConverter {
}
private void writeReplacement(OutputStream os, String[] replacement) throws IOException {
- for (int i = 0; i < replacement.length; i++) {
- os.write(replacement[i].getBytes());
+ for (String s : replacement) {
+ os.write(s.getBytes());
os.write(lineTerminator.getBytes());
}
}
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/Main.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/Main.java
index 5a94a41d..bbb1b9cc 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/Main.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/Main.java
@@ -38,12 +38,10 @@ public class Main {
public static void main(String[] args) {
System.out.println("Starting SLF4J Migrator");
- SwingUtilities.invokeLater(new Runnable() {
- public void run() {
- MigratorFrame inst = new MigratorFrame();
- inst.setLocationRelativeTo(null);
- inst.setVisible(true);
- }
+ SwingUtilities.invokeLater(() -> {
+ MigratorFrame inst = new MigratorFrame();
+ inst.setLocationRelativeTo(null);
+ inst.setVisible(true);
});
}
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/ProjectConverter.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/ProjectConverter.java
index 99f1a194..f7947577 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/ProjectConverter.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/ProjectConverter.java
@@ -27,7 +27,6 @@ package org.slf4j.migrator;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
-import java.util.Iterator;
import java.util.List;
import javax.swing.SwingUtilities;
@@ -38,25 +37,23 @@ import org.slf4j.migrator.line.RuleSet;
public class ProjectConverter {
- private RuleSet ruleSet;
+ private final RuleSet ruleSet;
private List<ConversionException> exception;
ProgressListener progressListener;
- public static void main(String[] args) throws IOException {
- SwingUtilities.invokeLater(new Runnable() {
- public void run() {
- MigratorFrame inst = new MigratorFrame();
- inst.setLocationRelativeTo(null);
- inst.setVisible(true);
- }
+ public static void main(String[] args) {
+ SwingUtilities.invokeLater(() -> {
+ MigratorFrame inst = new MigratorFrame();
+ inst.setLocationRelativeTo(null);
+ inst.setVisible(true);
});
}
/**
* Ask for concrete matcher implementation depending on the conversion mode
* Ask for user confirmation to convert the selected source directory if valid
- * Ask for user confirmation in case of number of files to convert > 1000
+ * Ask for user confirmation in case of number of files to convert &gt; 1000
*
* @param conversionType
* @param progressListener
@@ -83,9 +80,7 @@ public class ProjectConverter {
*/
private void scanFileList(List<File> lstFiles) {
progressListener.onFileScanBegin();
- Iterator<File> itFile = lstFiles.iterator();
- while (itFile.hasNext()) {
- File currentFile = itFile.next();
+ for (File currentFile : lstFiles) {
progressListener.onFileScan(currentFile);
scanFile(currentFile);
}
@@ -108,16 +103,14 @@ public class ProjectConverter {
public void addException(ConversionException exc) {
if (exception == null) {
- exception = new ArrayList<ConversionException>();
+ exception = new ArrayList<>();
}
exception.add(exc);
}
public void printException() {
if (exception != null) {
- Iterator<ConversionException> iterator = exception.iterator();
- while (iterator.hasNext()) {
- ConversionException exc = (ConversionException) iterator.next();
+ for (ConversionException exc : exception) {
exc.print();
}
exception = null;
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/helper/Abbreviator.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/helper/Abbreviator.java
index f2f9b35d..519a3f04 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/helper/Abbreviator.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/helper/Abbreviator.java
@@ -44,11 +44,11 @@ public class Abbreviator {
int firstIndex = filename.indexOf(folderSeparator, invariantPrefixLength);
if (firstIndex == -1) {
- // we cant't process this string
+ // we can't process this string
return filename;
}
StringBuilder buf = new StringBuilder(desiredLength);
- buf.append(filename.substring(0, firstIndex + 1));
+ buf.append(filename, 0, firstIndex + 1);
buf.append(FILLER);
int nextIndex = computeNextIndex(filename, firstIndex);
if (nextIndex != -1) {
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/internal/MigratorFrame.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/internal/MigratorFrame.java
index 377ac6e5..3ab15c60 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/internal/MigratorFrame.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/internal/MigratorFrame.java
@@ -46,16 +46,6 @@ import javax.swing.WindowConstants;
import org.slf4j.migrator.Constant;
import org.slf4j.migrator.helper.SpringLayoutHelper;
-/**
- * This code was edited or generated using CloudGarden's Jigloo SWT/Swing GUI
- * Builder, which is free for non-commercial use. If Jigloo is being used
- * commercially (ie, by a corporation, company or business for any purpose
- * whatever) then you should purchase a license for each developer using Jigloo.
- * Please visit www.cloudgarden.com for details. Use of Jigloo implies
- * acceptance of these licensing terms. A COMMERCIAL LICENSE HAS NOT BEEN
- * PURCHASED FOR THIS MACHINE, SO JIGLOO OR THIS CODE CANNOT BE USED LEGALLY FOR
- * ANY CORPORATE OR COMMERCIAL PURPOSE.
- */
public class MigratorFrame extends JFrame implements ActionListener {
private static final long serialVersionUID = 1L;
@@ -68,8 +58,8 @@ public class MigratorFrame extends JFrame implements ActionListener {
static final int X_SIZE = 700;
static final int Y_SIZE = 400;
- private SpringLayout layoutManager = new SpringLayout();
- private SpringLayoutHelper slh = new SpringLayoutHelper(layoutManager, BASIC_PADDING);
+ private final SpringLayout layoutManager = new SpringLayout();
+ private final SpringLayoutHelper slh = new SpringLayoutHelper(layoutManager, BASIC_PADDING);
private JLabel migrationLabel;
@@ -138,7 +128,7 @@ public class MigratorFrame extends JFrame implements ActionListener {
*/
private void constrainAll() {
- // contrain migration label
+ // constraints migration label
layoutManager.putConstraint(SpringLayout.WEST, migrationLabel, BASIC_PADDING, SpringLayout.EAST, this);
layoutManager.putConstraint(SpringLayout.NORTH, migrationLabel, BASIC_PADDING, SpringLayout.NORTH, this);
@@ -239,14 +229,14 @@ public class MigratorFrame extends JFrame implements ActionListener {
private void createAwareLabel() {
awareLabel = new JLabel();
- awareLabel.setText("<html>" + "<p>I am aware that this tool will directly modify all Java source files</p>"
- + "<p>in the selected folder without creating backup files.</p>" + "</html>");
+ awareLabel.setText("<html>" + "<p>I am aware that this tool will directly modify all Java source files"
+ + "<p>in the selected folder without creating backup files." + "</html>");
}
private void createWarningLabel() {
warningLabel = new JLabel();
- warningLabel.setText("<html>" + "<p><span color=\"red\">WARNING:</span> This SLF4J migration tool will directly modify all Java source files</p>"
- + "<p>in the selected project folder without creating a backup of the original files.</p>" + "</html>");
+ warningLabel.setText("<html>" + "<p><span color=\"red\">WARNING:</span> This SLF4J migration tool will directly modify all Java source files"
+ + "<p>in the selected project folder without creating a backup of the original files." + "</html>");
}
private void createMigrateButton() {
@@ -323,7 +313,7 @@ public class MigratorFrame extends JFrame implements ActionListener {
List<String> doSanityAnalysis() {
- List<String> errorList = new ArrayList<String>();
+ List<String> errorList = new ArrayList<>();
if (!radioJCL.isSelected() && !radioLog4j.isSelected() && !radioJUL.isSelected()) {
errorList.add("Please select the migration type: JCL, log4j, or JUL to SLF4J.");
}
@@ -351,7 +341,7 @@ public class MigratorFrame extends JFrame implements ActionListener {
buf.append(i);
buf.append(". ");
buf.append(msg);
- buf.append("</p>");
+ buf.append("");
i++;
}
buf.append("</html>");
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/EmptyRuleSet.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/EmptyRuleSet.java
index a0393265..3533d0e3 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/EmptyRuleSet.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/EmptyRuleSet.java
@@ -30,7 +30,7 @@ import java.util.List;
public class EmptyRuleSet implements RuleSet {
- List<ConversionRule> list = new ArrayList<ConversionRule>();
+ List<ConversionRule> list = new ArrayList<>();
public Iterator<ConversionRule> iterator() {
return list.iterator();
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JCLRuleSet.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JCLRuleSet.java
index f463e46d..8367d508 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JCLRuleSet.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JCLRuleSet.java
@@ -36,7 +36,7 @@ import java.util.regex.Pattern;
*/
public class JCLRuleSet implements RuleSet {
- private ArrayList<ConversionRule> conversionRuleList;
+ private final ArrayList<ConversionRule> conversionRuleList;
public JCLRuleSet() {
// matching : import org.apache.commons.logging.LogFactory;
@@ -54,7 +54,7 @@ public class JCLRuleSet implements RuleSet {
SingleConversionRule cr5 = new SingleConversionRule(Pattern.compile("LogFactory.getLog\\("), "LoggerFactory.getLogger(");
- conversionRuleList = new ArrayList<ConversionRule>();
+ conversionRuleList = new ArrayList<>();
conversionRuleList.add(cr0);
conversionRuleList.add(cr1);
conversionRuleList.add(cr2);
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JULRuleSet.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JULRuleSet.java
index b296b70a..da5f3378 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JULRuleSet.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/JULRuleSet.java
@@ -36,7 +36,7 @@ import java.util.regex.Pattern;
*/
public class JULRuleSet implements RuleSet {
- private ArrayList<ConversionRule> conversionRuleList;
+ private final ArrayList<ConversionRule> conversionRuleList;
public JULRuleSet() {
@@ -55,7 +55,7 @@ public class JULRuleSet implements RuleSet {
SingleConversionRule crWarning = new SingleConversionRule(Pattern.compile("\\.warning\\("), ".warn(");
SingleConversionRule crSevere = new SingleConversionRule(Pattern.compile("\\.severe\\("), ".error(");
- conversionRuleList = new ArrayList<ConversionRule>();
+ conversionRuleList = new ArrayList<>();
conversionRuleList.add(crImport0);
conversionRuleList.add(crImport1);
conversionRuleList.add(crImport2);
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/Log4jRuleSet.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/Log4jRuleSet.java
index c760496c..e07aa73a 100755
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/Log4jRuleSet.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/Log4jRuleSet.java
@@ -30,7 +30,7 @@ import java.util.regex.Pattern;
public class Log4jRuleSet implements RuleSet {
- private ArrayList<ConversionRule> conversionRuleList;
+ private final ArrayList<ConversionRule> conversionRuleList;
public Log4jRuleSet() {
@@ -57,7 +57,7 @@ public class Log4jRuleSet implements RuleSet {
SingleConversionRule variable1 = new SingleConversionRule(Pattern.compile("(^Category\\b)"), "Logger");
- conversionRuleList = new ArrayList<ConversionRule>();
+ conversionRuleList = new ArrayList<>();
conversionRuleList.add(crImport0);
conversionRuleList.add(catImport);
conversionRuleList.add(crImport1);
diff --git a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/MultiGroupConversionRule.java b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/MultiGroupConversionRule.java
index ce1ee520..f0769406 100644
--- a/slf4j-migrator/src/main/java/org/slf4j/migrator/line/MultiGroupConversionRule.java
+++ b/slf4j-migrator/src/main/java/org/slf4j/migrator/line/MultiGroupConversionRule.java
@@ -40,8 +40,8 @@ public class MultiGroupConversionRule implements ConversionRule {
// our conversion reg-expressions
final private static int MAX_GROUPS = 10;
- private Pattern pattern;
- private String[] replacementTable = new String[MAX_GROUPS];
+ private final Pattern pattern;
+ private final String[] replacementTable = new String[MAX_GROUPS];
public MultiGroupConversionRule(Pattern pattern) {
this.pattern = pattern;
diff --git a/slf4j-migrator/src/main/resources/META-INF/MANIFEST.MF b/slf4j-migrator/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 10f5bdf3..00000000
--- a/slf4j-migrator/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1 +0,0 @@
-Main-Class: org.slf4j.migrator.Main \ No newline at end of file
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/AternativeApproach.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/AternativeApproach.java
index d4b090a2..0626b871 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/AternativeApproach.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/AternativeApproach.java
@@ -34,7 +34,7 @@ import junit.framework.TestCase;
public class AternativeApproach extends TestCase {
/**
- * In this test we see that we cans use more simple Pattern to do the
+ * In this test we see that we can use more simple Pattern to do the
* conversion
*
*/
@@ -55,7 +55,7 @@ public class AternativeApproach extends TestCase {
/**
* In this test we replace, using the simple Pattern (Log), the full Log
- * declaration and instanciation. This is not convenient because we will also
+ * declaration and instantiation. This is not convenient because we will also
* replace all String containing "Log".
*/
public void test2() {
@@ -82,7 +82,7 @@ public class AternativeApproach extends TestCase {
}
/**
- * In this test we use a simple Pattern to replace the log instanciation
+ * In this test we use a simple Pattern to replace the log instantiation
* without influence on Log declaration.
*
*/
@@ -101,7 +101,7 @@ public class AternativeApproach extends TestCase {
/**
* In this test we try to replace keyword Log without influence on String
- * containg Log We see that we have to use two differents Patterns
+ * containing Log We see that we have to use two different Patterns
*/
public void test4() {
Pattern pat = Pattern.compile("(\\sLog\\b)");
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/FileConverterTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/FileConverterTest.java
index 9f3eb461..4e1b1382 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/FileConverterTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/FileConverterTest.java
@@ -27,29 +27,15 @@ package org.slf4j.migrator;
import java.io.File;
import java.io.IOException;
-import junit.framework.TestCase;
-
-import org.slf4j.migrator.InplaceFileConverter;
+import org.junit.Ignore;
+import org.junit.Test;
import org.slf4j.migrator.internal.NopProgressListener;
import org.slf4j.migrator.line.EmptyRuleSet;
-public class FileConverterTest extends TestCase {
-
- public FileConverterTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- }
-
- public void test() {
- }
+public class FileConverterTest {
+ @Test
+ @Ignore
public void XtestNOP() throws IOException {
InplaceFileConverter fc = new InplaceFileConverter(new EmptyRuleSet(), new NopProgressListener());
fc.convert(new File("c:/varargs.txt"));
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/ProjectConverterTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/ProjectConverterTest.java
index a8cee0bf..537ba3f4 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/ProjectConverterTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/ProjectConverterTest.java
@@ -26,17 +26,17 @@ package org.slf4j.migrator;
import java.io.File;
-import org.slf4j.migrator.Constant;
-import org.slf4j.migrator.ProjectConverter;
+import org.junit.Ignore;
+import org.junit.Test;
import org.slf4j.migrator.internal.NopProgressListener;
-import junit.framework.TestCase;
-
-public class ProjectConverterTest extends TestCase {
+public class ProjectConverterTest {
public void test() {
}
+ @Test
+ @Ignore
public void XtestBarracuda() {
ProjectConverter pc = new ProjectConverter(Constant.LOG4J_TO_SLF4J, new NopProgressListener());
File projectFolder = new File("c:/home/ceki//Varia/Barracuda");
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/AbbreviatorTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/AbbreviatorTest.java
index ab8c8cbb..ac470b88 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/AbbreviatorTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/AbbreviatorTest.java
@@ -24,11 +24,12 @@
*/
package org.slf4j.migrator.helper;
-import org.slf4j.migrator.helper.Abbreviator;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
-import junit.framework.TestCase;
+import org.junit.Test;
-public class AbbreviatorTest extends TestCase {
+public class AbbreviatorTest {
static final char FS = '/';
static final String INPUT_0 = "/abc/123456/ABC";
@@ -36,18 +37,7 @@ public class AbbreviatorTest extends TestCase {
RandomHelper rh = new RandomHelper(FS);
- public AbbreviatorTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- }
-
+ @Test
public void testSmoke() {
{
Abbreviator abb = new Abbreviator(2, 100, FS);
@@ -67,6 +57,7 @@ public class AbbreviatorTest extends TestCase {
}
}
+ @Test
public void testImpossibleToAbbreviate() {
Abbreviator abb = new Abbreviator(2, 20, FS);
String in = "iczldqwivpgm/mgrmvbjdxrwmqgprdjusth";
@@ -74,6 +65,7 @@ public class AbbreviatorTest extends TestCase {
assertEquals(in, r);
}
+ @Test
public void testNoFS() {
Abbreviator abb = new Abbreviator(2, 100, FS);
String r = abb.abbreviate("hello");
@@ -81,6 +73,7 @@ public class AbbreviatorTest extends TestCase {
}
+ @Test
public void testZeroPrefix() {
{
Abbreviator abb = new Abbreviator(0, 100, FS);
@@ -89,6 +82,7 @@ public class AbbreviatorTest extends TestCase {
}
}
+ @Test
public void testTheories() {
int MAX_RANDOM_FIXED_LEN = 20;
int MAX_RANDOM_AVG_LEN = 20;
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/RandomHelper.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/RandomHelper.java
index 1928daaa..f0e304ca 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/RandomHelper.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/helper/RandomHelper.java
@@ -28,7 +28,7 @@ import java.util.Random;
public class RandomHelper {
- private Random random = new Random(100);
+ private final Random random = new Random(100);
final char folderSeparator;
RandomHelper(char folderSeparator) {
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/JCLRuleSetTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/JCLRuleSetTest.java
index 442b0cf6..f480229a 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/JCLRuleSetTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/JCLRuleSetTest.java
@@ -24,15 +24,15 @@
*/
package org.slf4j.migrator.line;
-import org.slf4j.migrator.line.JCLRuleSet;
-import org.slf4j.migrator.line.LineConverter;
+import static org.junit.Assert.assertEquals;
-import junit.framework.TestCase;
+import org.junit.Test;
-public class JCLRuleSetTest extends TestCase {
+public class JCLRuleSetTest {
LineConverter jclConverter = new LineConverter(new JCLRuleSet());
+ @Test
public void testImportReplacement() {
// LogFactory import replacement
assertEquals("import org.slf4j.LoggerFactory;", jclConverter.getOneLineReplacement("import org.apache.commons.logging.LogFactory;"));
@@ -40,6 +40,7 @@ public class JCLRuleSetTest extends TestCase {
assertEquals("import org.slf4j.Logger;", jclConverter.getOneLineReplacement("import org.apache.commons.logging.Log;"));
}
+ @Test
public void testLogFactoryGetLogReplacement() {
// Logger declaration and instanciation without modifier
assertEquals(" Logger l = LoggerFactory.getLogger(MyClass.class);",
@@ -65,6 +66,7 @@ public class JCLRuleSetTest extends TestCase {
jclConverter.getOneLineReplacement("// myLog = LogFactory.getLog(MyClass.class);//logger instanciation"));
}
+ @Test
public void testLogFactoryGetFactoryReplacement() {
// Logger declaration and instanciation without modifier
@@ -91,6 +93,7 @@ public class JCLRuleSetTest extends TestCase {
jclConverter.getOneLineReplacement("// myLog = LogFactory.getFactory().getInstance(MyClass.class);//logger instanciation"));
}
+ @Test
public void testLogDeclarationReplacement() {
// simple Logger declaration
@@ -106,6 +109,7 @@ public class JCLRuleSetTest extends TestCase {
assertEquals("//private Logger myLog;", jclConverter.getOneLineReplacement("//private Log myLog;"));
}
+ @Test
public void testMultiLineReplacement() {
// Logger declaration on a line
assertEquals("protected Logger log =", jclConverter.getOneLineReplacement("protected Log log ="));
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/NoConversionTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/NoConversionTest.java
index 7160193b..60b1fdbf 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/NoConversionTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/NoConversionTest.java
@@ -24,18 +24,17 @@
*/
package org.slf4j.migrator.line;
-import org.slf4j.migrator.line.JCLRuleSet;
-import org.slf4j.migrator.line.LineConverter;
-import org.slf4j.migrator.line.Log4jRuleSet;
+import static org.junit.Assert.assertEquals;
-import junit.framework.TestCase;
+import org.junit.Test;
-public class NoConversionTest extends TestCase {
+public class NoConversionTest {
/**
* This test shows that performing JCL to SLF4J conversion has no impact on
* Log4j implementation
*/
+ @Test
public void testJclOverLog4jConversion() {
// running jcl to slf4j conversion
// JCLMatcher jclMatcher =
@@ -56,6 +55,7 @@ public class NoConversionTest extends TestCase {
* This test shows that performing Log4j to SLF4J conversion has no impact on
* JCL implementation
*/
+ @Test
public void testLog4jOverJclConversion() {
// running log4j to slf4j conversion
LineConverter log4jConverter = new LineConverter(new Log4jRuleSet());
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcher.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcher.java
index d392769b..032bddca 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcher.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcher.java
@@ -35,23 +35,23 @@ import org.slf4j.migrator.line.SingleConversionRule;
class TrivialMatcher implements RuleSet {
- private ArrayList<ConversionRule> conversionRuleList;
+ private final ArrayList<ConversionRule> conversionRuleList;
public TrivialMatcher() {
// simple rule no capturing group is defined, we use default capturing group which is group zero
SingleConversionRule cr = new SingleConversionRule(Pattern.compile("import org.slf4j.converter"), "simple replacement with an unique capturing group");
- // we define 4 differents capturing groups
+ // we define 4 different capturing groups
MultiGroupConversionRule cr1 = new MultiGroupConversionRule(Pattern.compile("(first group)( second group)( third group)( 4th group)"));
// group zero is ignored during treatment
// replacement for the first
cr1.addReplacement(1, "1st group");
- // no replacement for the second group it will remains the same
+ // no replacement for the second group it will remain the same
// empty string for the third group it will be deleted
cr1.addReplacement(3, "");
- // no replacement for the third group it will remains the same
+ // no replacement for the third group it will remain the same
- conversionRuleList = new ArrayList<ConversionRule>();
+ conversionRuleList = new ArrayList<>();
conversionRuleList.add(cr);
conversionRuleList.add(cr1);
}
@@ -60,4 +60,4 @@ class TrivialMatcher implements RuleSet {
return conversionRuleList.iterator();
}
-} \ No newline at end of file
+}
diff --git a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcherTest.java b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcherTest.java
index b5b3c6d4..0a9194df 100644
--- a/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcherTest.java
+++ b/slf4j-migrator/src/test/java/org/slf4j/migrator/line/TrivialMatcherTest.java
@@ -24,12 +24,13 @@
*/
package org.slf4j.migrator.line;
-import org.slf4j.migrator.line.LineConverter;
+import static org.junit.Assert.assertEquals;
-import junit.framework.TestCase;
+import org.junit.Test;
-public class TrivialMatcherTest extends TestCase {
+public class TrivialMatcherTest {
+ @Test
public void testSimpleReplacement() {
LineConverter trivialLC = new LineConverter(new TrivialMatcher());
diff --git a/slf4j-nop/LICENSE.txt b/slf4j-nop/LICENSE.txt
index 508a2728..e4079f54 100644
--- a/slf4j-nop/LICENSE.txt
+++ b/slf4j-nop/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2023 QOS.ch
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-nop/pom.xml b/slf4j-nop/pom.xml
index e0da3a69..18fd0c44 100755
--- a/slf4j-nop/pom.xml
+++ b/slf4j-nop/pom.xml
@@ -1,23 +1,28 @@
-<project
- xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-nop</artifactId>
<packaging>jar</packaging>
- <name>SLF4J NOP Binding</name>
- <description>SLF4J NOP Binding</description>
+ <name>SLF4J NOP Provider</name>
+ <description>SLF4J NOP Provider</description>
<url>http://www.slf4j.org</url>
+ <properties>
+ <module-name>org.slf4j.nop</module-name>
+ <slf4j.provider.implementation>org.slf4j.nop.NOPServiceProvider</slf4j.provider.implementation>
+ <slf4j.provider.type>nop</slf4j.provider.type>
+ </properties>
<dependencies>
<dependency>
@@ -26,25 +31,4 @@
</dependency>
</dependencies>
- <build>
- <plugins>
-
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
- </plugins>
-
- </build>
-
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-nop/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-nop/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index 10a947a6..00000000
--- a/slf4j-nop/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.NOPLoggerFactory;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- *
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled against.
- * The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
- private static final String loggerFactoryClassStr = NOPLoggerFactory.class.getName();
-
- /** The ILoggerFactory instance returned by the {@link #getLoggerFactory} method
- * should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- loggerFactory = new NOPLoggerFactory();
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-nop/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-nop/src/main/java/org/slf4j/impl/StaticMDCBinder.java
deleted file mode 100644
index 086b0169..00000000
--- a/slf4j-nop/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.helpers.NOPMDCAdapter;
-import org.slf4j.spi.MDCAdapter;
-
-/**
- * This implementation is bound to {@link NOPMDCAdapter}.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link StaticMDCBinder}.
- */
- public MDCAdapter getMDCA() {
- return new NOPMDCAdapter();
- }
-
- public String getMDCAdapterClassStr() {
- return NOPMDCAdapter.class.getName();
- }
-}
diff --git a/slf4j-nop/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-nop/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 1d255230..00000000
--- a/slf4j-nop/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-
-}
diff --git a/slf4j-nop/src/main/java/org/slf4j/nop/NOPServiceProvider.java b/slf4j-nop/src/main/java/org/slf4j/nop/NOPServiceProvider.java
new file mode 100755
index 00000000..515cf23b
--- /dev/null
+++ b/slf4j-nop/src/main/java/org/slf4j/nop/NOPServiceProvider.java
@@ -0,0 +1,46 @@
+package org.slf4j.nop;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.helpers.NOPLoggerFactory;
+import org.slf4j.helpers.NOPMDCAdapter;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class NOPServiceProvider implements SLF4JServiceProvider {
+
+ /**
+ * Declare the version of the SLF4J API this implementation is compiled against.
+ * The value of this field is modified with each major release.
+ */
+ // to avoid constant folding by the compiler, this field must *not* be final
+ public static String REQUESTED_API_VERSION = "2.0.99"; // !final
+
+ private final ILoggerFactory loggerFactory = new NOPLoggerFactory();
+ private final IMarkerFactory markerFactory = new BasicMarkerFactory();
+ private final MDCAdapter mdcAdapter = new NOPMDCAdapter();
+
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return REQUESTED_API_VERSION;
+ }
+
+ public void initialize() {
+
+ }
+
+
+}
diff --git a/slf4j-nop/src/main/java9/module-info.java b/slf4j-nop/src/main/java9/module-info.java
new file mode 100755
index 00000000..53e1f40a
--- /dev/null
+++ b/slf4j-nop/src/main/java9/module-info.java
@@ -0,0 +1,7 @@
+module org.slf4j.nop {
+ requires org.slf4j;
+ provides org.slf4j.spi.SLF4JServiceProvider with org.slf4j.nop.NOPServiceProvider;
+
+ exports org.slf4j.nop;
+ opens org.slf4j.nop to org.slf4j;
+}
diff --git a/slf4j-nop/src/main/resources/META-INF/MANIFEST.MF b/slf4j-nop/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index c009d03d..00000000
--- a/slf4j-nop/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,9 +0,0 @@
-Implementation-Title: slf4j-nop
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.nop
-Bundle-Name: slf4j-nop
-Bundle-Vendor: SLF4J.ORG
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-nop/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider b/slf4j-nop/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
new file mode 100755
index 00000000..9929e9df
--- /dev/null
+++ b/slf4j-nop/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
@@ -0,0 +1 @@
+org.slf4j.nop.NOPServiceProvider \ No newline at end of file
diff --git a/slf4j-nop/src/test/java/org/slf4j/InvocationTest.java b/slf4j-nop/src/test/java/org/slf4j/nop/InvocationTest.java
index ea57d374..8cb7c036 100644
--- a/slf4j-nop/src/test/java/org/slf4j/InvocationTest.java
+++ b/slf4j-nop/src/test/java/org/slf4j/nop/InvocationTest.java
@@ -22,11 +22,16 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.nop;
-import java.io.Closeable;
-import java.io.IOException;
-import junit.framework.TestCase;
+import static org.junit.Assert.assertNull;
+
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
/**
* Test whether invoking the SLF4J API causes problems or not.
@@ -34,29 +39,19 @@ import junit.framework.TestCase;
* @author Ceki Gulcu
*
*/
-public class InvocationTest extends TestCase {
-
- public InvocationTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
- super.tearDown();
- }
+public class InvocationTest {
+ @Test
public void test1() {
Logger logger = LoggerFactory.getLogger("test1");
logger.debug("Hello world.");
}
+ @Test
public void test2() {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
+ Integer i1 = Integer.valueOf(1);
+ Integer i2 = Integer.valueOf(2);
+ Integer i3 = Integer.valueOf(3);
Exception e = new Exception("This is a test exception.");
Logger logger = LoggerFactory.getLogger("test2");
@@ -72,10 +67,11 @@ public class InvocationTest extends TestCase {
logger.warn("Hello world 3", e);
logger.error("Hello world 4.");
- logger.error("Hello world {}", new Integer(3));
+ logger.error("Hello world {}", Integer.valueOf(3));
logger.error("Hello world 4.", e);
}
+ @Test
public void testNull() {
Logger logger = LoggerFactory.getLogger("testNull");
logger.debug(null);
@@ -90,6 +86,7 @@ public class InvocationTest extends TestCase {
logger.error(null, e);
}
+ @Test
public void testMarker() {
Logger logger = LoggerFactory.getLogger("testMarker");
Marker blue = MarkerFactory.getMarker("BLUE");
@@ -109,6 +106,7 @@ public class InvocationTest extends TestCase {
logger.error(blue, "hello {} and {} ", "world", "universe");
}
+ @Test
public void testMDC() {
MDC.put("k", "v");
assertNull(MDC.get("k"));
@@ -117,6 +115,7 @@ public class InvocationTest extends TestCase {
MDC.clear();
}
+ @Test
public void testMDCCloseable() {
MDC.MDCCloseable closeable = MDC.putCloseable("k", "v");
assertNull(MDC.get("k"));
diff --git a/slf4j-nop/src/test/java/org/slf4j/nop/MultithreadedInitializationTest.java b/slf4j-nop/src/test/java/org/slf4j/nop/MultithreadedInitializationTest.java
new file mode 100755
index 00000000..9cd0bc0c
--- /dev/null
+++ b/slf4j-nop/src/test/java/org/slf4j/nop/MultithreadedInitializationTest.java
@@ -0,0 +1,150 @@
+/**
+ * Copyright (c) 2004-2016 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.nop;
+
+import static org.junit.Assert.assertEquals;
+
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Random;
+import java.util.concurrent.BrokenBarrierException;
+import java.util.concurrent.CyclicBarrier;
+import java.util.concurrent.atomic.AtomicLong;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.LoggerFactoryFriend;
+
+public class MultithreadedInitializationTest {
+
+ final static int THREAD_COUNT = 4 + Runtime.getRuntime().availableProcessors() * 2;
+
+ private static final AtomicLong EVENT_COUNT = new AtomicLong(0);
+
+ final CyclicBarrier barrier = new CyclicBarrier(THREAD_COUNT + 1);
+
+ int diff = new Random().nextInt(10000);
+ String loggerName = "org.slf4j.impl.MultithreadedInitializationTest";
+ private final PrintStream oldErr = System.err;
+ StringPrintStream sps = new StringPrintStream(oldErr);
+
+ @Before
+ public void setup() {
+ LoggerFactoryFriend.reset();
+ System.setErr(sps);
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ LoggerFactoryFriend.reset();
+ System.setErr(oldErr);
+ }
+
+ @Test
+ public void multiThreadedInitialization() throws InterruptedException, BrokenBarrierException {
+ System.out.println("THREAD_COUNT=" + THREAD_COUNT);
+ LoggerAccessingThread[] accessors = harness();
+
+ for (LoggerAccessingThread accessor : accessors) {
+ EVENT_COUNT.getAndIncrement();
+ accessor.logger.info("post harness");
+ }
+
+ Logger logger = LoggerFactory.getLogger(loggerName + ".slowInitialization-" + diff);
+ logger.info("hello");
+ EVENT_COUNT.getAndIncrement();
+
+ assertEquals(0, sps.stringList.size());
+ }
+
+ private static LoggerAccessingThread[] harness() throws InterruptedException, BrokenBarrierException {
+ LoggerAccessingThread[] threads = new LoggerAccessingThread[THREAD_COUNT];
+ final CyclicBarrier barrier = new CyclicBarrier(THREAD_COUNT + 1);
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i] = new LoggerAccessingThread(barrier, i);
+ threads[i].start();
+ }
+
+ barrier.await();
+ for (int i = 0; i < THREAD_COUNT; i++) {
+ threads[i].join();
+ }
+ return threads;
+ }
+
+ static class LoggerAccessingThread extends Thread {
+ final CyclicBarrier barrier;
+ Logger logger;
+ int count;
+
+ LoggerAccessingThread(CyclicBarrier barrier, int count) {
+ this.barrier = barrier;
+ this.count = count;
+ }
+
+ public void run() {
+ try {
+ barrier.await();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ logger = LoggerFactory.getLogger(this.getClass().getName() + "-" + count);
+ logger.info("in run method");
+ EVENT_COUNT.getAndIncrement();
+ }
+ };
+
+ public static class StringPrintStream extends PrintStream {
+
+ public static final String LINE_SEP = System.getProperty("line.separator");
+ PrintStream other;
+ List<String> stringList = new ArrayList<>();
+
+ public StringPrintStream(PrintStream ps) {
+ super(ps);
+ other = ps;
+ }
+
+ public void print(String s) {
+ other.print(s);
+ stringList.add(s);
+ }
+
+ public void println(String s) {
+ other.println(s);
+ stringList.add(s);
+ }
+
+ public void println(Object o) {
+ other.println(o);
+ stringList.add(o.toString());
+ }
+ };
+
+}
diff --git a/slf4j-reload4j/LICENSE.txt b/slf4j-reload4j/LICENSE.txt
new file mode 100644
index 00000000..96084119
--- /dev/null
+++ b/slf4j-reload4j/LICENSE.txt
@@ -0,0 +1,24 @@
+Copyright (c) 2004-2023 QOS.ch Sarl (Switzerland)
+All rights reserved.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+
+
diff --git a/slf4j-reload4j/pom.xml b/slf4j-reload4j/pom.xml
new file mode 100644
index 00000000..3dadcd66
--- /dev/null
+++ b/slf4j-reload4j/pom.xml
@@ -0,0 +1,71 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-parent</artifactId>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
+ </parent>
+
+ <artifactId>slf4j-reload4j</artifactId>
+
+
+ <packaging>jar</packaging>
+ <name>SLF4J Reload4j Provider</name>
+ <description>SLF4J Reload4j Provider</description>
+ <url>http://reload4j.qos.ch</url>
+
+ <properties>
+ <slf4j.provider.implementation>org.slf4j.reload4j.Reload4jServiceProvider</slf4j.provider.implementation>
+ <slf4j.provider.type>reload4j</slf4j.provider.type>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>ch.qos.reload4j</groupId>
+ <artifactId>reload4j</artifactId>
+ </dependency>
+
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ <type>test-jar</type>
+ <version>${project.version}</version>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
+
+
+ <build>
+ <plugins>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-surefire-plugin</artifactId>
+ <version>2.19.1</version>
+ <configuration>
+ <forkCount>1</forkCount>
+ <reuseForks>false</reuseForks>
+ <reportFormat>plain</reportFormat>
+ <trimStackTrace>false</trimStackTrace>
+ <excludes>
+ <exclude>**/AllTest.java</exclude>
+ <exclude>**/PackageTest.java</exclude>
+ </excludes>
+ <argLine>-Xdebug -Xnoagent -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=8001</argLine>
+ <!--<argLine>XXadd-opens log4j/org.apache.log4j=org.slf4j.log4j12</argLine>-->
+ </configuration>
+ </plugin>
+
+ </plugins>
+ </build>
+</project>
diff --git a/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerAdapter.java b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerAdapter.java
new file mode 100644
index 00000000..90a305d3
--- /dev/null
+++ b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerAdapter.java
@@ -0,0 +1,213 @@
+/**
+ * Copyright (c) 2004-2011 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.reload4j;
+
+import static org.slf4j.event.EventConstants.NA_SUBST;
+
+import java.io.Serializable;
+
+import org.apache.log4j.Level;
+import org.apache.log4j.spi.LocationInfo;
+import org.apache.log4j.spi.ThrowableInformation;
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+import org.slf4j.event.DefaultLoggingEvent;
+import org.slf4j.event.LoggingEvent;
+import org.slf4j.event.SubstituteLoggingEvent;
+import org.slf4j.helpers.LegacyAbstractLogger;
+import org.slf4j.helpers.MessageFormatter;
+import org.slf4j.helpers.NormalizedParameters;
+import org.slf4j.helpers.SubstituteLogger;
+import org.slf4j.spi.LocationAwareLogger;
+import org.slf4j.spi.LoggingEventAware;
+import org.slf4j.spi.LoggingEventBuilder;
+
+/**
+ * A wrapper over {@link org.apache.log4j.Logger org.apache.log4j.Logger}
+ * conforming to the {@link Logger} interface.
+ *
+ * <p>
+ * Note that the logging levels mentioned in this class refer to those defined
+ * in the <a href=
+ * "http://logging.apache.org/log4j/docs/api/org/apache/log4j/Level.html">
+ * <code>org.apache.log4j.Level</code></a> class.
+ *
+ * <p>This class is a copy-and-paste of Log4j12LoggerAdapter from the
+ * slf4j-log4j12 module.</p>
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @since 2.0.0-alpha6
+ */
+public final class Reload4jLoggerAdapter extends LegacyAbstractLogger implements LocationAwareLogger, LoggingEventAware, Serializable {
+
+ private static final long serialVersionUID = 6989384227325275811L;
+
+ final transient org.apache.log4j.Logger logger;
+
+ final static String FQCN_NOMINAL = org.slf4j.helpers.AbstractLogger.class.getName();
+ final static String FQCN_SUBSTITUE = FQCN_NOMINAL;
+ final static String FQCN_FLUENT = org.slf4j.spi.DefaultLoggingEventBuilder.class.getName();
+
+ // WARN: Reload4jLoggerAdapter constructor should have only package access so
+ // that only Reload4jLoggerFactory be able to create one.
+ Reload4jLoggerAdapter(org.apache.log4j.Logger logger) {
+ this.logger = logger;
+ this.name = logger.getName();
+ }
+
+ /**
+ * Is this logger instance enabled for the TRACE level?
+ *
+ * @return True if this Logger is enabled for level TRACE, false otherwise.
+ */
+ public boolean isTraceEnabled() {
+ return logger.isTraceEnabled();
+ }
+
+ /**
+ * Is this logger instance enabled for the DEBUG level?
+ *
+ * @return True if this Logger is enabled for level DEBUG, false otherwise.
+ */
+ public boolean isDebugEnabled() {
+ return logger.isDebugEnabled();
+ }
+
+ /**
+ * Is this logger instance enabled for the INFO level?
+ *
+ * @return True if this Logger is enabled for the INFO level, false otherwise.
+ */
+ public boolean isInfoEnabled() {
+ return logger.isInfoEnabled();
+ }
+
+ /**
+ * Is this logger instance enabled for the WARN level?
+ *
+ * @return True if this Logger is enabled for the WARN level, false otherwise.
+ */
+ public boolean isWarnEnabled() {
+ return logger.isEnabledFor(Level.WARN);
+ }
+
+ /**
+ * Is this logger instance enabled for level ERROR?
+ *
+ * @return True if this Logger is enabled for level ERROR, false otherwise.
+ */
+ public boolean isErrorEnabled() {
+ return logger.isEnabledFor(Level.ERROR);
+ }
+
+ @Override
+ public void log(Marker marker, String callerFQCN, int level, String msg, Object[] arguments, Throwable t) {
+ Level log4jLevel = toLog4jLevel(level);
+ NormalizedParameters np = NormalizedParameters.normalize(msg, arguments, t);
+ String formattedMessage = MessageFormatter.basicArrayFormat(np.getMessage(), np.getArguments());
+ logger.log(callerFQCN, log4jLevel, formattedMessage, np.getThrowable());
+ }
+
+ @Override
+ protected void handleNormalizedLoggingCall(org.slf4j.event.Level level, Marker marker, String msg, Object[] arguments, Throwable throwable) {
+ Level log4jLevel = toLog4jLevel(level.toInt());
+ String formattedMessage = MessageFormatter.basicArrayFormat(msg, arguments);
+ logger.log(getFullyQualifiedCallerName(), log4jLevel, formattedMessage, throwable);
+ }
+
+ /**
+ * Called by {@link SubstituteLogger} or by {@link LoggingEventBuilder} instances
+ * @param event
+ */
+ public void log(LoggingEvent event) {
+ Level log4jLevel = toLog4jLevel(event.getLevel().toInt());
+ if (!logger.isEnabledFor(log4jLevel))
+ return;
+
+ org.apache.log4j.spi.LoggingEvent log4jevent = event2Log4jEvent(event, log4jLevel);
+ logger.callAppenders(log4jevent);
+
+ }
+
+ private org.apache.log4j.spi.LoggingEvent event2Log4jEvent(LoggingEvent event, Level log4jLevel) {
+
+ String formattedMessage = MessageFormatter.basicArrayFormat(event.getMessage(), event.getArgumentArray());
+
+ LocationInfo locationInfo = null;
+ String fqcn = null;
+
+ if (event instanceof SubstituteLoggingEvent) {
+ locationInfo = new LocationInfo(NA_SUBST, NA_SUBST, NA_SUBST, "0");
+ fqcn = FQCN_SUBSTITUE;
+ } else {
+ fqcn = FQCN_FLUENT;
+ }
+
+ ThrowableInformation ti = null;
+ Throwable t = event.getThrowable();
+ if (t != null)
+ ti = new ThrowableInformation(t);
+
+ if(event instanceof DefaultLoggingEvent) {
+ DefaultLoggingEvent defaultLoggingEvent = (DefaultLoggingEvent) event;
+ defaultLoggingEvent.setTimeStamp(System.currentTimeMillis());
+ }
+
+ org.apache.log4j.spi.LoggingEvent log4jEvent = new org.apache.log4j.spi.LoggingEvent(fqcn, logger, event.getTimeStamp(), log4jLevel, formattedMessage,
+ event.getThreadName(), ti, null, locationInfo, null);
+
+ return log4jEvent;
+ }
+
+ private Level toLog4jLevel(int slf4jLevelInt) {
+ Level log4jLevel;
+ switch (slf4jLevelInt) {
+ case LocationAwareLogger.TRACE_INT:
+ log4jLevel = Level.TRACE;
+ break;
+ case LocationAwareLogger.DEBUG_INT:
+ log4jLevel = Level.DEBUG;
+ break;
+ case LocationAwareLogger.INFO_INT:
+ log4jLevel = Level.INFO;
+ break;
+ case LocationAwareLogger.WARN_INT:
+ log4jLevel = Level.WARN;
+ break;
+ case LocationAwareLogger.ERROR_INT:
+ log4jLevel = Level.ERROR;
+ break;
+ default:
+ throw new IllegalStateException("Level number " + slf4jLevelInt + " is not recognized.");
+ }
+ return log4jLevel;
+ }
+
+ @Override
+ protected String getFullyQualifiedCallerName() {
+ return FQCN_NOMINAL;
+ }
+
+}
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerFactory.java b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerFactory.java
index e801f9cc..0aca814e 100644
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jLoggerFactory.java
+++ b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jLoggerFactory.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.reload4j;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
@@ -30,20 +30,41 @@ import java.util.concurrent.ConcurrentMap;
import org.apache.log4j.LogManager;
import org.slf4j.ILoggerFactory;
import org.slf4j.Logger;
+import org.slf4j.helpers.Reporter;
+import org.slf4j.helpers.Util;
/**
* Log4jLoggerFactory is an implementation of {@link ILoggerFactory} returning
- * the appropriate named {@link Log4jLoggerAdapter} instance.
+ * the appropriate named {@link Reload4jLoggerAdapter} instance.
*
* @author Ceki G&uuml;lc&uuml;
*/
-public class Log4jLoggerFactory implements ILoggerFactory {
+public class Reload4jLoggerFactory implements ILoggerFactory {
+
+ private static final String LOG4J_DELEGATION_LOOP_URL = "http://www.slf4j.org/codes.html#log4jDelegationLoop";
+
+ // check for delegation loops
+ static {
+ try {
+ Class.forName("org.apache.log4j.Log4jLoggerFactory");
+ String part1 = "Detected both log4j-over-slf4j.jar AND bound slf4j-log4j12.jar on the class path, preempting StackOverflowError. ";
+ String part2 = "See also " + LOG4J_DELEGATION_LOOP_URL + " for more details.";
+
+ Reporter.error(part1);
+ Reporter.error(part2);
+ throw new IllegalStateException(part1 + part2);
+ } catch (ClassNotFoundException e) {
+ // this is the good case
+ }
+ }
// key: name (String), value: a Log4jLoggerAdapter;
ConcurrentMap<String, Logger> loggerMap;
- public Log4jLoggerFactory() {
- loggerMap = new ConcurrentHashMap<String, Logger>();
+ public Reload4jLoggerFactory() {
+ loggerMap = new ConcurrentHashMap<>();
+ // force log4j to initialize
+ org.apache.log4j.LogManager.getRootLogger();
}
/*
@@ -62,7 +83,7 @@ public class Log4jLoggerFactory implements ILoggerFactory {
else
log4jLogger = LogManager.getLogger(name);
- Logger newInstance = new Log4jLoggerAdapter(log4jLogger);
+ Logger newInstance = new Reload4jLoggerAdapter(log4jLogger);
Logger oldInstance = loggerMap.putIfAbsent(name, newInstance);
return oldInstance == null ? newInstance : oldInstance;
}
diff --git a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jMDCAdapter.java b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jMDCAdapter.java
index 95b8ed02..8c874a68 100644
--- a/slf4j-log4j12/src/main/java/org/slf4j/impl/Log4jMDCAdapter.java
+++ b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jMDCAdapter.java
@@ -1,5 +1,5 @@
/**
- * Copyright (c) 2004-2011 QOS.ch
+ * Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
* All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining
@@ -22,16 +22,20 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.reload4j;
+import java.util.Deque;
import java.util.HashMap;
-import java.util.Iterator;
import java.util.Map;
+import org.slf4j.helpers.ThreadLocalMapOfStacks;
import org.slf4j.spi.MDCAdapter;
-public class Log4jMDCAdapter implements MDCAdapter {
+public class Reload4jMDCAdapter implements MDCAdapter {
+ private final ThreadLocalMapOfStacks threadLocalMapOfDeques = new ThreadLocalMapOfStacks();
+
+ @Override
public void clear() {
@SuppressWarnings("rawtypes")
Map map = org.apache.log4j.MDC.getContext();
@@ -40,6 +44,7 @@ public class Log4jMDCAdapter implements MDCAdapter {
}
}
+ @Override
public String get(String key) {
return (String) org.apache.log4j.MDC.get(key);
}
@@ -47,19 +52,21 @@ public class Log4jMDCAdapter implements MDCAdapter {
/**
* Put a context value (the <code>val</code> parameter) as identified with
* the <code>key</code> parameter into the current thread's context map. The
- * <code>key</code> parameter cannot be null. Log4j does <em>not</em>
+ * <code>key</code> parameter cannot be null. Log4j does <em>not</em>
* support null for the <code>val</code> parameter.
*
* <p>
* This method delegates all work to log4j's MDC.
*
* @throws IllegalArgumentException
- * in case the "key" or <b>"val"</b> parameter is null
+ * in case the "key" or <b>"val"</b> parameter is null
*/
+ @Override
public void put(String key, String val) {
org.apache.log4j.MDC.put(key, val);
}
+ @Override
public void remove(String key) {
org.apache.log4j.MDC.remove(key);
}
@@ -75,17 +82,45 @@ public class Log4jMDCAdapter implements MDCAdapter {
}
@SuppressWarnings({ "rawtypes", "unchecked" })
- public void setContextMap(Map contextMap) {
+ @Override
+ public void setContextMap(Map<String, String> contextMap) {
Map old = org.apache.log4j.MDC.getContext();
+
+ // we must cater for the case where the contextMap argument is null
+ if (contextMap == null) {
+ if (old != null) {
+ old.clear();
+ }
+ return;
+ }
+
if (old == null) {
- Iterator entrySetIterator = contextMap.entrySet().iterator();
- while (entrySetIterator.hasNext()) {
- Map.Entry mapEntry = (Map.Entry) entrySetIterator.next();
- org.apache.log4j.MDC.put((String) mapEntry.getKey(), mapEntry.getValue());
+ for (Map.Entry<String, String> mapEntry : contextMap.entrySet()) {
+ org.apache.log4j.MDC.put(mapEntry.getKey(), mapEntry.getValue());
}
} else {
old.clear();
old.putAll(contextMap);
}
}
+
+ @Override
+ public void pushByKey(String key, String value) {
+ threadLocalMapOfDeques.pushByKey(key, value);
+ }
+
+ @Override
+ public String popByKey(String key) {
+ return threadLocalMapOfDeques.popByKey(key);
+ }
+
+ @Override
+ public Deque<String> getCopyOfDequeByKey(String key) {
+ return threadLocalMapOfDeques.getCopyOfDequeByKey(key);
+ }
+
+ @Override
+ public void clearDequeByKey(String key) {
+ threadLocalMapOfDeques.clearDequeByKey(key);
+ }
}
diff --git a/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jServiceProvider.java b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jServiceProvider.java
new file mode 100644
index 00000000..ed023b31
--- /dev/null
+++ b/slf4j-reload4j/src/main/java/org/slf4j/reload4j/Reload4jServiceProvider.java
@@ -0,0 +1,62 @@
+package org.slf4j.reload4j;
+
+import org.apache.log4j.Level;
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.helpers.Reporter;
+import org.slf4j.helpers.Util;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class Reload4jServiceProvider implements SLF4JServiceProvider {
+
+ /**
+ * Declare the version of the SLF4J API this implementation is compiled against.
+ * The value of this field is modified with each major release.
+ */
+ // to avoid constant folding by the compiler, this field must *not* be final
+ public static String REQUESTED_API_VERSION = "2.0.99"; // !final
+
+ private ILoggerFactory loggerFactory;
+ private IMarkerFactory markerFactory;
+ private MDCAdapter mdcAdapter;
+
+ public Reload4jServiceProvider() {
+ try {
+ @SuppressWarnings("unused")
+ Level level = Level.TRACE;
+ } catch (NoSuchFieldError nsfe) {
+ Reporter.error("This version of SLF4J requires log4j version 1.2.12 or later. See also http://www.slf4j.org/codes.html#log4j_version");
+ }
+ }
+
+ @Override
+ public void initialize() {
+ loggerFactory = new Reload4jLoggerFactory();
+ markerFactory = new BasicMarkerFactory();
+ mdcAdapter = new Reload4jMDCAdapter();
+ }
+
+ @Override
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+
+ @Override
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return REQUESTED_API_VERSION;
+ }
+}
diff --git a/slf4j-reload4j/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider b/slf4j-reload4j/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
new file mode 100644
index 00000000..b81f3e12
--- /dev/null
+++ b/slf4j-reload4j/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
@@ -0,0 +1 @@
+org.slf4j.reload4j.Reload4jServiceProvider
diff --git a/slf4j-reload4j/src/test/java/org/slf4j/reload4j/EventFieldsTest.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/EventFieldsTest.java
new file mode 100644
index 00000000..bfff3e3f
--- /dev/null
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/EventFieldsTest.java
@@ -0,0 +1,61 @@
+package org.slf4j.reload4j;
+
+import org.apache.log4j.spi.LoggingEvent;
+import org.junit.After;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.List;
+
+import static org.junit.Assert.*;
+
+public class EventFieldsTest {
+
+ // value of LogManager.DEFAULT_CONFIGURATION_KEY;
+ static String CONFIG_FILE_KEY = "log4j.configuration";
+
+ @After
+ public void tearDown() throws Exception {
+ System.clearProperty(CONFIG_FILE_KEY);
+ }
+
+ @Test
+ public void testWhetherEventsFieldsAreSet() {
+ System.setProperty(CONFIG_FILE_KEY, "eventFields.properties");
+ Logger logger = LoggerFactory.getLogger(this.getClass());
+ logger.info("hello");
+ logger.atInfo().setMessage("hello").log();
+
+ org.slf4j.reload4j.Reload4jLoggerAdapter rootReload4j = (org.slf4j.reload4j.Reload4jLoggerAdapter) LoggerFactory.getLogger(Logger.ROOT_LOGGER_NAME);
+
+
+ ListAppender listAppender = (ListAppender) rootReload4j.logger.getAppender("LIST");
+
+ assertNotNull(listAppender);
+ assertNotNull(listAppender.list);
+
+ List<LoggingEvent> eventList = listAppender.list;
+
+ assertEquals(2, eventList.size());
+
+ LoggingEvent loggingEvent0 = eventList.get(0);
+ long timeStamp0 = loggingEvent0.getTimeStamp();
+ String threadName0 = loggingEvent0.getThreadName();
+ assertTrue(timeStamp0 != 0);
+ assertNotNull(threadName0);
+ assertFalse(threadName0.isEmpty());
+
+ LoggingEvent loggingEvent1 = eventList.get(1);
+ long timeStamp1 = loggingEvent1.getTimeStamp();
+ String threadName1 = loggingEvent1.getThreadName();
+ assertTrue(timeStamp1 != 0);
+ assertTrue(timeStamp1 >= timeStamp0);
+ assertNotNull(threadName1);
+ assertFalse(threadName1.isEmpty());
+ assertEquals(threadName0, threadName1);
+
+ }
+
+
+}
diff --git a/slf4j-log4j12/src/test/java/org/slf4j/InvocationTest.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/InvocationTest.java
index b3246f50..12d6db19 100644
--- a/slf4j-log4j12/src/test/java/org/slf4j/InvocationTest.java
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/InvocationTest.java
@@ -22,14 +22,25 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.reload4j;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.fail;
import java.util.HashMap;
import java.util.Map;
import org.apache.log4j.spi.LoggingEvent;
-
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
/**
* Test whether invoking the SLF4J API causes problems or not.
@@ -37,37 +48,35 @@ import junit.framework.TestCase;
* @author Ceki Gulcu
*
*/
-public class InvocationTest extends TestCase {
+public class InvocationTest {
ListAppender listAppender = new ListAppender();
org.apache.log4j.Logger root;
- public InvocationTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
root = org.apache.log4j.Logger.getRootLogger();
root.addAppender(listAppender);
-
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
root.getLoggerRepository().resetConfiguration();
}
+ @Test
public void test1() {
+
Logger logger = LoggerFactory.getLogger("test1");
logger.debug("Hello world.");
assertEquals(1, listAppender.list.size());
}
+ @Test
public void test2() {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
+ Integer i1 = Integer.valueOf(1);
+ Integer i2 = Integer.valueOf(2);
+ Integer i3 = Integer.valueOf(3);
Exception e = new Exception("This is a test exception.");
Logger logger = LoggerFactory.getLogger("test2");
@@ -85,11 +94,12 @@ public class InvocationTest extends TestCase {
logger.warn("Hello world 3", e);
logger.error("Hello world 4.");
- logger.error("Hello world {}", new Integer(3));
+ logger.error("Hello world {}", Integer.valueOf(3));
logger.error("Hello world 4.", e);
assertEquals(11, listAppender.list.size());
}
+ @Test
public void testNull() {
Logger logger = LoggerFactory.getLogger("testNull");
logger.trace(null);
@@ -106,18 +116,22 @@ public class InvocationTest extends TestCase {
assertEquals(8, listAppender.list.size());
}
- // http://bugzilla.slf4j.org/show_bug.cgi?id=78
+ // http://jira.qos.ch/browse/SLF4J-69
+ // formerly http://bugzilla.slf4j.org/show_bug.cgi?id=78
+ @Test
public void testNullParameter_BUG78() {
Logger logger = LoggerFactory.getLogger("testNullParameter_BUG78");
String[] parameters = null;
String msg = "hello {}";
- logger.debug(msg, parameters);
+ logger.debug(msg, (Object[]) parameters);
+
assertEquals(1, listAppender.list.size());
LoggingEvent e = (LoggingEvent) listAppender.list.get(0);
assertEquals(msg, e.getMessage());
}
+ @Test
public void testMarker() {
Logger logger = LoggerFactory.getLogger("testMarker");
Marker blue = MarkerFactory.getMarker("BLUE");
@@ -139,6 +153,7 @@ public class InvocationTest extends TestCase {
assertEquals(12, listAppender.list.size());
}
+ @Test
public void testMDC() {
MDC.put("k", "v");
assertNotNull(MDC.get("k"));
@@ -159,8 +174,9 @@ public class InvocationTest extends TestCase {
}
}
+ @Test
public void testMDCContextMapValues() {
- Map<String, String> map = new HashMap<String, String>();
+ Map<String, String> map = new HashMap<>();
map.put("ka", "va");
map.put("kb", "vb");
@@ -172,4 +188,22 @@ public class InvocationTest extends TestCase {
assertEquals("vb", MDC.get("kb"));
}
+ @Test
+ public void testCallerInfo() {
+ Logger logger = LoggerFactory.getLogger("testMarker");
+ listAppender.extractLocationInfo = true;
+ logger.debug("hello");
+ LoggingEvent event = listAppender.list.get(0);
+ assertEquals(this.getClass().getName(), event.getLocationInformation().getClassName());
+ }
+
+ @Test
+ public void testCallerInfoWithFluentAPI() {
+ Logger logger = LoggerFactory.getLogger("testMarker");
+ listAppender.extractLocationInfo = true;
+ logger.atDebug().log("hello");
+ LoggingEvent event = listAppender.list.get(0);
+ assertEquals(this.getClass().getName(), event.getLocationInformation().getClassName());
+ }
+
}
diff --git a/slf4j-log4j12/src/test/java/org/slf4j/ListAppender.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/ListAppender.java
index 29596899..92cd9d32 100644
--- a/slf4j-log4j12/src/test/java/org/slf4j/ListAppender.java
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/ListAppender.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.reload4j;
import java.util.ArrayList;
import java.util.List;
@@ -32,7 +32,7 @@ import org.apache.log4j.spi.LoggingEvent;
public class ListAppender extends AppenderSkeleton {
- public List<LoggingEvent> list = new ArrayList<LoggingEvent>();
+ public List<LoggingEvent> list = new ArrayList<>();
public boolean extractLocationInfo = false;
diff --git a/slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveInitializationTest.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/RecursiveInitializationTest.java
index 23a24437..ff68f2da 100644
--- a/slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveInitializationTest.java
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/RecursiveInitializationTest.java
@@ -22,35 +22,32 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.reload4j;
import java.util.Random;
-import junit.framework.TestCase;
-
+import org.junit.After;
+import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
-public class RecursiveInitializationTest extends TestCase {
+public class RecursiveInitializationTest {
// value of LogManager.DEFAULT_CONFIGURATION_KEY;
static String CONFIG_FILE_KEY = "log4j.configuration";
int diff = new Random().nextInt(10000);
+ String loggerName = "org.slf4j.impl.RecursiveInitializationTest";
- protected void setUp() throws Exception {
- System.setProperty(CONFIG_FILE_KEY, "recursiveInit.properties");
- super.setUp();
- }
-
- protected void tearDown() throws Exception {
+ @After
+ public void tearDown() throws Exception {
System.clearProperty(CONFIG_FILE_KEY);
- super.tearDown();
}
- public void testLog4j() {
- Logger logger = LoggerFactory.getLogger("x" + diff);
- System.out.println("logger class=" + logger.getClass().getName());
+ @Test
+ public void loggingDuringInitialization() {
+ System.setProperty(CONFIG_FILE_KEY, "recursiveInit.properties");
+ Logger logger = LoggerFactory.getLogger(loggerName + ".loggingDuringInitialization-" + diff);
logger.info("hello");
}
diff --git a/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMDCAdapterTest.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMDCAdapterTest.java
new file mode 100644
index 00000000..fa343b45
--- /dev/null
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMDCAdapterTest.java
@@ -0,0 +1,39 @@
+package org.slf4j.reload4j;
+
+import org.junit.Test;
+import org.slf4j.helpers.MDCAdapterTestBase;
+import org.slf4j.spi.MDCAdapter;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.junit.Assert.*;
+
+public class Reload4jMDCAdapterTest extends MDCAdapterTestBase {
+
+ protected MDCAdapter instantiateMDC() {
+ return new Reload4jMDCAdapter();
+ }
+
+
+ @Test
+ public void testClearingMDC() {
+ mdc.put("testKey", "testValue");
+ assertFalse(mdc.getCopyOfContextMap().isEmpty());
+ mdc.clear();
+ assertTrue(mdc.getCopyOfContextMap().isEmpty());
+ }
+
+ @Test
+ public void testSetContextMap() {
+ Map<String, String> map0 = new HashMap<>();
+ map0.put("key0", "val0");
+
+ mdc.setContextMap(map0);
+ Map map1 = mdc.getCopyOfContextMap();
+
+ assertEquals(map0, map1);
+ }
+
+
+}
diff --git a/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMultithreadedInitializationTest.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMultithreadedInitializationTest.java
new file mode 100644
index 00000000..febde1e8
--- /dev/null
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/Reload4jMultithreadedInitializationTest.java
@@ -0,0 +1,72 @@
+/**
+ * Copyright (c) 2004-2011 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.reload4j;
+
+import static org.junit.Assert.assertNotNull;
+
+import java.util.List;
+
+import org.apache.log4j.LogManager;
+import org.apache.log4j.spi.LoggingEvent;
+import org.junit.After;
+import org.junit.Before;
+import org.slf4j.reload4j.testHarness.RecursiveAppender;
+
+public class Reload4jMultithreadedInitializationTest extends org.slf4j.testHarness.MultithreadedInitializationTest {
+ static int NUM_LINES_BY_RECURSIVE_APPENDER = 3;
+
+ // value of LogManager.DEFAULT_CONFIGURATION_KEY;
+ static String CONFIG_FILE_KEY = "log4j.configuration";
+ final String loggerName = this.getClass().getName();
+
+ @Before
+ public void setup() {
+ System.setProperty(CONFIG_FILE_KEY, "recursiveInitWithActivationDelay.properties");
+ System.out.println("THREAD_COUNT=" + THREAD_COUNT);
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ System.clearProperty(CONFIG_FILE_KEY);
+ }
+
+ protected long getRecordedEventCount() {
+ List<LoggingEvent> eventList = getRecordedEvents();
+ assertNotNull(eventList);
+ return eventList.size();
+ }
+
+ protected int extraLogEvents() {
+ return NUM_LINES_BY_RECURSIVE_APPENDER;
+ }
+
+ private List<LoggingEvent> getRecordedEvents() {
+ org.apache.log4j.Logger root = LogManager.getRootLogger();
+ RecursiveAppender ra = (RecursiveAppender) root.getAppender("RECURSIVE");
+ assertNotNull(ra);
+ return ra.events;
+ }
+
+}
diff --git a/slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveAppender.java b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/testHarness/RecursiveAppender.java
index 0dc34b01..3857ba32 100644
--- a/slf4j-log4j12/src/test/java/org/slf4j/impl/RecursiveAppender.java
+++ b/slf4j-reload4j/src/test/java/org/slf4j/reload4j/testHarness/RecursiveAppender.java
@@ -22,8 +22,10 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.reload4j.testHarness;
+import java.util.ArrayList;
+import java.util.List;
import java.util.Random;
import org.apache.log4j.AppenderSkeleton;
@@ -34,15 +36,20 @@ import org.slf4j.LoggerFactory;
public class RecursiveAppender extends AppenderSkeleton {
int diff = new Random().nextInt();
+ int activationDelay = 0;
+ String loggerName = "org.slf4j.impl.RecursiveAppender" + diff;
+
+ public List<LoggingEvent> events = new ArrayList<>();
public RecursiveAppender() {
- System.out.println("in RecursiveAppender constructor");
- Logger logger = LoggerFactory.getLogger("RecursiveAppender" + diff);
- System.out.println("logger class=" + logger.getClass().getName());
+ System.out.println("XXXXXXX entering RecursiveAppender constructor");
+ Logger logger = LoggerFactory.getLogger(loggerName);
logger.info("Calling a logger in the constructor");
+ System.out.println("exiting RecursiveAppender constructor");
}
- protected void append(LoggingEvent arg0) {
+ protected void append(LoggingEvent e) {
+ events.add(e);
}
public void close() {
@@ -51,4 +58,31 @@ public class RecursiveAppender extends AppenderSkeleton {
public boolean requiresLayout() {
return false;
}
+
+ @Override
+ public void activateOptions() {
+ System.out.println("entering RecursiveAppender.activateOptions");
+ if (activationDelay > 0) {
+ Logger logger = LoggerFactory.getLogger(loggerName);
+ logger.info("About to wait {} millis", activationDelay);
+ try {
+ Thread.sleep(activationDelay);
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ logger.info("Done waiting {} millis", activationDelay);
+ }
+ super.activateOptions();
+
+ System.out.println("exiting RecursiveAppender.activateOptions");
+ }
+
+ public int getActivationDelay() {
+ return activationDelay;
+ }
+
+ public void setActivationDelay(int activationDelay) {
+ this.activationDelay = activationDelay;
+ }
+
}
diff --git a/slf4j-reload4j/src/test/resources/eventFields.properties b/slf4j-reload4j/src/test/resources/eventFields.properties
new file mode 100644
index 00000000..5922ca9f
--- /dev/null
+++ b/slf4j-reload4j/src/test/resources/eventFields.properties
@@ -0,0 +1,4 @@
+log4j.debug=true
+log4j.rootLogger=DEBUG, LIST
+
+log4j.appender.LIST=org.slf4j.reload4j.ListAppender
diff --git a/slf4j-log4j12/src/test/resources/recursiveInit.properties b/slf4j-reload4j/src/test/resources/recursiveInit.properties
index a8d5d765..a62a15e2 100644
--- a/slf4j-log4j12/src/test/resources/recursiveInit.properties
+++ b/slf4j-reload4j/src/test/resources/recursiveInit.properties
@@ -3,6 +3,7 @@ log4j.rootLogger=DEBUG, RECURSIVE
log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
-log4j.appender.CONSOLE.layout.ConversionPattern=%d [%t] %c - %m%n
+log4j.appender.CONSOLE.layout.ConversionPattern=[%t] %c - %m%n
-log4j.appender.RECURSIVE=org.slf4j.impl.RecursiveAppender \ No newline at end of file
+log4j.appender.RECURSIVE=org.slf4j.reload4j.testHarness.RecursiveAppender
+ \ No newline at end of file
diff --git a/slf4j-reload4j/src/test/resources/recursiveInitWithActivationDelay.properties b/slf4j-reload4j/src/test/resources/recursiveInitWithActivationDelay.properties
new file mode 100644
index 00000000..957894dd
--- /dev/null
+++ b/slf4j-reload4j/src/test/resources/recursiveInitWithActivationDelay.properties
@@ -0,0 +1,9 @@
+log4j.debug=true
+log4j.rootLogger=DEBUG, CONSOLE, RECURSIVE
+
+log4j.appender.CONSOLE=org.apache.log4j.ConsoleAppender
+log4j.appender.CONSOLE.layout=org.apache.log4j.PatternLayout
+log4j.appender.CONSOLE.layout.ConversionPattern=CON [%t] %c - %m%n
+
+log4j.appender.RECURSIVE=org.slf4j.reload4j.testHarness.RecursiveAppender
+log4j.appender.RECURSIVE.activationDelay=10
diff --git a/slf4j-simple/LICENSE.txt b/slf4j-simple/LICENSE.txt
index 508a2728..e4079f54 100644
--- a/slf4j-simple/LICENSE.txt
+++ b/slf4j-simple/LICENSE.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2004-2007 QOS.ch
+Copyright (c) 2004-2023 QOS.ch
All rights reserved.
Permission is hereby granted, free of charge, to any person obtaining
diff --git a/slf4j-simple/pom.xml b/slf4j-simple/pom.xml
index 79d5b966..776efc66 100755
--- a/slf4j-simple/pom.xml
+++ b/slf4j-simple/pom.xml
@@ -1,3 +1,4 @@
+<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
@@ -6,42 +7,35 @@
<parent>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
+ <version>2.0.12</version>
+ <relativePath>../parent/pom.xml</relativePath>
</parent>
<artifactId>slf4j-simple</artifactId>
<packaging>jar</packaging>
- <name>SLF4J Simple Binding</name>
- <description>SLF4J Simple binding</description>
+ <name>SLF4J Simple Provider</name>
+ <description>SLF4J Simple Provider</description>
<url>http://www.slf4j.org</url>
+ <properties>
+ <module-name>org.slf4j.simple</module-name>
+ <slf4j.provider.implementation>org.slf4j.simple.SimpleServiceProvider</slf4j.provider.implementation>
+ <slf4j.provider.type>simple</slf4j.provider.type>
+ </properties>
+
<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</dependency>
- </dependencies>
-
-
- <build>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-jar-plugin</artifactId>
- <configuration>
- <archive>
- <manifestEntries>
- <Bundle-Version>${parsedVersion.osgiVersion}</Bundle-Version>
- <Bundle-Description>${project.description}</Bundle-Description>
- <Implementation-Version>${project.version}</Implementation-Version>
- </manifestEntries>
- <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
- </archive>
- </configuration>
- </plugin>
-
- </plugins>
- </build>
+ <dependency>
+ <groupId>org.slf4j</groupId>
+ <artifactId>slf4j-api</artifactId>
+ <type>test-jar</type>
+ <version>${project.version}</version>
+ <scope>test</scope>
+ </dependency>
+ </dependencies>
-</project> \ No newline at end of file
+</project>
diff --git a/slf4j-simple/src/main/java/org/slf4j/impl/SimpleLogger.java b/slf4j-simple/src/main/java/org/slf4j/impl/SimpleLogger.java
deleted file mode 100644
index 7b0abf95..00000000
--- a/slf4j-simple/src/main/java/org/slf4j/impl/SimpleLogger.java
+++ /dev/null
@@ -1,648 +0,0 @@
-/**
- * Copyright (c) 2004-2012 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.InputStream;
-import java.io.PrintStream;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
-import java.text.DateFormat;
-import java.text.SimpleDateFormat;
-import java.util.Date;
-import java.util.Properties;
-
-import org.slf4j.Logger;
-import org.slf4j.helpers.FormattingTuple;
-import org.slf4j.helpers.MarkerIgnoringBase;
-import org.slf4j.helpers.MessageFormatter;
-import org.slf4j.helpers.Util;
-import org.slf4j.spi.LocationAwareLogger;
-
-/**
- * <p>Simple implementation of {@link Logger} that sends all enabled log messages,
- * for all defined loggers, to the console ({@code System.err}).
- * The following system properties are supported to configure the behavior of this logger:</p>
- *
- * <ul>
- * <li><code>org.slf4j.simpleLogger.logFile</code> - The output target which can be the <em>path</em> to a file, or
- * the special values "System.out" and "System.err". Default is "System.err".
- *
- * <li><code>org.slf4j.simpleLogger.defaultLogLevel</code> - Default log level for all instances of SimpleLogger.
- * Must be one of ("trace", "debug", "info", "warn", or "error"). If not specified, defaults to "info". </li>
- *
- * <li><code>org.slf4j.simpleLogger.log.<em>a.b.c</em></code> - Logging detail level for a SimpleLogger instance
- * named "a.b.c". Right-side value must be one of "trace", "debug", "info", "warn", or "error". When a SimpleLogger
- * named "a.b.c" is initialized, its level is assigned from this property. If unspecified, the level of nearest parent
- * logger will be used, and if none is set, then the value specified by
- * <code>org.slf4j.simpleLogger.defaultLogLevel</code> will be used.</li>
- *
- * <li><code>org.slf4j.simpleLogger.showDateTime</code> - Set to <code>true</code> if you want the current date and
- * time to be included in output messages. Default is <code>false</code></li>
- *
- * <li><code>org.slf4j.simpleLogger.dateTimeFormat</code> - The date and time format to be used in the output messages.
- * The pattern describing the date and time format is defined by
- * <a href="http://docs.oracle.com/javase/1.5.0/docs/api/java/text/SimpleDateFormat.html"><code>SimpleDateFormat</code></a>.
- * If the format is not specified or is invalid, the number of milliseconds since start up will be output. </li>
- *
- * <li><code>org.slf4j.simpleLogger.showThreadName</code> -Set to <code>true</code> if you want to output the current
- * thread name. Defaults to <code>true</code>.</li>
- *
- * <li><code>org.slf4j.simpleLogger.showLogName</code> - Set to <code>true</code> if you want the Logger instance name
- * to be included in output messages. Defaults to <code>true</code>.</li>
- *
- * <li><code>org.slf4j.simpleLogger.showShortLogName</code> - Set to <code>true</code> if you want the last component
- * of the name to be included in output messages. Defaults to <code>false</code>.</li>
- *
- * <li><code>org.slf4j.simpleLogger.levelInBrackets</code> - Should the level string be output in brackets? Defaults
- * to <code>false</code>.</li>
- *
- * <li><code>org.slf4j.simpleLogger.warnLevelString</code> - The string value output for the warn level. Defaults
- * to <code>WARN</code>.</li>
-
- * </ul>
- *
- * <p>In addition to looking for system properties with the names specified above, this implementation also checks for
- * a class loader resource named <code>"simplelogger.properties"</code>, and includes any matching definitions
- * from this resource (if it exists).</p>
- *
- * <p>With no configuration, the default output includes the relative time in milliseconds, thread name, the level,
- * logger name, and the message followed by the line separator for the host. In log4j terms it amounts to the "%r [%t]
- * %level %logger - %m%n" pattern. </p>
- * <p>Sample output follows.</p>
- * <pre>
- * 176 [main] INFO examples.Sort - Populating an array of 2 elements in reverse order.
- * 225 [main] INFO examples.SortAlgo - Entered the sort method.
- * 304 [main] INFO examples.SortAlgo - Dump of integer array:
- * 317 [main] INFO examples.SortAlgo - Element [0] = 0
- * 331 [main] INFO examples.SortAlgo - Element [1] = 1
- * 343 [main] INFO examples.Sort - The next log statement should be an error message.
- * 346 [main] ERROR examples.SortAlgo - Tried to dump an uninitialized array.
- * at org.log4j.examples.SortAlgo.dump(SortAlgo.java:58)
- * at org.log4j.examples.Sort.main(Sort.java:64)
- * 467 [main] INFO examples.Sort - Exiting main method.
- * </pre>
- *
- * <p>This implementation is heavily inspired by
- * <a href="http://commons.apache.org/logging/">Apache Commons Logging</a>'s SimpleLog.</p>
- *
- * @author Ceki G&uuml;lc&uuml;
- * @author <a href="mailto:sanders@apache.org">Scott Sanders</a>
- * @author Rod Waldhoff
- * @author Robert Burrell Donkin
- * @author C&eacute;drik LIME
- */
-public class SimpleLogger extends MarkerIgnoringBase {
-
- private static final long serialVersionUID = -632788891211436180L;
- private static final String CONFIGURATION_FILE = "simplelogger.properties";
-
- private static long START_TIME = System.currentTimeMillis();
- private static final Properties SIMPLE_LOGGER_PROPS = new Properties();
-
- private static final int LOG_LEVEL_TRACE = LocationAwareLogger.TRACE_INT;
- private static final int LOG_LEVEL_DEBUG = LocationAwareLogger.DEBUG_INT;
- private static final int LOG_LEVEL_INFO = LocationAwareLogger.INFO_INT;
- private static final int LOG_LEVEL_WARN = LocationAwareLogger.WARN_INT;
- private static final int LOG_LEVEL_ERROR = LocationAwareLogger.ERROR_INT;
-
- private static boolean INITIALIZED = false;
-
- private static int DEFAULT_LOG_LEVEL = LOG_LEVEL_INFO;
- private static boolean SHOW_DATE_TIME = false;
- private static String DATE_TIME_FORMAT_STR = null;
- private static DateFormat DATE_FORMATTER = null;
- private static boolean SHOW_THREAD_NAME = true;
- private static boolean SHOW_LOG_NAME = true;
- private static boolean SHOW_SHORT_LOG_NAME = false;
- private static String LOG_FILE = "System.err";
- private static PrintStream TARGET_STREAM = null;
- private static boolean LEVEL_IN_BRACKETS = false;
- private static String WARN_LEVEL_STRING = "WARN";
-
- /** All system properties used by <code>SimpleLogger</code> start with this prefix */
- public static final String SYSTEM_PREFIX = "org.slf4j.simpleLogger.";
-
- public static final String DEFAULT_LOG_LEVEL_KEY = SYSTEM_PREFIX + "defaultLogLevel";
- public static final String SHOW_DATE_TIME_KEY = SYSTEM_PREFIX + "showDateTime";
- public static final String DATE_TIME_FORMAT_KEY = SYSTEM_PREFIX + "dateTimeFormat";
- public static final String SHOW_THREAD_NAME_KEY = SYSTEM_PREFIX + "showThreadName";
- public static final String SHOW_LOG_NAME_KEY = SYSTEM_PREFIX + "showLogName";
- public static final String SHOW_SHORT_LOG_NAME_KEY = SYSTEM_PREFIX + "showShortLogName";
- public static final String LOG_FILE_KEY = SYSTEM_PREFIX + "logFile";
- public static final String LEVEL_IN_BRACKETS_KEY = SYSTEM_PREFIX + "levelInBrackets";
- public static final String WARN_LEVEL_STRING_KEY = SYSTEM_PREFIX + "warnLevelString";
-
- public static final String LOG_KEY_PREFIX = SYSTEM_PREFIX + "log.";
-
- private static String getStringProperty(String name) {
- String prop = null;
- try {
- prop = System.getProperty(name);
- } catch (SecurityException e) {
- ; // Ignore
- }
- return (prop == null) ? SIMPLE_LOGGER_PROPS.getProperty(name) : prop;
- }
-
- private static String getStringProperty(String name, String defaultValue) {
- String prop = getStringProperty(name);
- return (prop == null) ? defaultValue : prop;
- }
-
- private static boolean getBooleanProperty(String name, boolean defaultValue) {
- String prop = getStringProperty(name);
- return (prop == null) ? defaultValue : "true".equalsIgnoreCase(prop);
- }
-
- // Initialize class attributes.
- // Load properties file, if found.
- // Override with system properties.
- static void init() {
- INITIALIZED = true;
- loadProperties();
-
- String defaultLogLevelString = getStringProperty(DEFAULT_LOG_LEVEL_KEY, null);
- if (defaultLogLevelString != null)
- DEFAULT_LOG_LEVEL = stringToLevel(defaultLogLevelString);
-
- SHOW_LOG_NAME = getBooleanProperty(SHOW_LOG_NAME_KEY, SHOW_LOG_NAME);
- SHOW_SHORT_LOG_NAME = getBooleanProperty(SHOW_SHORT_LOG_NAME_KEY, SHOW_SHORT_LOG_NAME);
- SHOW_DATE_TIME = getBooleanProperty(SHOW_DATE_TIME_KEY, SHOW_DATE_TIME);
- SHOW_THREAD_NAME = getBooleanProperty(SHOW_THREAD_NAME_KEY, SHOW_THREAD_NAME);
- DATE_TIME_FORMAT_STR = getStringProperty(DATE_TIME_FORMAT_KEY, DATE_TIME_FORMAT_STR);
- LEVEL_IN_BRACKETS = getBooleanProperty(LEVEL_IN_BRACKETS_KEY, LEVEL_IN_BRACKETS);
- WARN_LEVEL_STRING = getStringProperty(WARN_LEVEL_STRING_KEY, WARN_LEVEL_STRING);
-
- LOG_FILE = getStringProperty(LOG_FILE_KEY, LOG_FILE);
- TARGET_STREAM = computeTargetStream(LOG_FILE);
-
- if (DATE_TIME_FORMAT_STR != null) {
- try {
- DATE_FORMATTER = new SimpleDateFormat(DATE_TIME_FORMAT_STR);
- } catch (IllegalArgumentException e) {
- Util.report("Bad date format in " + CONFIGURATION_FILE + "; will output relative time", e);
- }
- }
- }
-
- private static PrintStream computeTargetStream(String logFile) {
- if ("System.err".equalsIgnoreCase(logFile))
- return System.err;
- else if ("System.out".equalsIgnoreCase(logFile)) {
- return System.out;
- } else {
- try {
- FileOutputStream fos = new FileOutputStream(logFile);
- PrintStream printStream = new PrintStream(fos);
- return printStream;
- } catch (FileNotFoundException e) {
- Util.report("Could not open [" + logFile + "]. Defaulting to System.err", e);
- return System.err;
- }
- }
- }
-
- private static void loadProperties() {
- // Add props from the resource simplelogger.properties
- InputStream in = AccessController.doPrivileged(new PrivilegedAction<InputStream>() {
- public InputStream run() {
- ClassLoader threadCL = Thread.currentThread().getContextClassLoader();
- if (threadCL != null) {
- return threadCL.getResourceAsStream(CONFIGURATION_FILE);
- } else {
- return ClassLoader.getSystemResourceAsStream(CONFIGURATION_FILE);
- }
- }
- });
- if (null != in) {
- try {
- SIMPLE_LOGGER_PROPS.load(in);
- in.close();
- } catch (java.io.IOException e) {
- // ignored
- }
- }
- }
-
- /** The current log level */
- protected int currentLogLevel = LOG_LEVEL_INFO;
- /** The short name of this simple log instance */
- private transient String shortLogName = null;
-
- /**
- * Package access allows only {@link SimpleLoggerFactory} to instantiate
- * SimpleLogger instances.
- */
- SimpleLogger(String name) {
- if (!INITIALIZED) {
- init();
- }
- this.name = name;
-
- String levelString = recursivelyComputeLevelString();
- if (levelString != null) {
- this.currentLogLevel = stringToLevel(levelString);
- } else {
- this.currentLogLevel = DEFAULT_LOG_LEVEL;
- }
- }
-
- String recursivelyComputeLevelString() {
- String tempName = name;
- String levelString = null;
- int indexOfLastDot = tempName.length();
- while ((levelString == null) && (indexOfLastDot > -1)) {
- tempName = tempName.substring(0, indexOfLastDot);
- levelString = getStringProperty(LOG_KEY_PREFIX + tempName, null);
- indexOfLastDot = String.valueOf(tempName).lastIndexOf(".");
- }
- return levelString;
- }
-
- private static int stringToLevel(String levelStr) {
- if ("trace".equalsIgnoreCase(levelStr)) {
- return LOG_LEVEL_TRACE;
- } else if ("debug".equalsIgnoreCase(levelStr)) {
- return LOG_LEVEL_DEBUG;
- } else if ("info".equalsIgnoreCase(levelStr)) {
- return LOG_LEVEL_INFO;
- } else if ("warn".equalsIgnoreCase(levelStr)) {
- return LOG_LEVEL_WARN;
- } else if ("error".equalsIgnoreCase(levelStr)) {
- return LOG_LEVEL_ERROR;
- }
- // assume INFO by default
- return LOG_LEVEL_INFO;
- }
-
- /**
- * This is our internal implementation for logging regular (non-parameterized)
- * log messages.
- *
- * @param level One of the LOG_LEVEL_XXX constants defining the log level
- * @param message The message itself
- * @param t The exception whose stack trace should be logged
- */
- private void log(int level, String message, Throwable t) {
- if (!isLevelEnabled(level)) {
- return;
- }
-
- StringBuilder buf = new StringBuilder(32);
-
- // Append date-time if so configured
- if (SHOW_DATE_TIME) {
- if (DATE_FORMATTER != null) {
- buf.append(getFormattedDate());
- buf.append(' ');
- } else {
- buf.append(System.currentTimeMillis() - START_TIME);
- buf.append(' ');
- }
- }
-
- // Append current thread name if so configured
- if (SHOW_THREAD_NAME) {
- buf.append('[');
- buf.append(Thread.currentThread().getName());
- buf.append("] ");
- }
-
- if (LEVEL_IN_BRACKETS)
- buf.append('[');
-
- // Append a readable representation of the log level
- switch (level) {
- case LOG_LEVEL_TRACE:
- buf.append("TRACE");
- break;
- case LOG_LEVEL_DEBUG:
- buf.append("DEBUG");
- break;
- case LOG_LEVEL_INFO:
- buf.append("INFO");
- break;
- case LOG_LEVEL_WARN:
- buf.append(WARN_LEVEL_STRING);
- break;
- case LOG_LEVEL_ERROR:
- buf.append("ERROR");
- break;
- }
- if (LEVEL_IN_BRACKETS)
- buf.append(']');
- buf.append(' ');
-
- // Append the name of the log instance if so configured
- if (SHOW_SHORT_LOG_NAME) {
- if (shortLogName == null)
- shortLogName = computeShortName();
- buf.append(String.valueOf(shortLogName)).append(" - ");
- } else if (SHOW_LOG_NAME) {
- buf.append(String.valueOf(name)).append(" - ");
- }
-
- // Append the message
- buf.append(message);
-
- write(buf, t);
-
- }
-
- void write(StringBuilder buf, Throwable t) {
- TARGET_STREAM.println(buf.toString());
- if (t != null) {
- t.printStackTrace(TARGET_STREAM);
- }
- TARGET_STREAM.flush();
- }
-
- private String getFormattedDate() {
- Date now = new Date();
- String dateText;
- synchronized (DATE_FORMATTER) {
- dateText = DATE_FORMATTER.format(now);
- }
- return dateText;
- }
-
- private String computeShortName() {
- return name.substring(name.lastIndexOf(".") + 1);
- }
-
- /**
- * For formatted messages, first substitute arguments and then log.
- *
- * @param level
- * @param format
- * @param arg1
- * @param arg2
- */
- private void formatAndLog(int level, String format, Object arg1, Object arg2) {
- if (!isLevelEnabled(level)) {
- return;
- }
- FormattingTuple tp = MessageFormatter.format(format, arg1, arg2);
- log(level, tp.getMessage(), tp.getThrowable());
- }
-
- /**
- * For formatted messages, first substitute arguments and then log.
- *
- * @param level
- * @param format
- * @param arguments a list of 3 ore more arguments
- */
- private void formatAndLog(int level, String format, Object... arguments) {
- if (!isLevelEnabled(level)) {
- return;
- }
- FormattingTuple tp = MessageFormatter.arrayFormat(format, arguments);
- log(level, tp.getMessage(), tp.getThrowable());
- }
-
- /**
- * Is the given log level currently enabled?
- *
- * @param logLevel is this level enabled?
- */
- protected boolean isLevelEnabled(int logLevel) {
- // log level are numerically ordered so can use simple numeric
- // comparison
- return (logLevel >= currentLogLevel);
- }
-
- /** Are {@code trace} messages currently enabled? */
- public boolean isTraceEnabled() {
- return isLevelEnabled(LOG_LEVEL_TRACE);
- }
-
- /**
- * A simple implementation which logs messages of level TRACE according
- * to the format outlined above.
- */
- public void trace(String msg) {
- log(LOG_LEVEL_TRACE, msg, null);
- }
-
- /**
- * Perform single parameter substitution before logging the message of level
- * TRACE according to the format outlined above.
- */
- public void trace(String format, Object param1) {
- formatAndLog(LOG_LEVEL_TRACE, format, param1, null);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * TRACE according to the format outlined above.
- */
- public void trace(String format, Object param1, Object param2) {
- formatAndLog(LOG_LEVEL_TRACE, format, param1, param2);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * TRACE according to the format outlined above.
- */
- public void trace(String format, Object... argArray) {
- formatAndLog(LOG_LEVEL_TRACE, format, argArray);
- }
-
- /** Log a message of level TRACE, including an exception. */
- public void trace(String msg, Throwable t) {
- log(LOG_LEVEL_TRACE, msg, t);
- }
-
- /** Are {@code debug} messages currently enabled? */
- public boolean isDebugEnabled() {
- return isLevelEnabled(LOG_LEVEL_DEBUG);
- }
-
- /**
- * A simple implementation which logs messages of level DEBUG according
- * to the format outlined above.
- */
- public void debug(String msg) {
- log(LOG_LEVEL_DEBUG, msg, null);
- }
-
- /**
- * Perform single parameter substitution before logging the message of level
- * DEBUG according to the format outlined above.
- */
- public void debug(String format, Object param1) {
- formatAndLog(LOG_LEVEL_DEBUG, format, param1, null);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * DEBUG according to the format outlined above.
- */
- public void debug(String format, Object param1, Object param2) {
- formatAndLog(LOG_LEVEL_DEBUG, format, param1, param2);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * DEBUG according to the format outlined above.
- */
- public void debug(String format, Object... argArray) {
- formatAndLog(LOG_LEVEL_DEBUG, format, argArray);
- }
-
- /** Log a message of level DEBUG, including an exception. */
- public void debug(String msg, Throwable t) {
- log(LOG_LEVEL_DEBUG, msg, t);
- }
-
- /** Are {@code info} messages currently enabled? */
- public boolean isInfoEnabled() {
- return isLevelEnabled(LOG_LEVEL_INFO);
- }
-
- /**
- * A simple implementation which logs messages of level INFO according
- * to the format outlined above.
- */
- public void info(String msg) {
- log(LOG_LEVEL_INFO, msg, null);
- }
-
- /**
- * Perform single parameter substitution before logging the message of level
- * INFO according to the format outlined above.
- */
- public void info(String format, Object arg) {
- formatAndLog(LOG_LEVEL_INFO, format, arg, null);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * INFO according to the format outlined above.
- */
- public void info(String format, Object arg1, Object arg2) {
- formatAndLog(LOG_LEVEL_INFO, format, arg1, arg2);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * INFO according to the format outlined above.
- */
- public void info(String format, Object... argArray) {
- formatAndLog(LOG_LEVEL_INFO, format, argArray);
- }
-
- /** Log a message of level INFO, including an exception. */
- public void info(String msg, Throwable t) {
- log(LOG_LEVEL_INFO, msg, t);
- }
-
- /** Are {@code warn} messages currently enabled? */
- public boolean isWarnEnabled() {
- return isLevelEnabled(LOG_LEVEL_WARN);
- }
-
- /**
- * A simple implementation which always logs messages of level WARN according
- * to the format outlined above.
- */
- public void warn(String msg) {
- log(LOG_LEVEL_WARN, msg, null);
- }
-
- /**
- * Perform single parameter substitution before logging the message of level
- * WARN according to the format outlined above.
- */
- public void warn(String format, Object arg) {
- formatAndLog(LOG_LEVEL_WARN, format, arg, null);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * WARN according to the format outlined above.
- */
- public void warn(String format, Object arg1, Object arg2) {
- formatAndLog(LOG_LEVEL_WARN, format, arg1, arg2);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * WARN according to the format outlined above.
- */
- public void warn(String format, Object... argArray) {
- formatAndLog(LOG_LEVEL_WARN, format, argArray);
- }
-
- /** Log a message of level WARN, including an exception. */
- public void warn(String msg, Throwable t) {
- log(LOG_LEVEL_WARN, msg, t);
- }
-
- /** Are {@code error} messages currently enabled? */
- public boolean isErrorEnabled() {
- return isLevelEnabled(LOG_LEVEL_ERROR);
- }
-
- /**
- * A simple implementation which always logs messages of level ERROR according
- * to the format outlined above.
- */
- public void error(String msg) {
- log(LOG_LEVEL_ERROR, msg, null);
- }
-
- /**
- * Perform single parameter substitution before logging the message of level
- * ERROR according to the format outlined above.
- */
- public void error(String format, Object arg) {
- formatAndLog(LOG_LEVEL_ERROR, format, arg, null);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * ERROR according to the format outlined above.
- */
- public void error(String format, Object arg1, Object arg2) {
- formatAndLog(LOG_LEVEL_ERROR, format, arg1, arg2);
- }
-
- /**
- * Perform double parameter substitution before logging the message of level
- * ERROR according to the format outlined above.
- */
- public void error(String format, Object... argArray) {
- formatAndLog(LOG_LEVEL_ERROR, format, argArray);
- }
-
- /** Log a message of level ERROR, including an exception. */
- public void error(String msg, Throwable t) {
- log(LOG_LEVEL_ERROR, msg, t);
- }
-}
diff --git a/slf4j-simple/src/main/java/org/slf4j/impl/StaticLoggerBinder.java b/slf4j-simple/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
deleted file mode 100644
index a08ff675..00000000
--- a/slf4j-simple/src/main/java/org/slf4j/impl/StaticLoggerBinder.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.ILoggerFactory;
-import org.slf4j.LoggerFactory;
-import org.slf4j.spi.LoggerFactoryBinder;
-
-/**
- * The binding of {@link LoggerFactory} class with an actual instance of
- * {@link ILoggerFactory} is performed using information returned by this class.
- *
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticLoggerBinder implements LoggerFactoryBinder {
-
- /**
- * The unique instance of this class.
- *
- */
- private static final StaticLoggerBinder SINGLETON = new StaticLoggerBinder();
-
- /**
- * Return the singleton of this class.
- *
- * @return the StaticLoggerBinder singleton
- */
- public static final StaticLoggerBinder getSingleton() {
- return SINGLETON;
- }
-
- /**
- * Declare the version of the SLF4J API this implementation is compiled
- * against. The value of this field is usually modified with each release.
- */
- // to avoid constant folding by the compiler, this field must *not* be final
- public static String REQUESTED_API_VERSION = "1.6.99"; // !final
-
- private static final String loggerFactoryClassStr = SimpleLoggerFactory.class.getName();
-
- /**
- * The ILoggerFactory instance returned by the {@link #getLoggerFactory}
- * method should always be the same object
- */
- private final ILoggerFactory loggerFactory;
-
- private StaticLoggerBinder() {
- loggerFactory = new SimpleLoggerFactory();
- }
-
- public ILoggerFactory getLoggerFactory() {
- return loggerFactory;
- }
-
- public String getLoggerFactoryClassStr() {
- return loggerFactoryClassStr;
- }
-}
diff --git a/slf4j-simple/src/main/java/org/slf4j/impl/StaticMDCBinder.java b/slf4j-simple/src/main/java/org/slf4j/impl/StaticMDCBinder.java
deleted file mode 100644
index 086b0169..00000000
--- a/slf4j-simple/src/main/java/org/slf4j/impl/StaticMDCBinder.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.slf4j.helpers.NOPMDCAdapter;
-import org.slf4j.spi.MDCAdapter;
-
-/**
- * This implementation is bound to {@link NOPMDCAdapter}.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMDCBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMDCBinder SINGLETON = new StaticMDCBinder();
-
- private StaticMDCBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link StaticMDCBinder}.
- */
- public MDCAdapter getMDCA() {
- return new NOPMDCAdapter();
- }
-
- public String getMDCAdapterClassStr() {
- return NOPMDCAdapter.class.getName();
- }
-}
diff --git a/slf4j-simple/src/main/java/org/slf4j/impl/StaticMarkerBinder.java b/slf4j-simple/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
deleted file mode 100644
index 435a924b..00000000
--- a/slf4j-simple/src/main/java/org/slf4j/impl/StaticMarkerBinder.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/**
- * Copyright (c) 2004-2011 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-
-package org.slf4j.impl;
-
-import org.slf4j.IMarkerFactory;
-import org.slf4j.MarkerFactory;
-import org.slf4j.helpers.BasicMarkerFactory;
-import org.slf4j.spi.MarkerFactoryBinder;
-
-/**
- *
- * The binding of {@link MarkerFactory} class with an actual instance of
- * {@link IMarkerFactory} is performed using information returned by this class.
- *
- * @author Ceki G&uuml;lc&uuml;
- */
-public class StaticMarkerBinder implements MarkerFactoryBinder {
-
- /**
- * The unique instance of this class.
- */
- public static final StaticMarkerBinder SINGLETON = new StaticMarkerBinder();
-
- final IMarkerFactory markerFactory = new BasicMarkerFactory();
-
- private StaticMarkerBinder() {
- }
-
- /**
- * Currently this method always returns an instance of
- * {@link BasicMarkerFactory}.
- */
- public IMarkerFactory getMarkerFactory() {
- return markerFactory;
- }
-
- /**
- * Currently, this method returns the class name of
- * {@link BasicMarkerFactory}.
- */
- public String getMarkerFactoryClassStr() {
- return BasicMarkerFactory.class.getName();
- }
-
-}
diff --git a/slf4j-simple/src/main/java/org/slf4j/simple/OutputChoice.java b/slf4j-simple/src/main/java/org/slf4j/simple/OutputChoice.java
new file mode 100755
index 00000000..87a988e2
--- /dev/null
+++ b/slf4j-simple/src/main/java/org/slf4j/simple/OutputChoice.java
@@ -0,0 +1,55 @@
+package org.slf4j.simple;
+
+import java.io.PrintStream;
+
+/**
+ * This class encapsulates the user's choice of output target.
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ *
+ */
+class OutputChoice {
+
+ enum OutputChoiceType {
+ SYS_OUT, CACHED_SYS_OUT, SYS_ERR, CACHED_SYS_ERR, FILE;
+ }
+
+ final OutputChoiceType outputChoiceType;
+ final PrintStream targetPrintStream;
+
+ OutputChoice(OutputChoiceType outputChoiceType) {
+ if (outputChoiceType == OutputChoiceType.FILE) {
+ throw new IllegalArgumentException();
+ }
+ this.outputChoiceType = outputChoiceType;
+ if (outputChoiceType == OutputChoiceType.CACHED_SYS_OUT) {
+ this.targetPrintStream = System.out;
+ } else if (outputChoiceType == OutputChoiceType.CACHED_SYS_ERR) {
+ this.targetPrintStream = System.err;
+ } else {
+ this.targetPrintStream = null;
+ }
+ }
+
+ OutputChoice(PrintStream printStream) {
+ this.outputChoiceType = OutputChoiceType.FILE;
+ this.targetPrintStream = printStream;
+ }
+
+ PrintStream getTargetPrintStream() {
+ switch (outputChoiceType) {
+ case SYS_OUT:
+ return System.out;
+ case SYS_ERR:
+ return System.err;
+ case CACHED_SYS_ERR:
+ case CACHED_SYS_OUT:
+ case FILE:
+ return targetPrintStream;
+ default:
+ throw new IllegalArgumentException();
+ }
+
+ }
+
+}
diff --git a/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLogger.java b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLogger.java
new file mode 100644
index 00000000..c1b6c788
--- /dev/null
+++ b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLogger.java
@@ -0,0 +1,475 @@
+/**
+ * Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.simple;
+
+import java.io.PrintStream;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+import org.slf4j.Logger;
+import org.slf4j.Marker;
+import org.slf4j.event.Level;
+import org.slf4j.event.LoggingEvent;
+import org.slf4j.helpers.LegacyAbstractLogger;
+import org.slf4j.helpers.MessageFormatter;
+import org.slf4j.helpers.NormalizedParameters;
+import org.slf4j.spi.LocationAwareLogger;
+
+/**
+ * <p>
+ * Simple implementation of {@link Logger} that sends all enabled log messages,
+ * for all defined loggers, to the console ({@code System.err}). The following
+ * system properties are supported to configure the behavior of this logger:
+ *
+ *
+ * <ul>
+ * <li><code>org.slf4j.simpleLogger.logFile</code> - The output target which can
+ * be the <em>path</em> to a file, or the special values "System.out" and
+ * "System.err". Default is "System.err".</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.cacheOutputStream</code> - If the output
+ * target is set to "System.out" or "System.err" (see preceding entry), by
+ * default, logs will be output to the latest value referenced by
+ * <code>System.out/err</code> variables. By setting this parameter to true, the
+ * output stream will be cached, i.e. assigned once at initialization time and
+ * re-used independently of the current value referenced by
+ * <code>System.out/err</code>.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.defaultLogLevel</code> - Default log level
+ * for all instances of SimpleLogger. Must be one of ("trace", "debug", "info",
+ * "warn", "error" or "off"). If not specified, defaults to "info".</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.log.<em>a.b.c</em></code> - Logging detail
+ * level for a SimpleLogger instance named "a.b.c". Right-side value must be one
+ * of "trace", "debug", "info", "warn", "error" or "off". When a SimpleLogger
+ * named "a.b.c" is initialized, its level is assigned from this property. If
+ * unspecified, the level of nearest parent logger will be used, and if none is
+ * set, then the value specified by
+ * <code>org.slf4j.simpleLogger.defaultLogLevel</code> will be used.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.showDateTime</code> - Set to
+ * <code>true</code> if you want the current date and time to be included in
+ * output messages. Default is <code>false</code></li>
+ *
+ * <li><code>org.slf4j.simpleLogger.dateTimeFormat</code> - The date and time
+ * format to be used in the output messages. The pattern describing the date and
+ * time format is defined by <a href=
+ * "http://docs.oracle.com/javase/1.5.0/docs/api/java/text/SimpleDateFormat.html">
+ * <code>SimpleDateFormat</code></a>. If the format is not specified or is
+ * invalid, the number of milliseconds since start up will be output.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.showThreadName</code> -Set to
+ * <code>true</code> if you want to output the current thread name. Defaults to
+ * <code>true</code>.</li>
+ *
+ * <li>(since version 1.7.33 and 2.0.0-alpha6) <code>org.slf4j.simpleLogger.showThreadId</code> -
+ * If you would like to output the current thread id, then set to
+ * <code>true</code>. Defaults to <code>false</code>.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.showLogName</code> - Set to
+ * <code>true</code> if you want the Logger instance name to be included in
+ * output messages. Defaults to <code>true</code>.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.showShortLogName</code> - Set to
+ * <code>true</code> if you want the last component of the name to be included
+ * in output messages. Defaults to <code>false</code>.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.levelInBrackets</code> - Should the level
+ * string be output in brackets? Defaults to <code>false</code>.</li>
+ *
+ * <li><code>org.slf4j.simpleLogger.warnLevelString</code> - The string value
+ * output for the warn level. Defaults to <code>WARN</code>.</li>
+ *
+ * </ul>
+ *
+ * <p>
+ * In addition to looking for system properties with the names specified above,
+ * this implementation also checks for a class loader resource named
+ * <code>"simplelogger.properties"</code>, and includes any matching definitions
+ * from this resource (if it exists).
+ *
+ *
+ * <p>
+ * With no configuration, the default output includes the relative time in
+ * milliseconds, thread name, the level, logger name, and the message followed
+ * by the line separator for the host. In log4j terms it amounts to the "%r [%t]
+ * %level %logger - %m%n" pattern.
+ *
+ * <p>
+ * Sample output follows.
+ *
+ *
+ * <pre>
+ * 176 [main] INFO examples.Sort - Populating an array of 2 elements in reverse order.
+ * 225 [main] INFO examples.SortAlgo - Entered the sort method.
+ * 304 [main] INFO examples.SortAlgo - Dump of integer array:
+ * 317 [main] INFO examples.SortAlgo - Element [0] = 0
+ * 331 [main] INFO examples.SortAlgo - Element [1] = 1
+ * 343 [main] INFO examples.Sort - The next log statement should be an error message.
+ * 346 [main] ERROR examples.SortAlgo - Tried to dump an uninitialized array.
+ * at org.log4j.examples.SortAlgo.dump(SortAlgo.java:58)
+ * at org.log4j.examples.Sort.main(Sort.java:64)
+ * 467 [main] INFO examples.Sort - Exiting main method.
+ * </pre>
+ *
+ * <p>
+ * This implementation is heavily inspired by
+ * <a href="http://commons.apache.org/logging/">Apache Commons Logging</a>'s
+ * SimpleLog.
+ *
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @author Scott Sanders
+ * @author Rod Waldhoff
+ * @author Robert Burrell Donkin
+ * @author C&eacute;drik LIME
+ */
+public class SimpleLogger extends LegacyAbstractLogger {
+
+ private static final long serialVersionUID = -632788891211436180L;
+
+ private static final long START_TIME = System.currentTimeMillis();
+
+ protected static final int LOG_LEVEL_TRACE = LocationAwareLogger.TRACE_INT;
+ protected static final int LOG_LEVEL_DEBUG = LocationAwareLogger.DEBUG_INT;
+ protected static final int LOG_LEVEL_INFO = LocationAwareLogger.INFO_INT;
+ protected static final int LOG_LEVEL_WARN = LocationAwareLogger.WARN_INT;
+ protected static final int LOG_LEVEL_ERROR = LocationAwareLogger.ERROR_INT;
+
+ static char SP = ' ';
+ static final String TID_PREFIX = "tid=";
+
+
+ // The OFF level can only be used in configuration files to disable logging.
+ // It has
+ // no printing method associated with it in o.s.Logger interface.
+ protected static final int LOG_LEVEL_OFF = LOG_LEVEL_ERROR + 10;
+
+ private static boolean INITIALIZED = false;
+ static final SimpleLoggerConfiguration CONFIG_PARAMS = new SimpleLoggerConfiguration();
+
+ static void lazyInit() {
+ if (INITIALIZED) {
+ return;
+ }
+ INITIALIZED = true;
+ init();
+ }
+
+ // external software might be invoking this method directly. Do not rename
+ // or change its semantics.
+ static void init() {
+ CONFIG_PARAMS.init();
+ }
+
+ /** The current log level */
+ protected int currentLogLevel = LOG_LEVEL_INFO;
+ /** The short name of this simple log instance */
+ private transient String shortLogName = null;
+
+ /**
+ * All system properties used by <code>SimpleLogger</code> start with this
+ * prefix
+ */
+ public static final String SYSTEM_PREFIX = "org.slf4j.simpleLogger.";
+
+ public static final String LOG_KEY_PREFIX = SimpleLogger.SYSTEM_PREFIX + "log.";
+
+ public static final String CACHE_OUTPUT_STREAM_STRING_KEY = SimpleLogger.SYSTEM_PREFIX + "cacheOutputStream";
+
+ public static final String WARN_LEVEL_STRING_KEY = SimpleLogger.SYSTEM_PREFIX + "warnLevelString";
+
+ public static final String LEVEL_IN_BRACKETS_KEY = SimpleLogger.SYSTEM_PREFIX + "levelInBrackets";
+
+ public static final String LOG_FILE_KEY = SimpleLogger.SYSTEM_PREFIX + "logFile";
+
+ public static final String SHOW_SHORT_LOG_NAME_KEY = SimpleLogger.SYSTEM_PREFIX + "showShortLogName";
+
+ public static final String SHOW_LOG_NAME_KEY = SimpleLogger.SYSTEM_PREFIX + "showLogName";
+
+ public static final String SHOW_THREAD_NAME_KEY = SimpleLogger.SYSTEM_PREFIX + "showThreadName";
+
+ public static final String SHOW_THREAD_ID_KEY = SimpleLogger.SYSTEM_PREFIX + "showThreadId";
+
+ public static final String DATE_TIME_FORMAT_KEY = SimpleLogger.SYSTEM_PREFIX + "dateTimeFormat";
+
+ public static final String SHOW_DATE_TIME_KEY = SimpleLogger.SYSTEM_PREFIX + "showDateTime";
+
+ public static final String DEFAULT_LOG_LEVEL_KEY = SimpleLogger.SYSTEM_PREFIX + "defaultLogLevel";
+
+ /**
+ * Protected access allows only {@link SimpleLoggerFactory} and also derived classes to instantiate
+ * SimpleLogger instances.
+ */
+ protected SimpleLogger(String name) {
+ this.name = name;
+
+ String levelString = recursivelyComputeLevelString();
+ if (levelString != null) {
+ this.currentLogLevel = SimpleLoggerConfiguration.stringToLevel(levelString);
+ } else {
+ this.currentLogLevel = CONFIG_PARAMS.defaultLogLevel;
+ }
+ }
+
+ String recursivelyComputeLevelString() {
+ String tempName = name;
+ String levelString = null;
+ int indexOfLastDot = tempName.length();
+ while ((levelString == null) && (indexOfLastDot > -1)) {
+ tempName = tempName.substring(0, indexOfLastDot);
+ levelString = CONFIG_PARAMS.getStringProperty(SimpleLogger.LOG_KEY_PREFIX + tempName, null);
+ indexOfLastDot = String.valueOf(tempName).lastIndexOf(".");
+ }
+ return levelString;
+ }
+
+ /**
+ * To avoid intermingling of log messages and associated stack traces, the two
+ * operations are done in a synchronized block.
+ *
+ * @param buf
+ * @param t
+ */
+ void write(StringBuilder buf, Throwable t) {
+ PrintStream targetStream = CONFIG_PARAMS.outputChoice.getTargetPrintStream();
+
+ synchronized (CONFIG_PARAMS) {
+ targetStream.println(buf.toString());
+ writeThrowable(t, targetStream);
+ targetStream.flush();
+ }
+
+ }
+
+ protected void writeThrowable(Throwable t, PrintStream targetStream) {
+ if (t != null) {
+ t.printStackTrace(targetStream);
+ }
+ }
+
+ private String getFormattedDate() {
+ Date now = new Date();
+ String dateText;
+ synchronized (CONFIG_PARAMS.dateFormatter) {
+ dateText = CONFIG_PARAMS.dateFormatter.format(now);
+ }
+ return dateText;
+ }
+
+ private String computeShortName() {
+ return name.substring(name.lastIndexOf(".") + 1);
+ }
+
+ // /**
+ // * For formatted messages, first substitute arguments and then log.
+ // *
+ // * @param level
+ // * @param format
+ // * @param arg1
+ // * @param arg2
+ // */
+ // private void formatAndLog(int level, String format, Object arg1, Object arg2) {
+ // if (!isLevelEnabled(level)) {
+ // return;
+ // }
+ // FormattingTuple tp = MessageFormatter.format(format, arg1, arg2);
+ // log(level, tp.getMessage(), tp.getThrowable());
+ // }
+
+ // /**
+ // * For formatted messages, first substitute arguments and then log.
+ // *
+ // * @param level
+ // * @param format
+ // * @param arguments
+ // * a list of 3 ore more arguments
+ // */
+ // private void formatAndLog(int level, String format, Object... arguments) {
+ // if (!isLevelEnabled(level)) {
+ // return;
+ // }
+ // FormattingTuple tp = MessageFormatter.arrayFormat(format, arguments);
+ // log(level, tp.getMessage(), tp.getThrowable());
+ // }
+
+ /**
+ * Is the given log level currently enabled?
+ *
+ * @param logLevel is this level enabled?
+ * @return whether the logger is enabled for the given level
+ */
+ protected boolean isLevelEnabled(int logLevel) {
+ // log level are numerically ordered so can use simple numeric
+ // comparison
+ return (logLevel >= currentLogLevel);
+ }
+
+ /** Are {@code trace} messages currently enabled? */
+ public boolean isTraceEnabled() {
+ return isLevelEnabled(LOG_LEVEL_TRACE);
+ }
+
+ /** Are {@code debug} messages currently enabled? */
+ public boolean isDebugEnabled() {
+ return isLevelEnabled(LOG_LEVEL_DEBUG);
+ }
+
+ /** Are {@code info} messages currently enabled? */
+ public boolean isInfoEnabled() {
+ return isLevelEnabled(LOG_LEVEL_INFO);
+ }
+
+ /** Are {@code warn} messages currently enabled? */
+ public boolean isWarnEnabled() {
+ return isLevelEnabled(LOG_LEVEL_WARN);
+ }
+
+ /** Are {@code error} messages currently enabled? */
+ public boolean isErrorEnabled() {
+ return isLevelEnabled(LOG_LEVEL_ERROR);
+ }
+
+ /**
+ * SimpleLogger's implementation of
+ * {@link org.slf4j.helpers.AbstractLogger#handleNormalizedLoggingCall(Level, Marker, String, Object[], Throwable) AbstractLogger#handleNormalizedLoggingCall}
+ * }
+ *
+ * @param level the SLF4J level for this event
+ * @param marker The marker to be used for this event, may be null.
+ * @param messagePattern The message pattern which will be parsed and formatted
+ * @param arguments the array of arguments to be formatted, may be null
+ * @param throwable The exception whose stack trace should be logged, may be null
+ */
+ @Override
+ protected void handleNormalizedLoggingCall(Level level, Marker marker, String messagePattern, Object[] arguments, Throwable throwable) {
+
+ List<Marker> markers = null;
+
+ if (marker != null) {
+ markers = new ArrayList<>();
+ markers.add(marker);
+ }
+
+ innerHandleNormalizedLoggingCall(level, markers, messagePattern, arguments, throwable);
+ }
+
+ private void innerHandleNormalizedLoggingCall(Level level, List<Marker> markers, String messagePattern, Object[] arguments, Throwable t) {
+
+ StringBuilder buf = new StringBuilder(32);
+
+ // Append date-time if so configured
+ if (CONFIG_PARAMS.showDateTime) {
+ if (CONFIG_PARAMS.dateFormatter != null) {
+ buf.append(getFormattedDate());
+ buf.append(SP);
+ } else {
+ buf.append(System.currentTimeMillis() - START_TIME);
+ buf.append(SP);
+ }
+ }
+
+ // Append current thread name if so configured
+ if (CONFIG_PARAMS.showThreadName) {
+ buf.append('[');
+ buf.append(Thread.currentThread().getName());
+ buf.append("] ");
+ }
+
+ if (CONFIG_PARAMS.showThreadId) {
+ buf.append(TID_PREFIX);
+ buf.append(Thread.currentThread().getId());
+ buf.append(SP);
+ }
+
+ if (CONFIG_PARAMS.levelInBrackets)
+ buf.append('[');
+
+ // Append a readable representation of the log level
+ String levelStr = renderLevel(level.toInt());
+ buf.append(levelStr);
+ if (CONFIG_PARAMS.levelInBrackets)
+ buf.append(']');
+ buf.append(SP);
+
+ // Append the name of the log instance if so configured
+ if (CONFIG_PARAMS.showShortLogName) {
+ if (shortLogName == null)
+ shortLogName = computeShortName();
+ buf.append(String.valueOf(shortLogName)).append(" - ");
+ } else if (CONFIG_PARAMS.showLogName) {
+ buf.append(String.valueOf(name)).append(" - ");
+ }
+
+ if (markers != null) {
+ buf.append(SP);
+ for (Marker marker : markers) {
+ buf.append(marker.getName()).append(SP);
+ }
+ }
+
+ String formattedMessage = MessageFormatter.basicArrayFormat(messagePattern, arguments);
+
+ // Append the message
+ buf.append(formattedMessage);
+
+ write(buf, t);
+ }
+
+ protected String renderLevel(int levelInt) {
+ switch (levelInt) {
+ case LOG_LEVEL_TRACE:
+ return "TRACE";
+ case LOG_LEVEL_DEBUG:
+ return("DEBUG");
+ case LOG_LEVEL_INFO:
+ return "INFO";
+ case LOG_LEVEL_WARN:
+ return "WARN";
+ case LOG_LEVEL_ERROR:
+ return "ERROR";
+ }
+ throw new IllegalStateException("Unrecognized level ["+levelInt+"]");
+ }
+
+ public void log(LoggingEvent event) {
+ int levelInt = event.getLevel().toInt();
+
+ if (!isLevelEnabled(levelInt)) {
+ return;
+ }
+
+ NormalizedParameters np = NormalizedParameters.normalize(event);
+
+ innerHandleNormalizedLoggingCall(event.getLevel(), event.getMarkers(), np.getMessage(), np.getArguments(), event.getThrowable());
+ }
+
+ @Override
+ protected String getFullyQualifiedCallerName() {
+ return null;
+ }
+
+}
diff --git a/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerConfiguration.java b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerConfiguration.java
new file mode 100755
index 00000000..0a7f1310
--- /dev/null
+++ b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerConfiguration.java
@@ -0,0 +1,193 @@
+package org.slf4j.simple;
+
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.InputStream;
+import java.io.PrintStream;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.Properties;
+
+import org.slf4j.helpers.Reporter;
+import org.slf4j.helpers.Util;
+import org.slf4j.simple.OutputChoice.OutputChoiceType;
+
+/**
+ * This class holds configuration values for {@link SimpleLogger}. The
+ * values are computed at runtime. See {@link SimpleLogger} documentation for
+ * more information.
+ *
+ *
+ * @author Ceki G&uuml;lc&uuml;
+ * @author Scott Sanders
+ * @author Rod Waldhoff
+ * @author Robert Burrell Donkin
+ * @author C&eacute;drik LIME
+ *
+ * @since 1.7.25
+ */
+public class SimpleLoggerConfiguration {
+
+ private static final String CONFIGURATION_FILE = "simplelogger.properties";
+
+ static int DEFAULT_LOG_LEVEL_DEFAULT = SimpleLogger.LOG_LEVEL_INFO;
+ int defaultLogLevel = DEFAULT_LOG_LEVEL_DEFAULT;
+
+ private static final boolean SHOW_DATE_TIME_DEFAULT = false;
+ boolean showDateTime = SHOW_DATE_TIME_DEFAULT;
+
+ private static final String DATE_TIME_FORMAT_STR_DEFAULT = null;
+ private static String dateTimeFormatStr = DATE_TIME_FORMAT_STR_DEFAULT;
+
+ DateFormat dateFormatter = null;
+
+ private static final boolean SHOW_THREAD_NAME_DEFAULT = true;
+ boolean showThreadName = SHOW_THREAD_NAME_DEFAULT;
+
+ /**
+ * See https://jira.qos.ch/browse/SLF4J-499
+ * @since 1.7.33 and 2.0.0-alpha6
+ */
+ private static final boolean SHOW_THREAD_ID_DEFAULT = false;
+ boolean showThreadId = SHOW_THREAD_ID_DEFAULT;
+
+ final static boolean SHOW_LOG_NAME_DEFAULT = true;
+ boolean showLogName = SHOW_LOG_NAME_DEFAULT;
+
+ private static final boolean SHOW_SHORT_LOG_NAME_DEFAULT = false;
+ boolean showShortLogName = SHOW_SHORT_LOG_NAME_DEFAULT;
+
+ private static final boolean LEVEL_IN_BRACKETS_DEFAULT = false;
+ boolean levelInBrackets = LEVEL_IN_BRACKETS_DEFAULT;
+
+ private static final String LOG_FILE_DEFAULT = "System.err";
+ private String logFile = LOG_FILE_DEFAULT;
+ OutputChoice outputChoice = null;
+
+ private static final boolean CACHE_OUTPUT_STREAM_DEFAULT = false;
+ private boolean cacheOutputStream = CACHE_OUTPUT_STREAM_DEFAULT;
+
+ private static final String WARN_LEVELS_STRING_DEFAULT = "WARN";
+ String warnLevelString = WARN_LEVELS_STRING_DEFAULT;
+
+ private final Properties properties = new Properties();
+
+ void init() {
+ loadProperties();
+
+ String defaultLogLevelString = getStringProperty(SimpleLogger.DEFAULT_LOG_LEVEL_KEY, null);
+ if (defaultLogLevelString != null)
+ defaultLogLevel = stringToLevel(defaultLogLevelString);
+
+ showLogName = getBooleanProperty(SimpleLogger.SHOW_LOG_NAME_KEY, SimpleLoggerConfiguration.SHOW_LOG_NAME_DEFAULT);
+ showShortLogName = getBooleanProperty(SimpleLogger.SHOW_SHORT_LOG_NAME_KEY, SHOW_SHORT_LOG_NAME_DEFAULT);
+ showDateTime = getBooleanProperty(SimpleLogger.SHOW_DATE_TIME_KEY, SHOW_DATE_TIME_DEFAULT);
+ showThreadName = getBooleanProperty(SimpleLogger.SHOW_THREAD_NAME_KEY, SHOW_THREAD_NAME_DEFAULT);
+ showThreadId = getBooleanProperty(SimpleLogger.SHOW_THREAD_ID_KEY, SHOW_THREAD_ID_DEFAULT);
+ dateTimeFormatStr = getStringProperty(SimpleLogger.DATE_TIME_FORMAT_KEY, DATE_TIME_FORMAT_STR_DEFAULT);
+ levelInBrackets = getBooleanProperty(SimpleLogger.LEVEL_IN_BRACKETS_KEY, LEVEL_IN_BRACKETS_DEFAULT);
+ warnLevelString = getStringProperty(SimpleLogger.WARN_LEVEL_STRING_KEY, WARN_LEVELS_STRING_DEFAULT);
+
+ logFile = getStringProperty(SimpleLogger.LOG_FILE_KEY, logFile);
+
+ cacheOutputStream = getBooleanProperty(SimpleLogger.CACHE_OUTPUT_STREAM_STRING_KEY, CACHE_OUTPUT_STREAM_DEFAULT);
+ outputChoice = computeOutputChoice(logFile, cacheOutputStream);
+
+ if (dateTimeFormatStr != null) {
+ try {
+ dateFormatter = new SimpleDateFormat(dateTimeFormatStr);
+ } catch (IllegalArgumentException e) {
+ Reporter.error("Bad date format in " + CONFIGURATION_FILE + "; will output relative time", e);
+ }
+ }
+ }
+
+ private void loadProperties() {
+ // Add props from the resource simplelogger.properties
+ InputStream in = AccessController.doPrivileged((PrivilegedAction<InputStream>) () -> {
+ ClassLoader threadCL = Thread.currentThread().getContextClassLoader();
+ if (threadCL != null) {
+ return threadCL.getResourceAsStream(CONFIGURATION_FILE);
+ } else {
+ return ClassLoader.getSystemResourceAsStream(CONFIGURATION_FILE);
+ }
+ });
+ if (null != in) {
+ try {
+ properties.load(in);
+ } catch (java.io.IOException e) {
+ // ignored
+ } finally {
+ try {
+ in.close();
+ } catch (java.io.IOException e) {
+ // ignored
+ }
+ }
+ }
+ }
+
+ String getStringProperty(String name, String defaultValue) {
+ String prop = getStringProperty(name);
+ return (prop == null) ? defaultValue : prop;
+ }
+
+ boolean getBooleanProperty(String name, boolean defaultValue) {
+ String prop = getStringProperty(name);
+ return (prop == null) ? defaultValue : "true".equalsIgnoreCase(prop);
+ }
+
+ String getStringProperty(String name) {
+ String prop = null;
+ try {
+ prop = System.getProperty(name);
+ } catch (SecurityException e) {
+ ; // Ignore
+ }
+ return (prop == null) ? properties.getProperty(name) : prop;
+ }
+
+ static int stringToLevel(String levelStr) {
+ if ("trace".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_TRACE;
+ } else if ("debug".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_DEBUG;
+ } else if ("info".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_INFO;
+ } else if ("warn".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_WARN;
+ } else if ("error".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_ERROR;
+ } else if ("off".equalsIgnoreCase(levelStr)) {
+ return SimpleLogger.LOG_LEVEL_OFF;
+ }
+ // assume INFO by default
+ return SimpleLogger.LOG_LEVEL_INFO;
+ }
+
+ private static OutputChoice computeOutputChoice(String logFile, boolean cacheOutputStream) {
+ if ("System.err".equalsIgnoreCase(logFile))
+ if (cacheOutputStream)
+ return new OutputChoice(OutputChoiceType.CACHED_SYS_ERR);
+ else
+ return new OutputChoice(OutputChoiceType.SYS_ERR);
+ else if ("System.out".equalsIgnoreCase(logFile)) {
+ if (cacheOutputStream)
+ return new OutputChoice(OutputChoiceType.CACHED_SYS_OUT);
+ else
+ return new OutputChoice(OutputChoiceType.SYS_OUT);
+ } else {
+ try {
+ FileOutputStream fos = new FileOutputStream(logFile);
+ PrintStream printStream = new PrintStream(fos);
+ return new OutputChoice(printStream);
+ } catch (FileNotFoundException e) {
+ Reporter.error("Could not open [" + logFile + "]. Defaulting to System.err", e);
+ return new OutputChoice(OutputChoiceType.SYS_ERR);
+ }
+ }
+ }
+
+}
diff --git a/slf4j-simple/src/main/java/org/slf4j/impl/SimpleLoggerFactory.java b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerFactory.java
index 4c59f2dc..ceb0d4ee 100644
--- a/slf4j-simple/src/main/java/org/slf4j/impl/SimpleLoggerFactory.java
+++ b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleLoggerFactory.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j.impl;
+package org.slf4j.simple;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
@@ -41,33 +41,37 @@ public class SimpleLoggerFactory implements ILoggerFactory {
ConcurrentMap<String, Logger> loggerMap;
public SimpleLoggerFactory() {
- loggerMap = new ConcurrentHashMap<String, Logger>();
+ loggerMap = new ConcurrentHashMap<>();
+ SimpleLogger.lazyInit();
}
/**
* Return an appropriate {@link SimpleLogger} instance by name.
+ *
+ * This method will call {@link #createLogger(String)} if the logger
+ * has not been created yet.
*/
public Logger getLogger(String name) {
- Logger simpleLogger = loggerMap.get(name);
- if (simpleLogger != null) {
- return simpleLogger;
- } else {
- Logger newInstance = new SimpleLogger(name);
- Logger oldInstance = loggerMap.putIfAbsent(name, newInstance);
- return oldInstance == null ? newInstance : oldInstance;
- }
+ return loggerMap.computeIfAbsent(name, this::createLogger);
+ }
+
+ /**
+ * Actually creates the logger for the given name.
+ */
+ protected Logger createLogger(String name) {
+ return new SimpleLogger(name);
}
/**
* Clear the internal logger cache.
*
- * This method is intended to be called by classes (in the same package) for
- * testing purposes. This method is internal. It can be modified, renamed or
- * removed at any time without notice.
+ * This method is intended to be called by classes (in the same package or
+ * subclasses) for testing purposes. This method is internal. It can be
+ * modified, renamed or removed at any time without notice.
*
* You are strongly discouraged from calling this method in production code.
*/
- void reset() {
+ protected void reset() {
loggerMap.clear();
}
}
diff --git a/slf4j-simple/src/main/java/org/slf4j/simple/SimpleServiceProvider.java b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleServiceProvider.java
new file mode 100755
index 00000000..795200dc
--- /dev/null
+++ b/slf4j-simple/src/main/java/org/slf4j/simple/SimpleServiceProvider.java
@@ -0,0 +1,50 @@
+package org.slf4j.simple;
+
+import org.slf4j.ILoggerFactory;
+import org.slf4j.IMarkerFactory;
+import org.slf4j.helpers.BasicMarkerFactory;
+import org.slf4j.helpers.NOPMDCAdapter;
+import org.slf4j.spi.MDCAdapter;
+import org.slf4j.spi.SLF4JServiceProvider;
+
+public class SimpleServiceProvider implements SLF4JServiceProvider {
+
+ /**
+ * Declare the version of the SLF4J API this implementation is compiled against.
+ * The value of this field is modified with each major release.
+ */
+ // to avoid constant folding by the compiler, this field must *not* be final
+ public static String REQUESTED_API_VERSION = "2.0.99"; // !final
+
+ private ILoggerFactory loggerFactory;
+ private IMarkerFactory markerFactory;
+ private MDCAdapter mdcAdapter;
+
+ public ILoggerFactory getLoggerFactory() {
+ return loggerFactory;
+ }
+
+ @Override
+ public IMarkerFactory getMarkerFactory() {
+ return markerFactory;
+ }
+
+ @Override
+ public MDCAdapter getMDCAdapter() {
+ return mdcAdapter;
+ }
+
+ @Override
+ public String getRequestedApiVersion() {
+ return REQUESTED_API_VERSION;
+ }
+
+ @Override
+ public void initialize() {
+
+ loggerFactory = new SimpleLoggerFactory();
+ markerFactory = new BasicMarkerFactory();
+ mdcAdapter = new NOPMDCAdapter();
+ }
+
+}
diff --git a/slf4j-simple/src/main/java9/module-info.java b/slf4j-simple/src/main/java9/module-info.java
new file mode 100755
index 00000000..9b8e3d24
--- /dev/null
+++ b/slf4j-simple/src/main/java9/module-info.java
@@ -0,0 +1,6 @@
+module org.slf4j.simple {
+ requires org.slf4j;
+ provides org.slf4j.spi.SLF4JServiceProvider with org.slf4j.simple.SimpleServiceProvider;
+ exports org.slf4j.simple;
+ opens org.slf4j.simple to org.slf4j;
+}
diff --git a/slf4j-simple/src/main/resources/META-INF/MANIFEST.MF b/slf4j-simple/src/main/resources/META-INF/MANIFEST.MF
deleted file mode 100644
index 897c9727..00000000
--- a/slf4j-simple/src/main/resources/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,10 +0,0 @@
-Implementation-Title: slf4j-simple
-Bundle-ManifestVersion: 2
-Bundle-SymbolicName: slf4j.simple
-Bundle-Name: slf4j-simple
-Bundle-Vendor: SLF4J.ORG
-Require-Bundle: slf4j.api
-Bundle-RequiredExecutionEnvironment: J2SE-1.5
-Export-Package: org.slf4j.impl;version=${parsedVersion.osgiVersion}
-Import-Package: org.slf4j;version=${parsedVersion.osgiVersion}, org.slf4j.spi;version=${parsedVersion.osgiVersion}, org.slf4j.helpers;version=${parsedVersion.osgiVersion}
-Fragment-Host: slf4j.api \ No newline at end of file
diff --git a/slf4j-simple/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider b/slf4j-simple/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
new file mode 100755
index 00000000..5cda4490
--- /dev/null
+++ b/slf4j-simple/src/main/resources/META-INF/services/org.slf4j.spi.SLF4JServiceProvider
@@ -0,0 +1 @@
+org.slf4j.simple.SimpleServiceProvider \ No newline at end of file
diff --git a/slf4j-simple/src/test/java/org/slf4j/impl/SimpleLoggerTest.java b/slf4j-simple/src/test/java/org/slf4j/impl/SimpleLoggerTest.java
deleted file mode 100644
index 4c84762d..00000000
--- a/slf4j-simple/src/test/java/org/slf4j/impl/SimpleLoggerTest.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/**
- * Copyright (c) 2004-2012 QOS.ch
- * All rights reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- */
-package org.slf4j.impl;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-
-import static junit.framework.Assert.assertEquals;
-import static junit.framework.Assert.assertNull;
-
-public class SimpleLoggerTest {
-
- String A_KEY = SimpleLogger.LOG_KEY_PREFIX + "a";
-
- @Before
- public void before() {
- System.setProperty(A_KEY, "info");
- }
-
- @After
- public void after() {
- System.clearProperty(A_KEY);
- }
-
- @Test
- public void emptyLoggerName() {
- SimpleLogger simpleLogger = new SimpleLogger("a");
- assertEquals("info", simpleLogger.recursivelyComputeLevelString());
- }
-
- @Test
- public void loggerNameWithNoDots_WithLevel() {
- SimpleLogger simpleLogger = new SimpleLogger("a");
- assertEquals("info", simpleLogger.recursivelyComputeLevelString());
- }
-
- @Test
- public void loggerNameWithOneDotShouldInheritFromParent() {
- SimpleLogger simpleLogger = new SimpleLogger("a.b");
- assertEquals("info", simpleLogger.recursivelyComputeLevelString());
- }
-
- @Test
- public void loggerNameWithNoDots_WithNoSetLevel() {
- SimpleLogger simpleLogger = new SimpleLogger("x");
- assertNull(simpleLogger.recursivelyComputeLevelString());
- }
-
- @Test
- public void loggerNameWithOneDot_NoSetLevel() {
- SimpleLogger simpleLogger = new SimpleLogger("x.y");
- assertNull(simpleLogger.recursivelyComputeLevelString());
- }
-
-}
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/AcceptanceTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/AcceptanceTest.java
new file mode 100644
index 00000000..76985073
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/AcceptanceTest.java
@@ -0,0 +1,50 @@
+package org.slf4j.simple;
+
+import org.junit.Ignore;
+import org.slf4j.Logger;
+import org.slf4j.event.Level;
+
+import java.io.PrintStream;
+
+@Ignore
+public class AcceptanceTest extends LoggerTestSuite {
+
+ @Override
+ public Logger createLogger(ListAppendingOutputStream outputStream, Level level) {
+ SimpleLogger.CONFIG_PARAMS.outputChoice = new OutputChoice(new PrintStream(outputStream));
+
+ SimpleLogger logger = new SimpleLogger("TestSuiteLogger");
+ logger.currentLogLevel = SimpleLoggerConfiguration.stringToLevel(level.toString());
+ return logger;
+ }
+
+ @Override
+ public String extractMessage(String message) {
+ return message
+ .split("\n")[0]
+ .split("- ")[1];
+ }
+
+ @Override
+ public String extractExceptionMessage(String message) {
+ String[] logLines = message.split("\n");
+
+ if (logLines.length < 2) {
+ return null;
+ }
+ String exceptionLine = logLines[1];
+ return exceptionLine.split(": ")[1];
+ }
+
+ @Override
+ public String extractExceptionType(String message) {
+ String[] logLines = message.split("\n");
+
+ if (logLines.length < 2) {
+ return null;
+ }
+ String exceptionLine = logLines[1];
+ return exceptionLine.split(": ")[0];
+ }
+
+} \ No newline at end of file
diff --git a/slf4j-simple/src/test/java/org/slf4j/DetectLoggerNameMismatchTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/DetectLoggerNameMismatchTest.java
index c6c6f205..516ce8e4 100755
--- a/slf4j-simple/src/test/java/org/slf4j/DetectLoggerNameMismatchTest.java
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/DetectLoggerNameMismatchTest.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.simple;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
@@ -30,6 +30,9 @@ import static org.junit.Assert.assertTrue;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.LoggerFactoryFriend;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
@@ -48,6 +51,8 @@ public class DetectLoggerNameMismatchTest {
private static final String MISMATCH_STRING = "Detected logger name mismatch";
+ static String NAME_OF_THIS_CLASS = DetectLoggerNameMismatchTest.class.getName();
+
private final ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
private final PrintStream oldErr = System.err;
@@ -90,8 +95,9 @@ public class DetectLoggerNameMismatchTest {
public void testTriggerWholeMessage() {
setTrialEnabled(true);
LoggerFactory.getLogger(String.class);
- assertTrue("Actual value of byteArrayOutputStream: " + String.valueOf(byteArrayOutputStream), String.valueOf(byteArrayOutputStream).contains(
- "Detected logger name mismatch. Given name: \"java.lang.String\"; " + "computed name: \"org.slf4j.DetectLoggerNameMismatchTest\"."));
+ boolean success = String.valueOf(byteArrayOutputStream)
+ .contains("Detected logger name mismatch. Given name: \"java.lang.String\"; " + "computed name: \"" + NAME_OF_THIS_CLASS + "\".");
+ assertTrue("Actual value of byteArrayOutputStream: " + String.valueOf(byteArrayOutputStream), success);
}
/*
@@ -101,7 +107,7 @@ public class DetectLoggerNameMismatchTest {
public void testPassIfMatch() {
setTrialEnabled(true);
Logger logger = LoggerFactory.getLogger(DetectLoggerNameMismatchTest.class);
- assertEquals("org.slf4j.DetectLoggerNameMismatchTest", logger.getName());
+ assertEquals(DetectLoggerNameMismatchTest.class.getName(), logger.getName());
assertMismatchDetected(false);
}
@@ -113,7 +119,7 @@ public class DetectLoggerNameMismatchTest {
public void verifyLoggerDefinedInBaseWithOverridenGetClassMethod() {
setTrialEnabled(true);
Square square = new Square();
- assertEquals("org.slf4j.Square", square.logger.getName());
+ assertEquals(Square.class.getName(), square.logger.getName());
assertMismatchDetected(false);
}
@@ -121,7 +127,7 @@ public class DetectLoggerNameMismatchTest {
// The system property is read into a static variable at initialization time
// so we cannot just reset the system property to test this feature.
// Therefore we set the variable directly.
- LoggerFactory.DETECT_LOGGER_NAME_MISMATCH = enabled;
+ LoggerFactoryFriend.setDetectLoggerNameMismatch(enabled);
}
}
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/DoubleInitializationPitfallTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/DoubleInitializationPitfallTest.java
new file mode 100644
index 00000000..e4e39d5e
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/DoubleInitializationPitfallTest.java
@@ -0,0 +1,37 @@
+package org.slf4j.simple;
+
+import static org.junit.Assert.fail;
+
+import org.junit.Test;
+import org.slf4j.ILoggerFactory;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+import org.slf4j.MarkerFactory;
+
+// See https://jira.qos.ch/browse/SLF4J-463
+public class DoubleInitializationPitfallTest {
+
+ // See https://jira.qos.ch/browse/SLF4J-463
+ @Test
+ public void verifyImpactOfMarkerFactory() {
+ ILoggerFactory firstFactory = LoggerFactory.getILoggerFactory();
+ MarkerFactory.getMarker("DOUBLE_INIT");
+ ILoggerFactory secondFactory = LoggerFactory.getILoggerFactory();
+
+ if (firstFactory != secondFactory) {
+ fail("MarkerFactory.getMarker causes multiple provider initialization");
+ }
+ }
+
+ @Test
+ public void verifyImpactOfMDC() {
+ ILoggerFactory firstFactory = LoggerFactory.getILoggerFactory();
+ MDC.put("DoubleInitializationPitfallTest", "a");
+ ILoggerFactory secondFactory = LoggerFactory.getILoggerFactory();
+
+ if (firstFactory != secondFactory) {
+ fail("MarkerFactory.getMarker causes multiple provider initialization");
+ }
+ }
+
+}
diff --git a/slf4j-simple/src/test/java/org/slf4j/InvocationTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/InvocationTest.java
index 6842d07c..39d3da0e 100644
--- a/slf4j-simple/src/test/java/org/slf4j/InvocationTest.java
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/InvocationTest.java
@@ -22,11 +22,20 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.simple;
+
+import static org.junit.Assert.assertNull;
import java.io.PrintStream;
-import junit.framework.TestCase;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+import org.slf4j.Marker;
+import org.slf4j.MarkerFactory;
/**
* Test whether invoking the SLF4J API causes problems or not.
@@ -34,33 +43,31 @@ import junit.framework.TestCase;
* @author Ceki Gulcu
*
*/
-public class InvocationTest extends TestCase {
+public class InvocationTest {
PrintStream old = System.err;
- public InvocationTest(String arg0) {
- super(arg0);
- }
-
- protected void setUp() throws Exception {
- super.setUp();
+ @Before
+ public void setUp() throws Exception {
System.setErr(new SilentPrintStream(old));
}
- protected void tearDown() throws Exception {
- super.tearDown();
+ @After
+ public void tearDown() throws Exception {
System.setErr(old);
}
+ @Test
public void test1() {
Logger logger = LoggerFactory.getLogger("test1");
logger.debug("Hello world.");
}
+ @Test
public void test2() {
- Integer i1 = new Integer(1);
- Integer i2 = new Integer(2);
- Integer i3 = new Integer(3);
+ Integer i1 = Integer.valueOf(1);
+ Integer i2 = Integer.valueOf(2);
+ Integer i3 = Integer.valueOf(3);
Exception e = new Exception("This is a test exception.");
Logger logger = LoggerFactory.getLogger("test2");
@@ -76,18 +83,21 @@ public class InvocationTest extends TestCase {
logger.warn("Hello world 3", e);
logger.error("Hello world 4.");
- logger.error("Hello world {}", new Integer(3));
+ logger.error("Hello world {}", Integer.valueOf(3));
logger.error("Hello world 4.", e);
}
- // http://bugzilla.slf4j.org/show_bug.cgi?id=78
+ // http://jira.qos.ch/browse/SLF4J-69
+ // formerly http://bugzilla.slf4j.org/show_bug.cgi?id=78
+ @Test
public void testNullParameter_BUG78() {
Logger logger = LoggerFactory.getLogger("testNullParameter_BUG78");
String[] parameters = null;
String msg = "hello {}";
- logger.info(msg, parameters);
+ logger.info(msg, (Object[]) parameters);
}
+ @Test
public void testNull() {
Logger logger = LoggerFactory.getLogger("testNull");
logger.debug(null);
@@ -102,6 +112,7 @@ public class InvocationTest extends TestCase {
logger.error(null, e);
}
+ @Test
public void testMarker() {
Logger logger = LoggerFactory.getLogger("testMarker");
Marker blue = MarkerFactory.getMarker("BLUE");
@@ -121,6 +132,7 @@ public class InvocationTest extends TestCase {
logger.error(blue, "hello {} and {} ", "world", "universe");
}
+ @Test
public void testMDC() {
MDC.put("k", "v");
assertNull(MDC.get("k"));
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/LoggerTestSuite.java b/slf4j-simple/src/test/java/org/slf4j/simple/LoggerTestSuite.java
new file mode 100644
index 00000000..5784c1bd
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/LoggerTestSuite.java
@@ -0,0 +1,274 @@
+package org.slf4j.simple;
+
+
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.event.Level;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.ArrayList;
+import java.util.List;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+
+public abstract class LoggerTestSuite {
+
+ public static class ListAppendingOutputStream extends OutputStream {
+ private final StringBuilder word = new StringBuilder();
+ private int index = 0;
+ private final List<String> list;
+
+ private ListAppendingOutputStream(List<String> list) {this.list = list;}
+
+
+ @Override
+ public void write(int b) throws IOException {
+ word.append((char) b);
+ }
+
+ @Override
+ public void flush() {
+ list.add(word.toString());
+ word.delete(0, word.length());
+ index++;
+ }
+ }
+
+ private ListAppendingOutputStream prepareSink(List<String> source) {
+ return new ListAppendingOutputStream(source);
+
+ }
+
+ @Test
+ public void testTrace() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.TRACE);
+
+ assertTrue("Trace level should be enabled for this test", configuredLogger.isTraceEnabled());
+ configuredLogger.trace("Simple trace message");
+
+ assertEquals("Trace message should've been captured", 1, loggingEvents.size());
+ assertTrue("Message should be logged in trace level", isTraceMessage(loggingEvents.get(0)));
+ assertEquals("Supplied trace message wasn't found in the log",
+ "Simple trace message",
+ extractMessage(loggingEvents.get(0)));
+
+ loggingEvents.clear();
+
+ configuredLogger.debug("Simple debug message");
+ configuredLogger.info("Simple info message");
+ configuredLogger.warn("Simple warn message");
+ configuredLogger.error("Simple error message");
+ assertEquals("The other levels should have been captured", 4, loggingEvents.size());
+
+ }
+
+ @Test
+ public void testDebug() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.DEBUG);
+
+ configuredLogger.trace("Simple trace message");
+ assertEquals("Lower levels should have been ignored", 0, loggingEvents.size());
+
+ assertTrue("Debug level should be enabled for this test", configuredLogger.isDebugEnabled());
+ configuredLogger.debug("Simple debug message");
+
+ assertEquals("Debug message should've been captured", 1, loggingEvents.size());
+ assertTrue("Message should be logged in debug level", isDebugMessage(loggingEvents.get(0)));
+ assertEquals("Supplied debug message wasn't found in the log",
+ "Simple debug message",
+ extractMessage(loggingEvents.get(0)));
+
+ loggingEvents.clear();
+
+ configuredLogger.info("Simple info message");
+ configuredLogger.warn("Simple warn message");
+ configuredLogger.error("Simple error message");
+ assertEquals("The other levels should have been captured", 3, loggingEvents.size());
+ }
+
+
+ @Test
+ public void testInfo() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.INFO);
+
+ configuredLogger.trace("Simple trace message");
+ configuredLogger.debug("Simple debug message");
+ assertEquals("Lower levels should have been ignored", 0, loggingEvents.size());
+
+ assertTrue("Info level should be enabled for this test", configuredLogger.isInfoEnabled());
+ configuredLogger.info("Simple info message");
+
+ assertEquals("Info message should've been captured", 1, loggingEvents.size());
+ assertTrue("Message should be logged in debug level", isInfoMessage(loggingEvents.get(0)));
+ assertEquals("Supplied info message wasn't found in the log",
+ "Simple info message",
+ extractMessage(loggingEvents.get(0)));
+
+ loggingEvents.clear();
+
+ configuredLogger.warn("Simple warn message");
+ configuredLogger.error("Simple error message");
+ assertEquals("The other levels should have been captured", 2, loggingEvents.size());
+ }
+
+ @Test
+ public void testWarn() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.WARN);
+
+ configuredLogger.trace("Simple trace message");
+ configuredLogger.debug("Simple debug message");
+ configuredLogger.info("Simple info message");
+ assertEquals("Lower levels should have been ignored", 0, loggingEvents.size());
+
+ assertTrue("Warn level should be enabled for this test", configuredLogger.isWarnEnabled());
+ configuredLogger.warn("Simple warn message");
+
+ assertEquals("Warn message should've been captured", 1, loggingEvents.size());
+ assertTrue("Message should be logged in warn level", isWarnMessage(loggingEvents.get(0)));
+ assertEquals("Supplied warn message wasn't found in the log",
+ "Simple warn message",
+ extractMessage(loggingEvents.get(0)));
+
+ loggingEvents.clear();
+
+ configuredLogger.error("Simple error message");
+ assertEquals("The other levels should have been captured", 1, loggingEvents.size());
+ }
+
+ @Test
+ public void testError() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.ERROR);
+
+ configuredLogger.trace("Simple trace message");
+ configuredLogger.debug("Simple debug message");
+ configuredLogger.info("Simple info message");
+ configuredLogger.warn("Simple warn message");
+ assertEquals("Lower levels should have been ignored", 0, loggingEvents.size());
+
+ assertTrue("Error level should be enabled for this test", configuredLogger.isErrorEnabled());
+ configuredLogger.error("Simple error message");
+
+ assertEquals("Error message should've been captured", 1, loggingEvents.size());
+ assertTrue("Message should be logged in error level", isErrorMessage(loggingEvents.get(0)));
+ assertEquals("Supplied error message wasn't found in the log",
+ "Simple error message",
+ extractMessage(loggingEvents.get(0)));
+ }
+
+ @Test
+ public void testFormatting() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.INFO);
+
+ configuredLogger.info("Some {} string", "formatted");
+ assertEquals("The formatted message should've been captured", 1, loggingEvents.size());
+ assertEquals("Message should've been formatted", "Some formatted string", extractMessage(loggingEvents.get(0)));
+ }
+
+ @Test
+ public void testException() {
+ ArrayList<String> loggingEvents = new ArrayList<>();
+ Logger configuredLogger = createLogger(prepareSink(loggingEvents), Level.INFO);
+
+ Exception exception = new RuntimeException("My error");
+
+ configuredLogger.info("Logging with an exception", exception);
+ assertEquals("The formatted message should've been captured", 1, loggingEvents.size());
+ assertEquals("Message should've been formatted",
+ "My error",
+ extractExceptionMessage(loggingEvents.get(0)));
+
+ assertEquals("Message should've been formatted",
+ "java.lang.RuntimeException",
+ extractExceptionType(loggingEvents.get(0)));
+ }
+
+
+ /**
+ * Allows tests to check whether the log message contains a trace message.
+ * Override if needed.
+ * @param message String containing the full log message
+ * @return whether it is a trace message or not
+ */
+ protected boolean isTraceMessage(String message) {
+ return message.toLowerCase().contains("trace");
+ }
+
+ /**
+ * Allows tests to check whether the log message contains a debug message.
+ * Override if needed.
+ * @param message String containing the full log message
+ * @return whether it is a debug message or not
+ */
+ protected boolean isDebugMessage(String message) {
+ return message.toLowerCase().contains("debug");
+ }
+
+ /**
+ * Allows tests to check whether the log message contains an info message.
+ * Override if needed.
+ * @param message String containing the full log message
+ * @return whether it is an info message or not
+ */
+ protected boolean isInfoMessage(String message) {
+ return message.toLowerCase().contains("info");
+ }
+
+ /**
+ * Allows tests to check whether the log message contains a warn message.
+ * Override if needed.
+ * @param message String containing the full log message
+ * @return whether it is a warn message or not
+ */
+ protected boolean isWarnMessage(String message) {
+ return message.toLowerCase().contains("warn");
+ }
+
+ /**
+ * Allows tests to check whether the log message contains an error message.
+ * Override if needed.
+ * @param message String containing the full log message
+ * @return whether it is an error message or not
+ */
+ protected boolean isErrorMessage(String message) {
+ return message.toLowerCase().contains("error");
+ }
+
+ /**
+ * Extracts only the part of the log string that should represent the `message` string.
+ * @param message the full log message
+ * @return only the supplied message
+ */
+ public abstract String extractMessage(String message);
+
+ /**
+ * Extracts only the part of the log string that should represent the supplied exception message, if any.
+ * @param message the full log message
+ * @return only the supplied exception message
+ */
+ public abstract String extractExceptionMessage(String message);
+
+ /**
+ * Extracts only the part of the log string that should represent the supplied exception type.
+ * @param message the full log message
+ * @return only the supplied exception type name
+ */
+ public abstract String extractExceptionType(String message);
+
+ /**
+ * Configures the logger for running the tests.
+ * @param outputStream The output stream for logs to be written to
+ * @param level The expected level the tests will run for this logger
+ * @return a configured logger able to run the tests
+ */
+ public abstract Logger createLogger(ListAppendingOutputStream outputStream, Level level);
+
+} \ No newline at end of file
diff --git a/slf4j-simple/src/test/java/org/slf4j/SilentPrintStream.java b/slf4j-simple/src/test/java/org/slf4j/simple/SilentPrintStream.java
index 1d710d98..a440d2d7 100644
--- a/slf4j-simple/src/test/java/org/slf4j/SilentPrintStream.java
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/SilentPrintStream.java
@@ -22,7 +22,7 @@
* WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*/
-package org.slf4j;
+package org.slf4j.simple;
import java.io.PrintStream;
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerMultithreadedInitializationTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerMultithreadedInitializationTest.java
new file mode 100644
index 00000000..3abcb639
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerMultithreadedInitializationTest.java
@@ -0,0 +1,73 @@
+/**
+ * Copyright (c) 2004-2016 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.simple;
+
+import java.io.PrintStream;
+
+import org.junit.After;
+import org.junit.Before;
+import org.slf4j.LoggerFactoryFriend;
+import org.slf4j.helpers.StringPrintStream;
+import org.slf4j.testHarness.MultithreadedInitializationTest;
+
+public class SimpleLoggerMultithreadedInitializationTest extends MultithreadedInitializationTest {
+ // final static int THREAD_COUNT = 4 + Runtime.getRuntime().availableProcessors() * 2;
+ // private final List<Logger> createdLoggers = Collections.synchronizedList(new ArrayList<Logger>());
+ // private final AtomicLong eventCount = new AtomicLong(0);
+ //
+ // private final CyclicBarrier barrier = new CyclicBarrier(THREAD_COUNT + 1);
+ //
+ // final int diff = new Random().nextInt(10000);
+ static int NUM_LINES_IN_SLF4J_REPLAY_WARNING = 3;
+ private final PrintStream oldErr = System.err;
+ final String loggerName = this.getClass().getName();
+ StringPrintStream sps = new StringPrintStream(oldErr, false);
+
+ @Before
+ public void setup() {
+ System.out.println("THREAD_COUNT=" + THREAD_COUNT);
+ System.setErr(sps);
+ System.setProperty(SimpleLogger.LOG_FILE_KEY, "System.err");
+ LoggerFactoryFriend.reset();
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ LoggerFactoryFriend.reset();
+ System.clearProperty(SimpleLogger.LOG_FILE_KEY);
+ System.setErr(oldErr);
+ }
+
+ @Override
+ protected long getRecordedEventCount() {
+ return sps.stringList.size();
+ };
+
+ @Override
+ protected int extraLogEvents() {
+ return NUM_LINES_IN_SLF4J_REPLAY_WARNING;
+ }
+
+}
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerTest.java
new file mode 100644
index 00000000..ced12671
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/SimpleLoggerTest.java
@@ -0,0 +1,152 @@
+/**
+ * Copyright (c) 2004-2022 QOS.ch Sarl (Switzerland)
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.simple;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
+
+import java.io.ByteArrayOutputStream;
+import java.io.PrintStream;
+import java.util.regex.Pattern;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+public class SimpleLoggerTest {
+
+ String A_KEY = SimpleLogger.LOG_KEY_PREFIX + "a";
+ PrintStream original = System.out;
+ ByteArrayOutputStream bout = new ByteArrayOutputStream();
+ PrintStream replacement = new PrintStream(bout);
+
+ @Before
+ public void before() {
+ System.setProperty(A_KEY, "info");
+ }
+
+ @After
+ public void after() {
+ System.clearProperty(A_KEY);
+ System.clearProperty(SimpleLogger.CACHE_OUTPUT_STREAM_STRING_KEY);
+ System.clearProperty(SimpleLogger.SHOW_THREAD_ID_KEY);
+ System.clearProperty(SimpleLogger.SHOW_THREAD_NAME_KEY);
+ System.setErr(original);
+ }
+
+ @Test
+ public void emptyLoggerName() {
+ SimpleLogger simpleLogger = new SimpleLogger("a");
+ assertEquals("info", simpleLogger.recursivelyComputeLevelString());
+ }
+
+ @Test
+ public void offLevel() {
+ System.setProperty(A_KEY, "off");
+ SimpleLogger.init();
+ SimpleLogger simpleLogger = new SimpleLogger("a");
+ assertEquals("off", simpleLogger.recursivelyComputeLevelString());
+ assertFalse(simpleLogger.isErrorEnabled());
+ }
+
+ @Test
+ public void loggerNameWithNoDots_WithLevel() {
+ SimpleLogger.init();
+ SimpleLogger simpleLogger = new SimpleLogger("a");
+
+ assertEquals("info", simpleLogger.recursivelyComputeLevelString());
+ }
+
+ @Test
+ public void loggerNameWithOneDotShouldInheritFromParent() {
+ SimpleLogger simpleLogger = new SimpleLogger("a.b");
+ assertEquals("info", simpleLogger.recursivelyComputeLevelString());
+ }
+
+ @Test
+ public void loggerNameWithNoDots_WithNoSetLevel() {
+ SimpleLogger simpleLogger = new SimpleLogger("x");
+ assertNull(simpleLogger.recursivelyComputeLevelString());
+ }
+
+ @Test
+ public void loggerNameWithOneDot_NoSetLevel() {
+ SimpleLogger simpleLogger = new SimpleLogger("x.y");
+ assertNull(simpleLogger.recursivelyComputeLevelString());
+ }
+
+ @Test
+ public void checkUseOfLastSystemStreamReference() {
+ SimpleLogger.init();
+ SimpleLogger simpleLogger = new SimpleLogger(this.getClass().getName());
+
+ System.setErr(replacement);
+ simpleLogger.info("hello");
+ replacement.flush();
+ assertTrue(bout.toString().contains("INFO " + this.getClass().getName() + " - hello"));
+ }
+
+ @Test
+ public void checkUseOfCachedOutputStream() {
+ System.setErr(replacement);
+ System.setProperty(SimpleLogger.CACHE_OUTPUT_STREAM_STRING_KEY, "true");
+ SimpleLogger.init();
+ SimpleLogger simpleLogger = new SimpleLogger(this.getClass().getName());
+ // change reference to original before logging
+ System.setErr(original);
+
+ simpleLogger.info("hello");
+ replacement.flush();
+ assertTrue(bout.toString().contains("INFO " + this.getClass().getName() + " - hello"));
+ }
+
+ @Test
+ public void testTheadIdWithoutThreadName() {
+ System.setProperty(SimpleLogger.SHOW_THREAD_NAME_KEY, Boolean.FALSE.toString());
+ String patternStr = "^tid=\\d{1,12} INFO org.slf4j.simple.SimpleLoggerTest - hello";
+ commonTestThreadId(patternStr);
+ }
+
+ @Test
+ public void testThreadId() {
+ String patternStr = "^\\[.*\\] tid=\\d{1,12} INFO org.slf4j.simple.SimpleLoggerTest - hello";
+ commonTestThreadId(patternStr);
+ }
+
+ private void commonTestThreadId(String patternStr) {
+ System.setErr(replacement);
+ System.setProperty(SimpleLogger.SHOW_THREAD_ID_KEY, Boolean.TRUE.toString());
+ SimpleLogger.init();
+ SimpleLogger simpleLogger = new SimpleLogger(this.getClass().getName());
+ simpleLogger.info("hello");
+ replacement.flush();
+ String output = bout.toString();
+ System.out.println(patternStr);
+ System.out.println(output);
+ assertTrue(Pattern.compile(patternStr).matcher(output).lookingAt());
+ }
+}
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/MultithereadedExecutionTest.java b/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/MultithereadedExecutionTest.java
new file mode 100755
index 00000000..bb79ac54
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/MultithereadedExecutionTest.java
@@ -0,0 +1,131 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.simple.multiThreadedExecution;
+
+import java.io.PrintStream;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Tests that output in multithreaded environments is not mingled.
+ *
+ * See also https://jira.qos.ch/browse/SLF4J-515
+ */
+public class MultithereadedExecutionTest {
+
+ private static final int THREAD_COUNT = 2;
+ private final Thread[] threads = new Thread[THREAD_COUNT];
+
+ private static final long TEST_DURATION_IN_MILLIS = 100;
+
+ private final PrintStream oldOut = System.out;
+ StateCheckingPrintStream scps = new StateCheckingPrintStream(oldOut);
+
+ volatile boolean signal = false;
+
+ @Before
+ public void setup() {
+ System.setErr(scps);
+ // System.setProperty(SimpleLogger.LOG_FILE_KEY, "System.err");
+ // LoggerFactoryFriend.reset();
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ // LoggerFactoryFriend.reset();
+ // System.clearProperty(SimpleLogger.LOG_FILE_KEY);
+ System.setErr(oldOut);
+ }
+
+ @Test
+ public void test() throws Throwable {
+ WithException withException = new WithException();
+ Other other = new Other();
+ threads[0] = new Thread(withException);
+ threads[1] = new Thread(other);
+ threads[0].start();
+ threads[1].start();
+ Thread.sleep(TEST_DURATION_IN_MILLIS);
+ signal = true;
+ threads[0].join();
+ threads[1].join();
+
+ if (withException.throwable != null) {
+ throw withException.throwable;
+ }
+
+ if (other.throwable != null) {
+ throw other.throwable;
+ }
+
+ }
+
+ class WithException implements Runnable {
+
+ volatile Throwable throwable;
+ Logger logger = LoggerFactory.getLogger(WithException.class);
+
+ @Override
+ public void run() { // TODO Auto-generated method stub
+ int i = 0;
+
+ while (!signal) {
+ try {
+ logger.info("Hello {}", i, new Throwable("i=" + i));
+ i++;
+ } catch (Throwable t) {
+ throwable = t;
+ MultithereadedExecutionTest.this.signal = true;
+ return;
+ }
+ }
+
+ }
+ }
+
+ class Other implements Runnable {
+ volatile Throwable throwable;
+ Logger logger = LoggerFactory.getLogger(Other.class);
+
+ @Override
+ public void run() {
+ int i = 0;
+ while (!signal) {
+ try {
+ logger.info("Other {}", i++);
+ } catch (Throwable t) {
+ throwable = t;
+ MultithereadedExecutionTest.this.signal = true;
+ return;
+ }
+ }
+ }
+ }
+
+}
diff --git a/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/StateCheckingPrintStream.java b/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/StateCheckingPrintStream.java
new file mode 100755
index 00000000..dee4d0d9
--- /dev/null
+++ b/slf4j-simple/src/test/java/org/slf4j/simple/multiThreadedExecution/StateCheckingPrintStream.java
@@ -0,0 +1,140 @@
+/**
+ * Copyright (c) 2004-2021 QOS.ch
+ * All rights reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files (the
+ * "Software"), to deal in the Software without restriction, including
+ * without limitation the rights to use, copy, modify, merge, publish,
+ * distribute, sublicense, and/or sell copies of the Software, and to
+ * permit persons to whom the Software is furnished to do so, subject to
+ * the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+ * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+ * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+ * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ */
+package org.slf4j.simple.multiThreadedExecution;
+
+import java.io.PrintStream;
+import java.util.regex.Pattern;
+
+public class StateCheckingPrintStream extends PrintStream {
+
+ static String PACKAGE_NAME = "org.slf4j.simple.multiThreadedExecution";
+
+
+ enum State {
+ INITIAL, UNKNOWN, HELLO, THROWABLE, AT1, AT2, OTHER;
+ }
+
+ PrintStream other;
+
+ volatile State currentState = State.INITIAL;
+
+ public StateCheckingPrintStream(PrintStream ps) {
+ super(ps);
+ }
+
+ public void print(String s) {
+ }
+
+ public void println(String s) {
+
+ State next = computeState(s);
+ //System.out.println(next + " " + s);
+ switch (currentState) {
+ case INITIAL:
+ currentState = next;
+ break;
+
+ case UNKNOWN:
+ currentState = next;
+ break;
+
+ case OTHER:
+ if (next == State.UNKNOWN) {
+ currentState = State.UNKNOWN;
+ return;
+ }
+
+ if (next != State.OTHER && next != State.HELLO) {
+ throw badState(s, currentState, next);
+ }
+ currentState = next;
+ break;
+
+ case HELLO:
+ if (next != State.THROWABLE) {
+ throw badState(s, currentState, next);
+ }
+ currentState = next;
+ break;
+ case THROWABLE:
+ if (next != State.AT1) {
+ throw badState(s, currentState, next);
+ }
+ currentState = next;
+ break;
+
+ case AT1:
+ if (next != State.AT2) {
+ throw badState(s, currentState, next);
+ }
+ currentState = next;
+ break;
+
+ case AT2:
+ currentState = next;
+ break;
+ default:
+ throw new IllegalStateException("Unreachable code");
+ }
+ }
+
+ private IllegalStateException badState(String s, State currentState2, State next) {
+ return new IllegalStateException("Unexpected state " + next + " for current state " + currentState2 + " for " + s);
+
+ }
+
+ String OTHER_PATTERN_STR = ".*Other \\d{1,5}";
+ String HELLO_PATTERN_STR = ".*Hello \\d{1,5}";
+ String THROWABLE_PATTERN_STR = "java.lang.Throwable: i=\\d{1,5}";
+ String AT1_PATTERN_STR = "\\s*at " + PACKAGE_NAME + ".*";
+ String AT2_PATTERN_STR = "\\s*at " + ".*Thread.java.*";
+
+ Pattern PATTERN_OTHER = Pattern.compile(OTHER_PATTERN_STR);
+ Pattern PATTERN_HELLO = Pattern.compile(HELLO_PATTERN_STR);
+ Pattern PATTERN_THROWABLE = Pattern.compile(THROWABLE_PATTERN_STR);
+ Pattern PATTERN_AT1 = Pattern.compile(AT1_PATTERN_STR);
+ Pattern PATTERN_AT2 = Pattern.compile(AT2_PATTERN_STR);
+
+ private State computeState(String s) {
+
+ if (PATTERN_OTHER.matcher(s).matches()) {
+ return State.OTHER;
+ } else if (PATTERN_HELLO.matcher(s).matches()) {
+ return State.HELLO;
+ } else if (PATTERN_THROWABLE.matcher(s).matches()) {
+ return State.THROWABLE;
+ } else if (PATTERN_AT1.matcher(s).matches()) {
+ return State.AT1;
+ } else if (PATTERN_AT2.matcher(s).matches()) {
+ return State.AT2;
+ } else {
+ return State.UNKNOWN;
+ }
+ }
+
+ public void println(Object o) {
+ println(o.toString());
+ }
+} \ No newline at end of file
diff --git a/slf4j-site/pom.xml b/slf4j-site/pom.xml
deleted file mode 100755
index 2e0c180d..00000000
--- a/slf4j-site/pom.xml
+++ /dev/null
@@ -1,43 +0,0 @@
-<project xmlns="http://maven.apache.org/POM/4.0.0"
- xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
-
- <modelVersion>4.0.0</modelVersion>
-
- <parent>
- <groupId>org.slf4j</groupId>
- <artifactId>slf4j-parent</artifactId>
- <version>1.7.13-SNAPSHOT</version>
- </parent>
-
- <artifactId>slf4j-site</artifactId>
-
- <packaging>jar</packaging>
- <name>SLF4J Site</name>
- <description>SLF4J Site</description>
- <url>http://www.slf4j.org</url>
-
- <build>
- <resources>
- <resource>
- <directory>src/site/pages</directory>
- <!--We're saving filtered html docs in a temporary folder-->
- <!--and telling the site plug in to get the docs there.-->
- <targetPath>../../../target/site</targetPath>
- <filtering>true</filtering>
- </resource>
- </resources>
- <plugins>
- <plugin>
- <groupId>org.apache.maven.plugins</groupId>
- <artifactId>maven-site-plugin</artifactId>
- <version>${maven-site-plugin.version}</version>
- <configuration>
- <outputDirectory>${project.parent.basedir}/target/site
- </outputDirectory>
- </configuration>
- </plugin>
- </plugins>
- </build>
-
-</project> \ No newline at end of file
diff --git a/slf4j-site/src/site/images.src/bindings.flw b/slf4j-site/src/site/images.src/bindings.flw
deleted file mode 100644
index 15ca876c..00000000
--- a/slf4j-site/src/site/images.src/bindings.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/bridging-black.flw b/slf4j-site/src/site/images.src/bridging-black.flw
deleted file mode 100755
index 1552a824..00000000
--- a/slf4j-site/src/site/images.src/bridging-black.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/bridging.flw b/slf4j-site/src/site/images.src/bridging.flw
deleted file mode 100644
index 3efbf2ba..00000000
--- a/slf4j-site/src/site/images.src/bridging.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/concrete-bindings.odg b/slf4j-site/src/site/images.src/concrete-bindings.odg
deleted file mode 100644
index ea1a712d..00000000
--- a/slf4j-site/src/site/images.src/concrete-bindings.odg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/core-bindings.flw b/slf4j-site/src/site/images.src/core-bindings.flw
deleted file mode 100644
index 72333e54..00000000
--- a/slf4j-site/src/site/images.src/core-bindings.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/core-bindings1.flw b/slf4j-site/src/site/images.src/core-bindings1.flw
deleted file mode 100644
index 727f54ae..00000000
--- a/slf4j-site/src/site/images.src/core-bindings1.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/core-bindings2.flw b/slf4j-site/src/site/images.src/core-bindings2.flw
deleted file mode 100644
index a0fcc282..00000000
--- a/slf4j-site/src/site/images.src/core-bindings2.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/core-bindings3.flw b/slf4j-site/src/site/images.src/core-bindings3.flw
deleted file mode 100644
index d87c4035..00000000
--- a/slf4j-site/src/site/images.src/core-bindings3.flw
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/follow_us.odg b/slf4j-site/src/site/images.src/follow_us.odg
deleted file mode 100644
index 3b7c8474..00000000
--- a/slf4j-site/src/site/images.src/follow_us.odg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/images.src/legacy.odg b/slf4j-site/src/site/images.src/legacy.odg
deleted file mode 100644
index 52ab455c..00000000
--- a/slf4j-site/src/site/images.src/legacy.odg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/pages/.htaccess b/slf4j-site/src/site/pages/.htaccess
deleted file mode 100644
index eb903bf0..00000000
--- a/slf4j-site/src/site/pages/.htaccess
+++ /dev/null
@@ -1 +0,0 @@
-Redirect permanent /log4j-over-slf4j.html http://www.slf4j.org/legacy.html#log4j-over-slf4j \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/bug-reporting.html b/slf4j-site/src/site/pages/bug-reporting.html
deleted file mode 100755
index 259d7625..00000000
--- a/slf4j-site/src/site/pages/bug-reporting.html
+++ /dev/null
@@ -1,90 +0,0 @@
-
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Bug reporting</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
- <script type="text/javascript">prefix='';
- </script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
-
- <h1>Before you report a bug</h1>
-
- <p>The SLF4J community consists of those who use SLF4J and its
- implementations, help answer questions on discussions lists,
- contribute documentation and patches, and those who develop and
- maintain the code for SLF4J and its implementations. Almost all
- those who assist on a day to day basis resolving bug reports do
- this for a wide variety of reasons, and almost all of them do this
- on their own time.
- </p>
-
- <p>Many bugs reported end up not being a bug in SLF4J, but are due
- to misconfiguration, problems caused by installed applications,
- the operating system, etc.
- </p>
-
- <p>Before reporting a bug please make every effort to resolve the
- problem yourself. <em>Just reporting a bug will not fix it. A good
- bug report includes a detailed description of the problem and a
- succinct test case which can reproduce the problem.</em>
- </p>
-
- <h3>Review the documentation</h3>
-
- <p>Review the documentation for the version of component you are
- using. The problem you are having may already be addressed in the
- docs.
- </p>
-
- <h3>Search the mailing list archives</h3>
-
- <p>It is very likely you are not the first to run into a problem.
- Others may have already found a solution. Our various <a
- href="mailing-lists.html">mailing lists</a> are likely to have
- discussed this problem before.
- </p>
-
- <h3>Search JIRA</h3>
-
- <p>Please search the bug database to see if the bug you are seeing
- has already been reported. The bug may have already been fixed
- and is available in a later version. If someone else has reported
- the same bug, you could add supporting information to help
- reproduce and resolve the bug.
- </p>
-
- <ul>
- <li><a
- href="http://jira.qos.ch/issues/?jql=project%20%3D%20SLF4J">Search for
- SLF4J bugs</a></li>
- </ul>
-
- <h3>Reporting a bug</h3>
-
- <p>Only after you have exhausted the aforementioned steps, should
- you file a formal report in JIRA, our bug tracking system.
- </p>
-
- <p>Please make sure you provide as much information as
- possible. Its very hard to fix a bug if the person looking into
- the problem can't reproduce it.
- </p>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/changes/changes-1.3.txt b/slf4j-site/src/site/pages/changes/changes-1.3.txt
deleted file mode 100644
index 40797650..00000000
--- a/slf4j-site/src/site/pages/changes/changes-1.3.txt
+++ /dev/null
@@ -1,45 +0,0 @@
-
-Changes in SLF4J 1.3.0 with respect to 1.2 as reported by the clirr
-tool.
-
-slf4j-api
-=========
-
-INFO: 6000: org.slf4j.Logger: Added public field ROOT_LOGGER_NAME
-INFO: 8000: org.slf4j.LoggerFactory: Class org.slf4j.LoggerFactory added
-INFO: 8000: org.slf4j.MarkerFactory: Class org.slf4j.MarkerFactory added
-INFO: 8000: org.slf4j.helpers.BasicMarker: Class org.slf4j.helpers.BasicMarker added
-INFO: 8000: org.slf4j.helpers.BasicMarkerFactory: Class org.slf4j.helpers.BasicMarkerFactory added
-INFO: 8000: org.slf4j.helpers.MarkerIgnoringBase: Class org.slf4j.helpers.MarkerIgnoringBase added
-INFO: 8000: org.slf4j.helpers.MessageFormatter: Class org.slf4j.helpers.MessageFormatter added
-INFO: 8000: org.slf4j.helpers.Util: Class org.slf4j.helpers.Util added
-ERROR: 8001: org.slf4j.impl.BasicMarker: Class org.slf4j.impl.BasicMarker removed
-ERROR: 8001: org.slf4j.impl.BasicMarkerFactory: Class org.slf4j.impl.BasicMarkerFactory removed
-ERROR: 8001: org.slf4j.impl.MarkerIgnoringBase: Class org.slf4j.impl.MarkerIgnoringBase removed
-ERROR: 8001: org.slf4j.impl.MessageFormatter: Class org.slf4j.impl.MessageFormatter removed
-ERROR: 8001: org.slf4j.impl.Util: Class org.slf4j.impl.Util removed
-INFO: 8000: org.slf4j.spi.LocationAwareLogger: Class org.slf4j.spi.LocationAwareLogger added
-
-slf4j-nop
-=========
-
-ERROR: 8001: org.slf4j.LoggerFactory: Class org.slf4j.LoggerFactory removed
-ERROR: 8001: org.slf4j.MarkerFactory: Class org.slf4j.MarkerFactory removed
-
-slf4j-simple
-============
-
-ERROR: 8001: org.slf4j.LoggerFactory: Class org.slf4j.LoggerFactory removed
-ERROR: 8001: org.slf4j.MarkerFactory: Class org.slf4j.MarkerFactory removed
-
-slf4j-log4j12
-=============
-
-ERROR: 8001: org.slf4j.LoggerFactory: Class org.slf4j.LoggerFactory removed
-ERROR: 8001: org.slf4j.MarkerFactory: Class org.slf4j.MarkerFactory removed
-
-slf4j-jdk14
-===========
-
-ERROR: 8001: org.slf4j.LoggerFactory: Class org.slf4j.LoggerFactory removed
-ERROR: 8001: org.slf4j.MarkerFactory: Class org.slf4j.MarkerFactory removed \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/codes.html b/slf4j-site/src/site/pages/codes.html
deleted file mode 100755
index f331be3b..00000000
--- a/slf4j-site/src/site/pages/codes.html
+++ /dev/null
@@ -1,483 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/2000/REC-xhtml1-20000126/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Error Codes</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
-
- <style>
- h3.doAnchor {
- border-top: 2px solid #888;
- padding-top: 1ex;
- }
- </style>
-</head>
-<body onload="prettyPrint(); decorate();">
- <script type="text/javascript" src="js/prettify.js"></script>
- <script type="text/javascript">prefix='';</script>
- <script type="text/javascript" src="templates/header.js"></script>
- <script type="text/javascript" src="js/jquery-min.js"></script>
- <script type="text/javascript" src="js/decorator.js"></script>
-
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
-
-
- <div id="content">
-
- <center>
- <h2>SLF4J warning or error messages and their meanings</h2>
-
- </center>
-
-
- <h3 class="doAnchor" name="release">The method
- <code>o.a.commons.logging.impl.SLF4FLogFactory#release</code> was
- invoked.
- </h3>
-
- <p>Given the structure of the commons-logging API, in particular
- as implemented by SLF4J, the
- <code>o.a.commons.logging.impl.SLF4FLogFactory#release()</code>
- method should never be called. However, depending on the
- deployment of <em>commons-logging.jar</em> files in your servlet
- container, <code>release()</code> method may be unexpectedly
- invoked by a copy of
- <code>org.apache.commons.logging.LogFactory</code> class shipping
- with <em>commons-logging.jar</em>.
- </p>
-
- <p>This is a relatively common occurrence with recent versions of
- Tomcat, especially if you place <em>jcl-over-slf4j.jar</em> in
- <em>WEB-INF/lib</em> directory of your web-application instead of
- <em>$TOMCAT_HOME/common/lib</em>, where $TOMCAT_HOME stands for
- the directory where Tomcat is installed. In order to fully benefit
- from the stability offered by <em>jcl-over-slf4j.jar</em>, we
- recommend that you place <em>jcl-over-slf4j.jar</em> in
- <em>$TOMCAT_HOME/common/lib</em> without placing a copy in your
- web-applications.
- </p>
-
- <p>Please also see <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=22">bug
- #22</a>.</p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="unsupported_operation_in_jcl_over_slf4j">Operation
- [suchAndSuch] is not supported in jcl-over-slf4j.
- </h3>
-
- <p>An <code>UnsupportedOperationException</code> is thrown whenever
- one of the protected methods introduced in JCL 1.1 are
- invoked. These methods are invoked by <code>LogFactory</code>
- implementations shipping with
- <em>commons-logging.jar</em>. However, the <code>LogFactory</code>
- implemented by <em>jcl-over-slf4j.jar</em>, namely
- SLF4FLogFactory, does not call any of these methods.
- </p>
-
- <p>If you observe this problem, then it is highly probable that you
- have a copy of <em>commons-logging.jar</em> in your class path
- overriding the classes shipping with
- <em>jcl-over-slf4j.jar</em>. Note that this issue is very similar
- in nature to the warning issued when the
- "o.a.commons.logging.impl.SLF4FLogFactory.release()" method is
- invoked, discussed in the previous item.
- </p>
-
- <!-- ====================================================== -->
- <h3 class="doAnchor" name="loggerNameMismatch">Detected logger
- name mismatch</h3>
-
- <p>Logger name mismatch warnings are printed only if the
- <code>slf4j.detectLoggerNameMismatch</code> system property is set
- to true. By default, this property is not set and no warnings will
- be printed even in case of a logger name mismatch.
- </p>
-
- <p><span class="label">since 1.7.9</span> The warning will
- be printed in case the name of the logger specified via a class
- passed as an argument to the
- <code>LoggerFactory.getLogger(Class)</code> method differs from
- the name of the caller as computed internally by SLF4J.
- </p>
-
- <p>For example, the following code snippet</p>
-
-<pre class="prettyprint source">package com.acme;
-import com.foo.Kangaroo;
-
-class <b>Fruit</b> {
- Logger logger = LoggerFactory.getLogger(<b>Kangaroo.class</b>);
-}</pre>
-
- <p>will result in the warning</p>
-
- <pre class="prettyprint source">SLF4J: Detected logger name mismatch. Given name: "com.foo.Kangaroo"; computed name: "com.acme.Fruit".</pre>
-
- <p>but only if <code>slf4j.detectLoggerNameMismatch</code> system
- property is set to true.</p>
-
- <p>No warning will be issued for the special case where the class
- in which the logger is defined is a super-type of the class
- parameter passed as argument. For example,</p>
-
- <pre class="prettyprint source">class A {
- Logger logger = LoggerFactory.getLogger(getClass());
-}
-class B extends A {
- // no mismatch warning will be issued when B is instantiated
- // given that class A is a super-type of class B
-}</pre>
-
- <p>If you come across a mismatch warning which cannot be
- explained, then you might have spotted a white elephant, that is a
- very rare occurrence where SLF4J cannot correctly compute the name
- of the class where a logger is defined. We are very interested to
- learn about such cases. If and when you spot an inexplicable
- mismatch, please do file a <a href="bug-reporting.html">bug
- report</a> with us.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="StaticLoggerBinder">Failed to load class
- <code>org.slf4j.impl.StaticLoggerBinder</code></h3>
-
- <p>This error is reported when the
- <code>org.slf4j.impl.StaticLoggerBinder</code> class could not be
- loaded into memory. This happens when no appropriate SLF4J
- binding could be found on the class path. Placing one (and only
- one) of <em>slf4j-nop.jar</em>, <em>slf4j-simple.jar</em>,
- <em>slf4j-log4j12.jar</em>, <em>slf4j-jdk14.jar</em> or
- <em>logback-classic.jar</em> on the class path should solve the
- problem.
- </p>
-
- <p><span class="label">since 1.6.0</span> As of SLF4J version 1.6, in the absence of a binding, SLF4J
- will default to a no-operation (NOP) logger implementation.
- </p>
-
- <p>You can download SLF4J bindings from the project <a
- href="http://www.slf4j.org/download.html">download page</a>. </p>
-
- <!-- ====================================================== -->
- <!-- duplicates /faq.html#IllegalAccessError -->
-
-<!--
- <h3>
- <a name="illegalAccess" href="#illegalAccess">java.lang.IllegalAccessError: tried to access field
- org.slf4j.impl.StaticLoggerBinder.SINGLETON from class
- org.slf4j.LoggerFactory</a>
- </h3>
-
- <p>When this errors occurs, the exception looks as follows:</p>
- <p class="source">java.lang.IllegalAccessError: tried to access field org.slf4j.impl.StaticLoggerBinder.SINGLETON \
- from class org.slf4j.LoggerFactory
- at org.slf4j.LoggerFactory.&lt;clinit&gt;(LoggerFactory.java:60)
- ... </p>
-
- <p>The error is caused by the static initializer of the
- <code>LoggerFactory</code> class attempting to directly access the
- SINGLETON field of
- <code>org.slf4j.impl.StaticLoggerBinder</code>. While this was
- allowed in SLF4J 1.5.5 and earlier, in 1.5.6 and later the
- SINGLETON field has been marked as private access.
- </p>
-
- <p>From a broader perspective, this issue is a manifestation of
- problems encountered when mixing different versions of SLF4J
- artifacts. Please also refer to the relevant <a
- href="faq.html#compatibility">FAQ entry</a>.
- </p>
--->
-
- <!-- ====================================================== -->
- <h3 class="doAnchor" name="multiple_bindings">Multiple bindings
- were found on the class path
- </h3>
-
-
- <p>SLF4J API is designed to bind with one and only one underlying
- logging framework at a time. If more than one binding is present
- on the class path, SLF4J will emit a warning, listing the location
- of those bindings.</p>
-
- <p>When multiple bindings are available on the class path, select
- one and only one binding you wish to use, and remove the other
- bindings. For example, if you have both
- <em>slf4j-simple-${version}.jar</em> and
- <em>slf4j-nop-${version}.jar</em> on the class path and you wish
- to use the nop (no-operation) binding, then remove
- <em>slf4j-simple-${version}.jar</em> from the class path.
- </p>
-
- <p>The list of locations that SLF4J provides in this warning
- usually provides sufficient information to identify the dependency
- transitively pulling in an unwanted SLF4J binding into your
- project. In your project's pom.xml file, exclude this SLF4J
- binding when declaring the unscrupulous dependency. For example,
- <em>cassandra-all</em> version 0.8.1 declares both <em>log4j</em>
- and <em>slf4j-log4j12</em> as compile-time dependencies. Thus,
- when you include <em>cassandra-all</em> as a dependency in your
- project, the <em>cassandra-all</em> declaration will cause both
- <em>slf4j-log4j12.jar</em> and <em>log4j.jar</em> to be pulled in
- as dependencies. In case you do not wish to use log4j as the the
- SLF4J backend, you can instruct Maven to exclude these two
- artifacts as shown next:</p>
-
- <pre class="prettyprint">&lt;dependencies>
- &lt;dependency>
- &lt;groupId> org.apache.cassandra&lt;/groupId>
- &lt;artifactId>cassandra-all&lt;/artifactId>
- &lt;version>0.8.1&lt;/version>
-
- &lt;exclusions>
- &lt;exclusion>
- &lt;groupId>org.slf4j&lt;/groupId>
- &lt;artifactId>slf4j-log4j12&lt;/artifactId>
- &lt;/exclusion>
- &lt;exclusion>
- &lt;groupId>log4j&lt;/groupId>
- &lt;artifactId>log4j&lt;/artifactId>
- &lt;/exclusion>
- &lt;/exclusions>
-
- &lt;/dependency>
-&lt;/dependencies></pre>
-
- <p><span class="label notice">Note</span> The warning emitted by
- SLF4J is just that, a warning. Even when multiple bindings are
- present, SLF4J will pick one logging framework/implementation and
- bind with it. The way SLF4J picks a binding is determined by the
- JVM and for all practical purposes should be considered random. As
- of version 1.6.6, SLF4J will name the framework/implementation
- class it is actually bound to.</p>
-
- <p>Embedded components such as libraries or frameworks should not
- declare a dependency on any SLF4J binding but only depend on
- slf4j-api. When a library declares a compile-time dependency on a
- SLF4J binding, it imposes that binding on the end-user, thus
- negating SLF4J's purpose. When you come across an embedded
- component declaring a compile-time dependency on any SLF4J binding,
- please take the time to contact the authors of said
- component/library and kindly ask them to mend their ways.</p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="version_mismatch">slf4j-api version
- does not match that of the binding</h3>
-
- <p>An SLF4J binding designates an artifact such as
- <em>slf4j-jdk14.jar</em> or <em>slf4j-log4j12.jar</em> used to
- <em>bind</em> slf4j to an underlying logging framework, say,
- java.util.logging and respectively log4j.
- </p>
-
- <p>Mixing mixing different versions of <em>slf4j-api.jar</em> and
- SLF4J binding can cause problems. For example, if you are using
- slf4j-api-${project.version}.jar, then you should also use
- slf4j-simple-${project.version}.jar, using slf4j-simple-1.5.5.jar
- will not work.</p>
-
- <p><span class="label notice">Note</span> From the client's
- perspective all versions of slf4j-api are compatible. Client code
- compiled with <em>slf4j-api-N.jar</em> will run perfectly fine
- with <em>slf4j-api-M.jar</em> for any N and M. You only need to
- ensure that the version of your binding matches that of the
- slf4j-api.jar. You do not have to worry about the version of
- slf4j-api.jar used by a given dependency in your project. You
- can always use any version of <em>slf4j-api.jar</em>, and as long
- as the version of <em>slf4j-api.jar</em> and its binding match,
- you should be fine.
- </p>
-
- <p>At initialization time, if SLF4J suspects that there may be a
- api vs. binding version mismatch problem, it will emit a warning
- about the suspected mismatch.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="null_LF">Logging factory implementation
- cannot be null</h3>
-
- <p>This error is reported when the <code>LoggerFactory</code>
- class could not find an appropriate binding. Placing one (and only
- one) of <em>slf4j-nop.jar</em>, <em>slf4j-simple.jar</em>,
- <em>slf4j-log4j12.jar</em>, <em>slf4j-jdk14.jar</em> or
- <em>logback-classic.jar</em> on the class path should prove to be
- an effective remedy.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="log4jDelegationLoop">Detected both
- log4j-over-slf4j.jar AND slf4j-log4j12.jar on the class path,
- preempting <code>StackOverflowError</code>.
- </h3>
-
- <p>The purpose of slf4j-log4j12 module is to delegate or redirect
- calls made to an SLF4J logger to log4j. The purpose of the
- log4j-over-slf4j module is to redirect calls made to a log4j
- logger to SLF4J. If both <em>slf4j-log4j12.jar</em> and
- <em>log4j-over-slf4j.jar</em> are present on the class path, a
- <code>StackOverflowError</code> will inevitably occur immediately
- after the first invocation of an SLF4J or a log4j logger.
- </p>
-
- <p>Here is how the exception might look like:</p>
-
- <pre class="prettyprint source">Exception in thread "main" java.lang.StackOverflowError
- at java.util.Hashtable.containsKey(Hashtable.java:306)
- at org.apache.log4j.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:36)
- at org.apache.log4j.LogManager.getLogger(LogManager.java:39)
- at org.slf4j.impl.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:73)
- at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:249)
- at org.apache.log4j.Category.&lt;init>(Category.java:53)
- at org.apache.log4j.Logger..&lt;init>(Logger.java:35)
- at org.apache.log4j.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:39)
- at org.apache.log4j.LogManager.getLogger(LogManager.java:39)
- at org.slf4j.impl.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:73)
- at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:249)
- at org.apache.log4j.Category..&lt;init>(Category.java:53)
- at org.apache.log4j.Logger..&lt;init>(Logger.java:35)
- at org.apache.log4j.Log4jLoggerFactory.getLogger(Log4jLoggerFactory.java:39)
- at org.apache.log4j.LogManager.getLogger(LogManager.java:39)
- subsequent lines omitted...</pre>
-
- <p><span class="label">Since 1.5.11</span> SLF4J software preempts
- the inevitable stack overflow error by throwing an exception with
- details about the actual cause of the problem. This is deemed to
- be better than leaving the user wondering about the reasons of the
- <code>StackOverflowError</code>.
- </p>
-
- <p>For more background on this topic see <a
- href="legacy.html">Bridging legacy APIs</a>.
- </p>
-
- <!-- ====================================================== -->
-
-
- <h3 class="doAnchor" name="jclDelegationLoop">Detected both
- jcl-over-slf4j.jar AND slf4j-jcl.jar on the class path, preempting
- <code>StackOverflowError</code>.
- </h3>
-
- <p>The purpose of slf4j-jcl module is to delegate or redirect
- calls made to an SLF4J logger to jakarta commons logging
- (JCL). The purpose of the jcl-over-slf4j module is to redirect
- calls made to a JCL logger to SLF4J. If both
- <em>slf4j-jcl.jar</em> and <em>jcl-over-slf4j.jar</em> are present
- on the class path, then a <code>StackOverflowError</code> will
- inevitably occur immediately after the first invocation of an
- SLF4J or a JCL logger.
- </p>
-
- <p>Here is how the exception might look like:</p>
-
- <pre class="prettyprint source">Exception in thread "main" java.lang.StackOverflowError
- at java.lang.String.hashCode(String.java:1482)
- at java.util.HashMap.get(HashMap.java:300)
- at org.slf4j.impl.JCLLoggerFactory.getLogger(JCLLoggerFactory.java:67)
- at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:249)
- at org.apache.commons.logging.impl.SLF4JLogFactory.getInstance(SLF4JLogFactory.java:155)
- at org.apache.commons.logging.LogFactory.getLog(LogFactory.java:289)
- at org.slf4j.impl.JCLLoggerFactory.getLogger(JCLLoggerFactory.java:69)
- at org.slf4j.LoggerFactory.getLogger(LoggerFactory.java:249)
- at org.apache.commons.logging.impl.SLF4JLogFactory.getInstance(SLF4JLogFactory.java:155)
- subsequent lines omitted...</pre>
-
-
- <p><span class="label">Since 1.5.11</span> SLF4J software preempts
- the inevitable stack overflow error by throwing an exception with
- details about the actual cause of the problem. This is deemed to
- be better than leaving the user wondering about the reasons of the
- <code>StackOverflowError</code>.
- </p>
-
- <p>For more background on this topic see <a
- href="legacy.html">Bridging legacy APIs</a>.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="no_static_mdc_binder">Failed to load
- class "org.slf4j.impl.StaticMDCBinder"</h3>
-
- <p>This error indicates that appropriate SLF4J binding could not
- be found on the class path. Placing one (and only one) of
- <em>slf4j-nop.jar</em>, <em>slf4j-simple.jar</em>,
- <em>slf4j-log4j12.jar</em>, <em>slf4j-jdk14.jar</em> or
- <em>logback-classic.jar</em> on the class path should solve the
- problem.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="null_MDCA">MDCAdapter cannot be null
- </h3>
-
- <p>This error is reported when <code>org.slf4j.MDC</code> class
- has not been initialized correctly. Same cause and remedy as the
- previously listed item.
- </p>
-
- <!-- ====================================================== -->
-
- <h3 class="doAnchor" name="log4j_version">SLF4J versions 1.4.0 and
- later requires log4j 1.2.12 or later</h3>
-
- <p>The trace level was added to log4j in version 1.2.12 released
- on August 29, 2005. The trace level was added to the SLF4J API in
- version 1.4.0 on May 16th, 2007. Thus, starting with SLF4J 1.4.0,
- the log4j binding for SLF4J requires log4j version 1.2.12 or
- above.
- </p>
-
- <p>However, as reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=68">bug 68</a>, in
- some environments it may be difficult to upgrade the log4j
- version. To accommodate such circumstances, SLF4J's
- <code>Log4jLoggerAdapter</code> will map the TRACE level as
- DEBUG.</p>
-
-
- <h3 class="doAnchor" name="substituteLogger" >Substitute loggers
- were created during the default configuration phase of the
- underlying logging system</h3>
-
- <p>Highly configurable logging systems such as logback and log4j
- may create components which invoke loggers during their own
- initialization. See issue <a
- href="http://jira.qos.ch/browse/LOGBACK-127">LOGBACK-127</a> for a
- typical occurrence. However, since the binding process with SLF4J
- has not yet completed (because the underlying logging system was
- not yet completely loaded into memory), it is not possible to
- honor such logger creation requests.</p>
-
- <p>To avoid this chicken-and-egg problem, SLF4J creates substitute
- loggers during this phase (initialization). Calls made to the
- substitute loggers during this phase are simply dropped. After the
- initialization completes, the substitute logger will delegate
- logging calls to the appropriate logger implementation and
- otherwise will function as any other logger returned by
- <code>LoggerFactory</code>.
- </p>
-
- <p>If any substitute logger had to be created, SLF4J will emit a a
- listing of such loggers. This list is intended to let you know
- that any logging calls made to these loggers during initialization
- have been dropped.
- </p>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
- </div>
-
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/compatibility.html b/slf4j-site/src/site/pages/compatibility.html
deleted file mode 100755
index cf4afb9c..00000000
--- a/slf4j-site/src/site/pages/compatibility.html
+++ /dev/null
@@ -1,269 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/2000/REC-xhtml1-20000126/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
-
-<meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
-<title>Compatibility report</title>
-<link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
-</head>
-<body>
- <script>
-prefix='';
-</script>
-
-<script src="templates/header.js"></script>
-<div id="left">
- <script src="templates/left.js"></script>
-</div>
-<div id="right">
- <script src="templates/right.js"></script>
-</div>
-<div id="content">
-
-
- <h1>Compatibility report</h1>
-
- <p>Given the very large user base of SLF4J, we take backward
- compatibility very seriously. As such, changes that may cause
- incompatibility problems are listed in this page. Moreover, since
- slf4j-api.jar is the main entry point into SLF4J, that is the module
- that will be covered in most detail.
- </p>
-
- <p>Please note that in many cases incompatibility problems are
- caused by mixing different versions of slf4j artifacts. For example,
- if you are using slf4j-api-1.5.4.jar you should also use
- slf4j-simple-1.5.4.jar, using slf4j-simple-1.4.2.jar will not
- work. The same goes for all other SLF4J artifacts.
- </p>
-
- <p>The list is computed using <a
- href="http://clirr.sourceforge.net/">clirr</a>. If you have reasons
- to suspect incompatible changes not mentioned here, please kindly
- contact the slf4j developers list.</p>
-
- <h2><a href="#1_5_7" name="1_5_6">Version 1.5.7 compared to 1.5.6</a></h2>
-
- <p>No breaking changes to report.</p>
-
- <h2><a href="#1_5_6" name="1_5_5">Version 1.5.6 compared to 1.5.5</a></h2>
-
-
- <table class="bodyTable">
- <tr>
- <th>Severity</th>
- <th>Description</th>
- <th>Class</th>
- <th>Method / Field</th>
- </tr>
- <tr>
- <td>Error</td>
- <td>The&nbsp;number&nbsp;of&nbsp;parameters&nbsp;of SubstituteLoggerFactory
- constructor has changed</td>
- <td>org.slf4j.helpers.SubstituteLoggerFactory</td>
- <td>public SubstituteLoggerFactory(java.util.List)</td>
- </tr>
- </table>
-
- <p>&nbsp;</p>
-
- <p>The <code>SubstituteLoggerFactory</code> class is used internally
- by the LoggerFactory class. Changes to the constructor of
- SubstituteLoggerFactory should have strictly no effect on users.
- </p>
-
- <h2><a href="#1_5_5" name="1_5_4">Version 1.5.5 compared to 1.5.4</a></h2>
-
- <p>No breaking changes to report.</p>
-
- <h2><a href="#1_5_4" name="1_5_4">Version 1.5.4 compared to 1.5.3</a></h2>
-
- <h3>slf4j-api module, list of breaking changes:</h3>
-
-
- <table class="bodyTable">
- <tr>
- <th>Severity</th>
- <th>Description</th>
- <th>Class</th>
- <th>Method / Field</th>
- </tr>
- <tr>
- <td>Error</td>
- <td>Method 'hasReferences()' has been added to an interface</td>
- <td>org.slf4j.Marker</td>
- <td>public boolean hasReferences()</td>
- </tr>
- <tr class="alt">
- <td>Info</td>
- <td>Method 'hasChildren()' was deprecated</td>
- <td>org.slf4j.Marker</td>
- <td>public boolean hasChildren()</td>
- </tr>
-
- </table>
-
- <p>&nbsp;</p>
-
- <p>The <code>hasChildren()</code> and other documentation in the
- Marker interface was misleading users to think in terms of parent
- child relationship for markers. However, as <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=100">bug 100</a>
- illustrates, associating markers as parents and children is not very
- helpful. It is much better to think of markers in terms of abstract
- graphs. As such, we now say that a marker contains (zero or more)
- <code>references</code> to other markers.
- </p>
-
- <p>This breaking change is justified because it corrects a
- conceptual error in the design. Previously, it was all too easy for
- developers to get confused and incorrectly link markers
- together.</p>
-
- <h2><a href="#1_5_3" name="1_5_3">Version 1.5.3 compared to 1.5.2</a></h2>
-
- <h3>slf4j-api module, list of breaking changes:</h3>
-
-
- <table class="bodyTable">
- <tr>
- <th>Severity</th>
- <th>Description</th>
- <th>Class</th>
- <th>Method / Field</th>
- </tr>
- <tr >
- <td>Error</td>
- <td>Added final modifier to class</td>
- <td>org.slf4j.helpers.MessageFormatter</td>
- <td></td>
- </tr>
- </table>
-
- <p>Declaring <code>MessageFormatter</code> class as final should not
- affect users, unless they extend this class. However, since this
- class is intended to be used internally, very few users should be
- affected.
- </p>
-
- <h2><a href="#1_5_2" name="1_5_2">Version 1.5.2 compared to 1.5.1</a></h2>
-
- <p>No breaking changes to report.</p>
-
- <h2><a href="#1_5_1" name="1_5_1">Version 1.5.1 compared to 1.5.0</a></h2>
-
-
- <h3>slf4j-api module, list of breaking changes:</h3>
-
-
- <table class="bodyTable">
- <tr>
- <th>Severity</th>
- <th>Description</th>
- <th>Class</th>
- <th>Method / Field</th>
- </tr>
- <tr >
- <td>Error</td>
- <td>Method 'getCopyOfContextMap()' has been added to an
- interface
- </td>
- <td>org.slf4j.spi.MDCAdapter</td>
- <td>public java.util.Map getCopyOfContextMap()</td>
- </tr>
- <tr class="alt">
- <td>Error</td>
- <td>Method 'setContextMap(Map)' has been added to an
- interface
- </td>
- <td>org.slf4j.spi.MDCAdapter</td>
- <td>public void setContextMap(java.util.Map)</td>
- </tr>
-
- <tr>
- <td>Error</td>
- <td>Method 'getDetachedMarker(String)' has been added to an
- interface
- </td>
- <td>org.slf4j.IMarkerFactory</td>
- <td>public org.slf4j.Marker getDetachedMarker(java.lang.String)</td>
- </tr>
-
- <tr class="alt">
- <td>Info</td>
- <td>Method 'equals(Object)' has been added to an
- interface
- </td>
- <td>org.slf4j.Marker</td>
- <td>public boolean equals(java.lang.Object)</td>
- </tr>
-
- <tr>
- <td>info</td>
- <td>Method 'hashCode()' has been added to an
- interface
- </td>
- <td>org.slf4j.Marker</td>
- <td>public int hashCode()</td>
- </tr>
-
- </table>
-
- <p>The addition of the <code>getCopyOfContextMap()</code> method in
- the <code>MDCAdapter</code> class should only impact users who have
- their own implementation of the said interface. Except for bindings
- that ship with SLF4J and for logback-classic, which will be
- naturally upgraded, there are no known other implementations of
- <code>MDCAdapter</code>. In a rare but still possible scenario, if
- the user mixes different versions for slf4j-api.jar, say version
- 1.5.1. and an SLF4J binding, say slf4j-log4j12.jar version 1.5.0,
- then a <code>java.lang.AbstractMethodError</code> will be thrown,
- but only if the client code calls the newly added method. <span
- style="color:green"> In short, although generally speaking the
- addition of a method to an interface is a breaking change, we are
- confident that no users will be impacted in this particular
- case.</span>
- </p>
-
- <p>Similar reasoning applies to the <code>setContextMap(Map)</code>
- method.</p>
-
- <p>The addition of <code>getDetachedMarker(String)</code> method in
- the <code>org.slf4j.IMarkerFactory</code> should not impact users as
- the only (known) implementation of this interface ships with SLF4J
- itself.
- </p>
-
- <p>The <code>equals()</code> and <code>hashCode()</code> methods
- were added to the <code>org.slf4j.Marker</code> interface for
- documentation purposes. Given that all objects implicitly implement
- these methods, their addition should theoretically not break
- existing code. </p>
-
-
- <h3>Other modules</h3>
-
- <p>No breaking changes to report.</p>
-
-
- <!-- ========================================= -->
- <h2><a href="#1_5_0" name="1_5_0">Version 1.5.0 compared to
- 1.4.3</a></h2>
-
- <p>No breaking changes to report.</p>
-
- <!-- ========================================= -->
- <h2><a href="#1_4_3" name="1_4_3">Version 1.4.3 compared to
- 1.4.2</a></h2>
- <p>No breaking changes to report.</p>
-
- <!-- ========================================= -->
- <h2><a href="#1_4_2" name="1_4_2">Version 1.4.2 compared to 1.4.1</a></h2>
- <p>No breaking changes to report.</p>
-
- <!-- ========================================= -->
- <h2><a href="#1_4_1" name="1_4_1">Version 1.4.1 compared to
- 1.4.0</a></h2>
- <p>No breaking changes to report.</p>
-
-</div> </body> </html> \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/css/popup.css b/slf4j-site/src/site/pages/css/popup.css
deleted file mode 100644
index 2b20468e..00000000
--- a/slf4j-site/src/site/pages/css/popup.css
+++ /dev/null
@@ -1,67 +0,0 @@
-
-/* =========== popup ================== */
-#backgroundPopup {
- display:none;
- position:fixed;
- _position:absolute; /* hack for internet explorer 6*/
- height:100%;
- width:100%;
- top:0;
- left:0;
- background:#000000;
- border:1px solid #cecece;
- z-index:1;
-}
-
-#popupContents {
- display:none;
- position:fixed;
- _position:absolute; /* hack for internet explorer 6*/
- height: 150px;
- width: 408px;
- background:#FFFFFF;
- border: 2px solid #cecece;
- z-index:2;
- padding-left: 1ex;
- font-size:13px;
-}
-
-#popupContents p {
- margin: 0px;
-}
-#popupContents h3 {
- margin: 0px;
-}
-
-#popupContactClose {
- font-size:14px;
- line-height:14px;
- right:6px;
- top:4px;
- position:absolute;
- color:#6fa5fd;
- font-weight:700;
- display:block;
-}
-
-a.popupLink {
- background: #FFF;
- color: #0079C5;
- font-family: "Comic Sans MS", sans-serif;
- white-space: nowrap;
- font-size: 14px;
- font-weight: bold;
-
- border-top: 2px solid #DDD;
- border-left: 2px solid #DDD;
- border-right: 2px solid #888;
- border-bottom: 2px solid #888;
- padding: 0px 1em 0px 1em;
- margin: 0px 0px 3px 0px;
-}
-
-a.popupLink:hover {
- background: #E0E0EF;
- cursor: pointer;
-}
-
diff --git a/slf4j-site/src/site/pages/css/prettify.css b/slf4j-site/src/site/pages/css/prettify.css
deleted file mode 100644
index 290a86a4..00000000
--- a/slf4j-site/src/site/pages/css/prettify.css
+++ /dev/null
@@ -1,29 +0,0 @@
-.str{color:#080}
-.kwd{color:#008}
-.com{color:#800}
-.typ{color:#606}
-.lit{color:#066}
-.pun{color:#660}
-.pln{color:#000}
-.tag{color:#008}
-.atn{color:#606}
-.atv{color:#080}
-.dec{color:#606}
-
-pre.prettyprint{
- padding:2px;
- border-top: 1px solid #888; border-bottom: 1px solid #888;
-}
-@media print{.str{color:#060}
-
-.kwd{
- color:#006;font-weight:bold}
- .com{color:#600;font-style:italic
-}
-.typ{color:#404;font-weight:bold}
-.lit{color:#044}
-.pun{color:#440}
-.pln{color:#000}
-.tag{color:#006;font-weight:bold}
-.atn{color:#404}
-.atv{color:#060}} \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/css/site.css b/slf4j-site/src/site/pages/css/site.css
deleted file mode 100755
index 5fd72a66..00000000
--- a/slf4j-site/src/site/pages/css/site.css
+++ /dev/null
@@ -1,449 +0,0 @@
-html {
- padding:0px;
- margin:0px;
-}
-
-body {
- background-color: #fff;
- font-family: Verdana, Arial, SunSans-Regular, Sans-Serif;
- color: #000;
- padding:0px;
- margin:0px;
- font-size: small;
-}
-
-#job img { border:1px solid #DDDDDD; }
-#job:hover img { border:1px solid #8888EE; }
-
-p, h2, pre {
- margin: 0px;
- padding-top: 5px;
- padding-bottom: 5px;
- /*padding-left: 1ex;*/
- /*padding: 5px 20px 5px 20px; */
-}
-
-p.rm {
- padding-top: 0px;
- padding-bottom: 0px;
-}
-
-a {
- color: #4183c4;
- /*font-size: smaller;*/
- background-color:transparent;
- text-decoration: none;
-}
-
-#content a:hover {
- text-decoration: underline;
-}
-
-.source {
- border-top: 1px solid #DDDDDD;
- border-bottom: 1px solid #DDDDDD;
- background:#f5f5f5;
- font-family: Courier, "MS Courier New", Prestige, Everson Monocourrier, monospace;
- padding-bottom: 0.5ex;
- padding-top: 0.5ex;
- padding-left: 1ex;
-
- margin-left: 0ex;
- margin-top: 0.5ex;
- margin-bottom: 0.5ex;
- white-space: pre;
-
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
-
-pre {
- background-color:transparent;
- font-family: Monaco, Andale Mono, Courier New, monospace;
-}
-
-.alignright {
- margin-top: 0;
- text-align: right;
- font-size: 10px;
-}
-
-h1, h2, h3, h4 {
- color: #333;
-}
-
-h2 {
- padding-top:10px;
- background-color: transparent;
- font-weight: 900;
- font-size: x-large;
-}
-
-h3 {
- padding-top: 5px;
- background-color: transparent;
- font-weight: normal;
- font-size: large;
-}
-
-h4 {
- padding-top:5px;
- background-color: transparent;
- font-weight: normal;
- font-size: large;
-}
-
-table.footer {
- width: 100%;
-}
-
-.footer {
- text-align: right;
- color: #564b47;
- background-color: #fff;
- padding:0px;
- border-top: 1px solid #CCCCCC;
- margin-top: 3ex;
- font-size: smaller;
-}
-
-
-strong {
- /*font-size: 13px;*/
- font-weight: bold;
-}
-
-/* positioning-layers static and absolute */
-
-#breadcrumbs {
- padding: 3px 10px 3px 10px;
- margin: 0px 4px 0px 4px;
- font-size: small;
- border: 1px solid #CCCCCC;
- /*border-bottom: 1px solid #aaa;
- /* background-color: #ccc; lime;
- border-color: #663300;*/
- background-color: #ffd0a0;
- /*max-width: 77em;*/
-}
-
-#left {
- position: absolute;
- left: 0px;
- width: 15em;
- margin: 4px 0px 0px 4px;
- padding: 0px;
- font-size: 80%;
- background-color: #ffffff;
-}
-
-.menuGroup {
- border: 1px solid #cccccc;
- background-color: #fff8e8;
- color: #564b47;
- border: 1px solid #cccccc;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
-
-.menuGroup a {
- display: block;
- width: 95.5%;
- margin: 0px;
- padding: 2px;
- border: solid 1px #fff8e8;
- color: #0066cc;
- text-decoration: none;
-}
-
-.menuGroup a:hover {
- border: solid 1px #FFFFFF;
- background-color: #3333CC;
- color: #ffffff;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
-
-.pub {
- text-align: center;
-}
-
-#left .pub a:hover {
- background-color: transparent;
- border: solid 0px #FFFFFF;
-}
-
-#left a:hover, #right a:hover {
- border: solid 1px #FFFFFF;
- background-color: #3333CC;
- color: #ffffff;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
-
-#left div.jobadd {
- font-size: 160%;
- color: #fff;
- margin: 0px;
- padding: 1ex;
-
- text-align: center;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-
- background-image: -ms-linear-gradient(bottom right, #FFBB55 0%, #FF8822 100%);
- background-image: -moz-linear-gradient(bottom right, #FFBB55 0%, #FF8822 100%);
- background-image: -o-linear-gradient(bottom right, #FFBB55 0%, #FF8822 100%);
- background-image: -webkit-gradient(linear, right bottom, left top, color-stop(0, #FFBB55), color-stop(1, #FF8822));
- background-image: -webkit-linear-gradient(bottom right, #FFBB55 0%, #FF8822 100%);
- background-image: linear-gradient(to top left, #FFBB55 0%, #FF8822 100%);
-}
-
-#left div.jobadd a, div.jobadd a:hover {
- background-color: transparent;
- color: #fff;
- border-width: 0px;
-}
-
-p.menu_header {
- margin: 0px;
- padding: 2px;
- font-weight: normal;
- background-color: #ffd0a0;
- border-top: solid 1px #CCCCCC;
- border-bottom: solid 1px #CCCCCC;
-}
-
-#content {
- margin: 0px 12em 0px 16em;
- padding: 0px;
- background-color: #ffffff;
-}
-
-
-#content img {
- border:none;
- margin-left: auto;
- margin-right: auto;
- display: block;
-}
-
-.author {
- text-align: left;
- font-weight: bold;
-}
-
-.definition {
- padding-left: 5px;
- padding-right: 5px;
- margin: 5px 50px 5px 50px;
- text-align: justify;
- background-color: #E6E64C;
-}
-
-.deftitle {
- font-weight: bold;
-}
-
-.big {
- font-size: 130%;
-}
-
-.green {
- color: green;
-}
-.blue {
- color: blue;
-}
-
-.red {
- color: red;
-}
-
-.bold {
- font-weight: bold;
-}
-
-.redBold {
- color: red;
- font-weight: bold;
-}
-.greenBold {
- color: green;
- font-weight: bold;
-}
-
-code {
- font-family: Courier, monospace;
-}
-
-
-.option {
- border: 1px solid black;
- font-family: Arial, sans-serif;
-}
-.highlight {
- width: 18em;
- float: right;
- display: inline;
- font-size: 110%;
-
- border: 2px solid #711;
- -webkit-border-radius: 4px;
- -moz-border-radius: 4px;
- border-radius: 4px;
- background:#FFE0B0;
- padding-top: 1ex;
- padding-left: 1ex;
- padding-right: 1ex;
- padding-bottom: 1ex;
- margin-left: 1em;
- margin-right: 0em;
- margin-bottom: 1ex;
-}
-
-
-.survey {
- font-weight: bolder;
- font-size: larger;
-
- border:1px solid #cccccc;
- background:#FFCC99;
- padding-left: 1ex;
- padding-right: 1ex;
-}
-/* ========== body table ============ */
-table.bodyTable {
- padding: 0px;
- margin-left: -2px;
- margin-right: -2px;
-}
-
-table.bodyTable th {
- color: white;
- background-color: #bbb;
- font-weight: bold;
-}
-
-
-table.bodyTable td {
- padding-left: 0.5ex;
- padding-bottom: 0.5ex;
-}
-
-
-/* apply to tr elements of tables which are both bodytable and dark */
-table[class="bodyTable dark"] tr {
- background-color: #ddd;
-}
-
-/* apply to tr elements of tables which are both bodytable and dark */
-table[class="bodyTable properties"] tr {
- vertical-align: top;
-}
-
-table.bodyTable tr.a {
- background-color: #ddd;
-}
-
-table.bodyTable tr.b {
- background-color: #eee;
-}
-
-table.bodyTable tr.alt {
- background-color: #eee;
-}
-
-.striped tr:nth-child(odd) td {
- background-color: #f9f9f9;
-}
-.striped td {
- background-color: #f0f0f0;
-}
-
-/* EOF =============== bodyTable =============== */
-
-.label {
- padding: 1px 3px 2px;
- font-size: 9.75px;
- font-weight: bold;
- color: #ffffff;
- text-transform: uppercase;
- white-space: nowrap;
- background-color: #bfbfbf;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
-.label.notice {
- background-color: #62cffc;
-}
-
-
-/* ------------------------------------ */
-
-dt {
- border-top: 2px solid #888888;
- color: #333;
- padding-bottom: 1ex;
- padding-top: 1ex;
- font-weight: bold;
-}
-dd {
- margin-top: 1ex;
- margin-bottom: 1ex;
-}
-
-/* ------------------------------------ */
-.anchor { display:none; }
-
-h1 .anchor:before {content:url(anchor24.png);}
-h2 .anchor:before {content:url(anchor20.png);}
-h3 .anchor:before {content:url(anchor16.png);}
-h4 .anchor:before {content:url(anchor12.png);}
-td .anchor:before {content:url(anchor12.png);}
-dt .anchor:before {content:url(anchor12.png);}
-
-h1:hover .anchor { margin-left: -24px; }
-h2:hover .anchor { margin-left: -20px; }
-h3:hover .anchor { margin-left: -16px; }
-h4:hover .anchor { margin-left: -12px; }
-td:hover .anchor { margin-left: -12px; }
-dt:hover .anchor { margin-left: -12px; }
-
-h1:hover .anchor,
-h2:hover .anchor,
-h3:hover .anchor,
-h4:hover .anchor,
-td:hover .anchor,
-dt:hover .anchor {
- display: inline-block;
- text-decoration: none;
-}
-
-
-/* ------------ twitter button ------- */
-.twitter_button {
- vertical-align: text-bottom;
- padding-top: 3px;
- padding-right: 16px;
- float: left;
- height: 18px;div
- text-shadow: 0 1px 0 rgba(255, 255, 255, 0.5);
- white-space: nowrap;
- background-color: white;
- background-image: -moz-linear-gradient(top, #ffffff, #dedede);
- background-image: -webkit-gradient(linear, left top, left bottom, from(#ffffff), to(#dedede));
- background-image: -ms-linear-gradient(top, #ffffff, #dedede);
- background-image: linear-gradient(top, #ffffff, #dedede);
- background-image: -o-linear-gradient(top, #ffffff, #dedede);
- border: #CCC solid 1px;
- -webkit-border-radius: 3px;
- -moz-border-radius: 3px;
- border-radius: 3px;
-}
diff --git a/slf4j-site/src/site/pages/docs.html b/slf4j-site/src/site/pages/docs.html
deleted file mode 100644
index 9788d788..00000000
--- a/slf4j-site/src/site/pages/docs.html
+++ /dev/null
@@ -1,153 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Documentation</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
- <script type="text/javascript">prefix='';</script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <noscript>Please turn on Javascript to view this menu</noscript>
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
- <h1>Documentation</h1>
-
- <p>Given the small size of SLF4J, its documentation is not very
- lengthy.</p>
-
- <ul>
- <li><a href="manual.html">User manual</a></li>
- <li><a href="faq.html">FAQ</a></li>
- <li><a href="codes.html">SLF4J error messages</a></li>
- <li><a href="legacy.html">Bridging legacy APIs</a></li>
- <li><a href="migrator.html">SLF4J Migrator</a></li>
- <li><a href="extensions.html">SLF4J extensions</a></li>
-
- <li><a href="localization.html">Localization/Internalization support</a></li>
-
- <li><a href="apidocs/index.html">javadocs</a></li>
- <li>
- <a href="xref/index.html">sources</a>,
- <a href="xref-test/index.html">test sources</a>
- </li>
- </ul>
-
-
- <h2>Videos</h2>
-
- <table>
- <tr>
- <td>
- <a href="http://www.youtube.com/watch?v=tMLEbGJ2z7I&hd=1;"><img style="align:left;" src="images/beginnerSLF4J.png"/></a>
- </td>
- </tr>
- </table>
-
- <h2>Articles, blogs &amp; presentations</h2>
-
- <ul>
-
- <li>
- <a
- href="http://jayunit100.blogspot.ch/2013/10/simplifying-distinction-between-sl4j.html">Simplifying
- the distinction between SL4J and commons logging</a>, by Jay
- Vyas
- </li>
-
- <li>
- <a
- href="http://runjva.appspot.com/logging101/index.html">Logging
- in Java with slf4j</a>, by Thorbj&oslash;rn Ravn Andersen
- </li>
-
- <li>
- <a href="http://eclipsezone.com/articles/franey-logging/?source=archives">Universal
- Logger Plug-ins for RCP Applications</a>, by John J. Franey
- </li>
-
-
- <li><a href="http://blog.frankel.ch/tech/dev/java/thoughts-on-java-logging-and-slf4j">Thoughts on Java logging and SLF4J</a> by Nicolas Frankel
- </li>
-
- <li><a href="http://glauche.de/2009/08/24/">Logging with SLF4J and
- Guice</a>, by Michael Glauche </li>
-
- <li>
- <a href="slf4j-in-10-slides.ppt">SLF4J in 10 slides</a>, by Ceki G&uuml;lc&uuml;
- </li>
-
- <li><a
- href="http://parleys.com/play/514892260364bc17fc56be83/chapter0/about">Devoxx-2009
- video presentation</a>, by Ceki G&#252;lc&#252; </li>
-
- <li>
- <a
- href="http://day-to-day-stuff.blogspot.com/2007/10/announcement-version-99-does-not-exist.html">
- Version 99 Does Not Exist</a>, by Erik van Oosten
- </li>
-
- <li>
- <a href="http://www.catosplace.net/blogs/personal/?p=442">JUnit
- 4 Test Logging Tips using SLF4J</a>, by Pete Sellars
- </li>
-
- <li>
- <a
- href="http://tapestryjava.blogspot.com/2007/08/so-long-commons-logging-hello-slf4j.html">So
- long, commons-logging, hello SLF4J</a>, by Howard Lewis Ship
- </li>
-
- <li>
- <a
- href="http://bsnyderblog.blogspot.com/2007/08/my-soapbox-for-slf4j.html">My
- Soapbox for SLF4J</a>, by Bruce Snyder
- </li>
-
- <li>
- <a
- href="http://blog.springsource.com/2009/12/04/logging-dependencies-in-spring/">Logging
- Dependencies in Spring </a> by Dave Syer
- </li>
-
- <li>
- <a href="http://baptiste-wicht.developpez.com/tutorials/java/slf4j/">Logging with SLF4J</a>
- by Baptiste Wicht
- </li>
-
- <li>
- <a href="http://javajing.com/2012/06/08/slf4j.html">Steps to use
- SLF4J</a> short (8 minute) video
- </li>
-
- </ul>
-
- <h4>In French</h4>
-
- <ul>
- <li><a
- href="http://www.insideit.fr/post/2009/11/23/SLF4J-LOGBack">SLF4J
- &amp; Logback : simplifiez-vous les logs</a> by Ludovic Meurillon
- </li>
-
- <li>
- <a
- href="http://baptiste-wicht.developpez.com/tutoriels/java/slf4j/">Journalisation avec SLF4J
- </a> by Baptiste Wicht
- </li>
-
- </ul>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
-
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/download.html b/slf4j-site/src/site/pages/download.html
deleted file mode 100644
index f7b19307..00000000
--- a/slf4j-site/src/site/pages/download.html
+++ /dev/null
@@ -1,123 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Binary files</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/popup.css" media="screen" />
- </head>
- <body onload="">
- <script type="text/javascript">prefix='';</script>
-
- <script type="text/javascript" src="templates/header.js" ></script>
- <div id="left">
- <noscript>Please turn on Javascript to view this menu</noscript>
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
-
- <div id="popupContents">
- <h3>Would you like to subscribe to the QOS.CH announcements mailing
- list?</h3>
-
-
- <p>The list is reserved for announcements related to QOS.CH
- projects such as cal10n, logback, mistletoe and SLF4J.</p>
- <br/>
- <table width="100%">
- <tr>
- <td><a class="popupLink" id="announce">Yes, I'd like to subscribe.</a></td>
- <td><a class="popupLink" id="popupContentsClose">No, thanks.</a></td>
- </tr>
- </table>
- </div>
- <div id="backgroundPopup"></div>
-
-
- <div id="content">
-
- <h2>Latest official SLF4J distribution</h2>
-
-
- <p>Download version ${project.version} including <i>full source code</i>,
- class files and documentation in ZIP or TAR.GZ format: </p>
-
- <ul>
- <li><a href="dist/slf4j-${project.version}.tar.gz"><b>slf4j-${project.version}.tar.gz</b></a> </li>
- <li><a href="dist/slf4j-${project.version}.zip"><b>slf4j-${project.version}.zip</b></a> </li>
- </ul>
-
-
- <h3>Previous versions</h3>
-
- <p>Previous versions of SLF4J can be downloaded from the <a
- href="dist/">main repository</a>.
- </p>
-
- <h3>javadoc downloads</h3>
-
- <p>For each slf4j module, the corresponding javadoc artifacts can be
- downloaded from the <a
- href="http://repo2.maven.org/maven2/org/slf4j/">Maven central
- repository</a> as <em>javadoc.jar</em> files.
- </p>
-
- <h2>Closely related projects</h2>
-
-
- <ul>
- <li><a
- href="http://projects.lidalia.org.uk/sysout-over-slf4j/">sysout-over-slf4j</a>
- module redirects all calls to System.out and System.err to an
- SLF4J defined logger with the name of the fully qualified class in
- which the System.out.println (or similar) call was made, at
- configurable levels. </li>
-
- <li><a href="http://projects.lidalia.org.uk/slf4j-test">SLF4J
- Test</a> is an SLF4J implementation focused on facilitating easier
- unit testing of logging code.
- </li>
-
- <li><a
- href="http://projects.lidalia.org.uk/lidalia-slf4j-ext/">Lidalia
- SLF4J Extensions</a> allows logging at a level determined at runtime
- rather than compile-time.
- </li>
- </ul>
-
- <h2>Additional SLF4J-related software</h2>
-
- <ul>
-
- <li><a href="http://code.google.com/p/jdbcdslog/">jdbcdslog</a> a
- tracing tool for JDBC, by Andriy Kolyadenko</li>
-
- <li><a href="http://www.jwaresoftware.org/wiki/log4ant/home">Log4Ant</a>, by JWare Software
- </li>
-
- <li><a href="http://code.google.com/p/log4jdbc/">log4jdbc</a>, a
- JDBC driver which logs SQL information before delegating to an
- underlying JDBC driver, by Arthur Blake
- </li>
-
- <li><a href="http://code.google.com/p/slf4fx/">SLF4Fx</a>, an open
- source logging suite for Flex, by Dmitry Motylev
- </li>
-
- <li><a
- href="http://svn.codehaus.org/sonar/trunk/sonar-web/src/main/webapp/WEB-INF/lib/slf4j_logger.rb">SLF4J
- logger for JRuby on Rails</a> and <a
- href="http://svn.codehaus.org/sonar/trunk/sonar-web/src/main/webapp/WEB-INF/config/environments/production.rb">settings
- file</a>, by SonarSource </li>
-
- </ul>
-
-
- </p>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/extensions.html b/slf4j-site/src/site/pages/extensions.html
deleted file mode 100755
index d4695810..00000000
--- a/slf4j-site/src/site/pages/extensions.html
+++ /dev/null
@@ -1,886 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J extensions</title>
-
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
- </head>
- <body onload="prettyPrint()">
- <script type="text/javascript">prefix='';</script>
- <script type="text/javascript" src="js/prettify.js"></script>
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
- <h1>SLF4J extensions</h1>
-
- <p>SLF4J extensions are packaged within <em>slf4j-ext.jar</em>
- which ships with SLF4J. </p>
-
-
- <ul>
- <li><a href="#profiler">Profiler</a></li>
- <li><a href="#extended_logger">Extended logger</a></li>
- <li><a href="#event_logger">Event Logging</a></li>
- <li><a href="#javaagent">Logging added with Java agent (requires Java 5)</a></li>
- </ul>
-
- <h2><a name="profiler"></a>Profilers</h2>
-
- <h3>What is a profiler?</h3>
-
- <p>According to wikipedia, <a
- href="http://en.wikipedia.org/wiki/Profiler_%28computer_science%29">profiling</a>
- is the investigation of a program's behavior using information
- gathered as the program runs, i.e. it is a form of dynamic program
- analysis, as opposed to static code analysis. The usual goal of
- performance analysis is to determine which parts of a program to
- optimize for speed or memory usage.
- </p>
-
- <p>SLF4J profilers, a.k.a. poor man's profilers, will help the
- developer gather performance data. Essentially, a profiler
- consists of one or more stopwatches. Stopwatches are driven
- (started/stopped) by statements in the <em>source code</em>. An
- example should make the point clearer.
- </p>
-
- <h3>Basic example</h3>
-
-
- <em>Example: Using the profiler: <a
- href="xref-test/org/slf4j/profiler/BasicProfilerDemo.html">BasicProfilerDemo</a></em>
-
- <pre class="prettyprint source">[omitted]
-32 public class BasicProfilerDemo {
-33
-34 public static void main(String[] args) {
-35 // create a profiler called "BASIC"
-36 <b>Profiler profiler = new Profiler("BASIC");</b>
-37 <b>profiler.start("A");</b>
-38 doA();
-39
-40 <b>profiler.start("B");</b>
-41 doB();
-42
-43 <b>profiler.start("OTHER");</b>
-44 doOther();
-45 <b>profiler.stop().print();</b>
-46 }
-[omitted]</pre>
-
-
- <p>Running the above example will output the following output.</p>
-
- <p class="source">+ Profiler [BASIC]
-|-- elapsed time [A] 220.487 milliseconds.
-|-- elapsed time [B] 2499.866 milliseconds.
-|-- elapsed time [OTHER] 3300.745 milliseconds.
-|-- Total [BASIC] 6022.568 milliseconds.</p>
-
- <p>Instantiating a profiler starts a global stopwatch. Each call to
- the start() method starts a new and named stopwatch. In addition to
- starting a named stopwatch, the start() method also causes the
- previous stopwatch to stop. Thus, the call to
- <code>profiler.start("A")</code> starts a stopwatch named "A". The
- subsequent call to <code>profiler.start("B")</code> starts
- stopwatch "B" and simultaneously stops the stopwatch named
- "A". Invoking the <code>stop()</code> on a profiler stops the last
- stopwatch as well as the global stopwatch which was started when
- the profiler was instantiated.
- </p>
-
-
- <h3>Profiler nesting</h3>
-
- <p>Profilers can also be nested. By nesting profilers, it is
- possible to measure a task which itself has subtasks that need to
- be timed and measured.
- </p>
-
- <p>Starting a nested profiler will stop any previously started
- stopwatch or nested profiler associated with the parent profiler.
- </p>
-
- <p>Often times, the subtask is implemented by a different class as
- the class hosting the parent profiler. Using the
- <code>ProfilerRegistry</code> is a convenient way of passing a
- nested profiler to an object outside the current object. Each
- thread has its own profiler registry which can be retrieved by
- invoking the <code>getThreadContextInstance()</code> method.
- </p>
-
- <em>Example: <a
- href="xref-test/org/slf4j/profiler/NestedProfilerDemo.html">NestedProfilerDemo</a>
- </em>
-
- <pre class="prettyprint source">33 public class NestedProfilerDemo {
-34
-35 public static void main(String[] args) {
-36 // create a profiler called "DEMO"
-37 Profiler profiler = new Profiler("DEMO");
-38
-39 // register this profiler in the thread context's profiler registry
-40 <b>ProfilerRegistry profilerRegistry = ProfilerRegistry.getThreadContextInstance();</b>
-41 <b>profiler.registerWith(profilerRegistry);</b>
-42
-43 // start a stopwatch called "RANDOM"
-44 profiler.start("RANDOM");
-45 RandomIntegerArrayGenerator riaGenerator = new RandomIntegerArrayGenerator();
-46 int n = 1000*1000;
-47 int[] randomArray = riaGenerator.generate(n);
-48
-49 // create and start a nested profiler called "SORT_AND_PRUNE"
-50 // By virtue of its parent-child relationship with the "DEMO"
-51 // profiler, and the previous registration of the parent profiler,
-52 // this nested profiler will be automatically registered
-53 // with the thread context's profiler registry
-54 <b>profiler.startNested(SortAndPruneComposites.NESTED_PROFILER_NAME);</b>
-55
-56 SortAndPruneComposites pruner = new SortAndPruneComposites(randomArray);
-57 pruner.sortAndPruneComposites();
-58
-59 // stop and print the "DEMO" printer
-60 profiler.stop().print();
-61 }
-62 }</pre>
-
- <p>Here is the relevant excerpt from the <a
- href="xref-test/org/slf4j/profiler/SortAndPruneComposites.html">SortAndPruneComposites</a>
- class.
- </p>
-
- <pre class="prettyprint source">[omitted]
-6 public class SortAndPruneComposites {
-7
-8 static String NESTED_PROFILER_NAME = "SORT_AND_PRUNE";
-9
-10 final int[] originalArray;
-11 final int originalArrayLength;
-12
-13 public SortAndPruneComposites(int[] randomArray) {
-14 this.originalArray = randomArray;
-15 this.originalArrayLength = randomArray.length;
-16
-17 }
-18
-19 public int[] sortAndPruneComposites() {
-20 // retrieve previously registered profiler named "SORT_AND_PRUNE"
-21 ProfilerRegistry profilerRegistry = ProfilerRegistry.getThreadContextInstance();
-22 <b>Profiler sortProfiler = profilerRegistry.get(NESTED_PROFILER_NAME);</b>
-23
-24 // start a new stopwatch called SORT
-25 sortProfiler.start("SORT");
-26 int[] sortedArray = sort();
-27 // start a new stopwatch called PRUNE_COMPOSITES
-28 sortProfiler.start("PRUNE_COMPOSITES");
-29 int result[] = pruneComposites(sortedArray);
-30
-31 return result;
-32 }
-[omitted] </pre>
-
-
- <p>On a Dual-Core Intel CPU clocked at 3.2 GHz, running the
- <code>ProfilerDemo</code> application yields the following output:</p>
-
- <p class="source">+ Profiler [DEMO]
-|-- elapsed time [RANDOM] 70.524 milliseconds.
-|---+ Profiler [SORT_AND_PRUNE]
- |-- elapsed time [SORT] 665.281 milliseconds.
- |-- elapsed time [PRUNE_COMPOSITES] 5695.515 milliseconds.
- |-- Subtotal [SORT_AND_PRUNE] 6360.866 milliseconds.
-|-- elapsed time [SORT_AND_PRUNE] 6360.866 milliseconds.
-|-- Total [DEMO] 6433.922 milliseconds.</p>
-
- <p>From the above, we learn that generating 1'000'000 random
- integers takes 70 ms, sorting them 665 ms, and pruning the composite
- (non-prime) integers 5695 ms, for a grand total of 6433 ms. Given
- that pruning composites takes most of the CPU effort, any future
- optimizations efforts would be directed at the pruning part.
- </p>
-
- <p>With just a few well-placed profiler calls we were able to
- identify hot-spots in our application. Also note that passing a
- profiler to a target class could be achieved by registering it in a
- profiler registry and then retrieving it in the target class.
- </p>
-
- <h3>Printing using a logger</h3>
-
- <p> Invoking <code>profiler.print</code> will always print the
- output on the console. If you wish to leave the profiler code in
- production, then you probably need more control over the output
- destination. This can be accomplished by associating a logger of
- your choice with a profiler.
- </p>
-
- <p>After you have associated a logger with a profiler, you would
- invoke the <code>log()</code> method instead of <code>print()</code>
- previously, as the next example illustrates.
- </p>
-
- <em>Profiler with a logger: <a
- href="xref-test/org/slf4j/profiler/NestedProfilerDemo2.html">NestedProfilerDemo2</a>
- </em>
-
- <pre class="prettyprint source">[omitted]
-17 public class NestedProfilerDemo2 {
-18
-19 static Logger logger = LoggerFactory.getLogger(NestedProfilerDemo2.class);
-20
-21 public static void main(String[] args) {
-22 Profiler profiler = new Profiler("DEMO");
-23 // associate a logger with the profiler
-24 <b>profiler.setLogger(logger);</b>
-25
-26 ProfilerRegistry profilerRegistry = ProfilerRegistry.getThreadContextInstance();
-27 profiler.registerWith(profilerRegistry);
-28
-29 profiler.start("RANDOM");
-30 RandomIntegerArrayGenerator riaGenerator = new RandomIntegerArrayGenerator();
-31 int n = 10*1000;
-32 int[] randomArray = riaGenerator.generate(n);
-33
-34 profiler.startNested(SortAndPruneComposites.NESTED_PROFILER_NAME);
-35
-36 SortAndPruneComposites pruner = new SortAndPruneComposites(randomArray);
-37 pruner.sortAndPruneComposites();
-38
-39 // stop and log
-40 profiler.stop().<b>log()</b>;
-41 }
-42 } </pre>
-
- <p>The output generated by this example will depend on the logging
- environment, but should be very similar to the output generated by
- the previous <code>NestedProfilerDemo</code> example.
- </p>
-
- <p>The log() method logs at level DEBUG using a marker named
- "PROFILER".</p>
-
- <p>If your logging system supports markers, e.g. logback, you could
- specifically enable or disable output generated by SLF4J
- profilers. Here is logback configuration file disabling output for
- any logging event bearing the "PROFILER" marker, even if the logger
- used by the profiler is enabled for the debug level.
- </p>
-
-
- <em>logback configuration disabling logging from profilers, and only
- profilers</em>
-
- <pre class="prettyprint source">&lt;configuration>
-
- <b>&lt;turboFilter class="ch.qos.logback.classic.turbo.MarkerFilter">
- &lt;Marker>PROFILER&lt;/Marker>
- &lt;OnMatch>DENY&lt;/OnMatch>
- &lt;/turboFilter></b>
-
- &lt;appender name="STDOUT"
- class="ch.qos.logback.core.ConsoleAppender">
- &lt;layout class="ch.qos.logback.classic.PatternLayout">
- &lt;Pattern>%-5level %logger{36} - %msg%n&lt;/Pattern>
- &lt;/layout>
- &lt;/appender>
-
- &lt;root>
- &lt;level value="DEBUG" />
- &lt;appender-ref ref="STDOUT" />
- &lt;/root>
-&lt;/configuration> </pre>
-
-
-<!-- .............................................................. -->
-
- <h2><a name="mdcStrLookup"></a>MDCStrLookup</h2>
-
- <p>StrLookup is a class defined in Apache Commons Lang. It is used
- in conjunction with the StrSubstitutor class to allow Strings to
- have tokens in the Strings dynamically replaced at run time. There
- are many cases where it is desirable to merge the values for keys
- in the SLF4J MDC into Strings. MDCStrLookup makes this possible.
- </p>
- <p>
- Apache Commons Configuration provides a ConfigurationInterpolator
- class. This class allows new StrLookups to be registered and the
- values can then be used to merge with both the configuration of
- Commons Configuration as well as the configuration files it manages.
- </p>
- <p>
- StrLookup obviously has a dependency on Commons Lang. The Maven
- pom.xml for slf4j-ext lists this dependency as optional so
- that those wishing to use other extensions are not required to
- unnecessarily package the commons lang jar. Therefore, when using
- MDCStrLookup the dependency for commons-lang must be explicitly
- declared along with slf4j-ext.
- </p>
-
-<!-- .............................................................. -->
-
- <h2><a name="extended_logger"></a>Extended Logger</h2>
-
- <p>The <a
- href="apidocs/org/slf4j/ext/XLogger.html"><code>XLogger</code></a>
- class provides a few extra logging methods that are quite useful
- for following the execution path of applications. These methods
- generate logging events that can be filtered separately from other
- debug logging. Liberal use of these methods is encouraged as the
- output has been found to
- </p>
-
- <ul>
- <li>aid in problem diagnosis in development without requiring a
- debug session</li>
-
- <li>aid in problem diagnosis in production where no debugging is
- possible</li>
-
- <li>help educate new developers in learning the application.</li>
- </ul>
-
-
- <p>The two most used methods are the <code>entry()</code> and
- <code>exit()</code> methods. <code>entry()</code> should be placed
- at the beginning of methods, except perhaps for simple getters and
- setters. <code>entry()</code> can be called passing from 0 to 4
- parameters. Typically these will be parameters passed to the
- method. The <code>entry()</code> method logs with a level of TRACE
- and uses a <code>Marker</code> with a name of "ENTER" which is also
- a "FLOW" Marker.
- </p>
-
- <p>The <code>exit()</code> method should be placed before any
- return statement or as the last statement of methods without a
- return. <code>exit()</code> can be called with or without a
- parameter. Typically, methods that return void will use
- <code>exit()</code> while methods that return an Object will use
- exit(Object obj). The <code>entry()</code> method logs with a
- level of TRACE and uses a Marker with a name of "EXIT" which is
- also a "FLOW" Marker.
- </p>
-
- <p>The throwing() method can be used by an application when it is
- throwing an exception that is unlikely to be handled, such as a
- RuntimeException. This will insure that proper diagnostics are
- available if needed. The logging event generated will have a level
- of ERROR and will have an associated Marker with a name of
- "THROWING" which is also an "EXCEPTION" Marker.
- </p>
-
- <p>The catching() method can be used by an application when it
- catches an Exception that it is not going to rethrow, either
- explicitly or attached to another Exception. The logging event
- generated will have a level of ERROR and will have an associated
- Marker with a name of "CATCHING" which is also an "EXCEPTION"
- Marker.
- </p>
-
- <p>By using these extended methods applications that standardize on
- SLF4J can be assured that they will be able to perform diagnostic
- logging in a standardized manner.
- </p>
-
- <p>Note that XLogger instances are obtained to through the
- <a
- href="apidocs/org/slf4j/ext/XLoggerFactory.html"><code>XLoggerFactory</code></a>
- utility class.</p>
-
- <p>The following example shows a simple application using these
- methods in a fairly typical manner. The <code>throwing()</code>
- method is not present since no Exceptions are explicitly thrown and
- not handled.
- </p>
-
- <pre class="prettyprint source">package com.test;
-
-import org.slf4j.ext.XLogger;
-import org.slf4j.ext.XLoggerFactory;
-
-import java.util.Random;
-
-public class TestService {
- private XLogger logger = XLoggerFactory.getXLogger(TestService.class
- .getName());
-
- private String[] messages = new String[] { "Hello, World",
- "Goodbye Cruel World", "You had me at hello" };
-
- private Random rand = new Random(1);
-
- public String retrieveMessage() {
- logger.entry();
-
- String testMsg = getMessage(getKey());
-
- logger.exit(testMsg);
- return testMsg;
- }
-
- public void exampleException() {
- logger.entry();
- try {
- String msg = messages[messages.length];
- logger.error("An exception should have been thrown");
- } catch (Exception ex) {
- logger.catching(ex);
- }
- logger.exit();
- }
-
- public String getMessage(int key) {
- logger.entry(key);
-
- String value = messages[key];
-
- logger.exit(value);
- return value;
- }
-
- private int getKey() {
- logger.entry();
- int key = rand.nextInt(messages.length);
- logger.exit(key);
- return key;
- }
-}</pre>
-
- <p>This test application uses the preceding service to generate
- logging events.
- </p>
-
- <pre class="prettyprint source">package com.test;
-
-public class App {
- public static void main( String[] args ) {
- TestService service = new TestService();
- service.retrieveMessage();
- service.retrieveMessage();
- service.exampleException();
- }
-} </pre>
-
- <p>The configuration below will cause all output to be routed to
- target/test.log. The pattern for the FileAppender includes the
- class name, line number and method name. Including these in the
- pattern are critical for the log to be of value.
- </p>
-
- <pre class="prettyprint source">&lt;?xml version='1.0' encoding='UTF-8'?>
-&lt;configuration&gt;
- &lt;appender name="console" class="ch.qos.logback.core.ConsoleAppender"&gt;
- &lt;filter class="ch.qos.logback.classic.filter.LevelFilter"&gt;
- &lt;level&gt;ERROR&lt;/level&gt;
- &lt;onMatch&gt;ACCEPT&lt;/onMatch&gt;
- &lt;onMismatch&gt;DENY&lt;/onMismatch&gt;
- &lt;/filter&gt;
- &lt;layout class="ch.qos.logback.classic.PatternLayout"&gt;
- &lt;Pattern&gt;%d{HH:mm:ss.SSS} %-5level %class{36}:%L %M - %msg%n&lt;/Pattern&gt;
- &lt;/layout&gt;
- &lt;/appender&gt;
- &lt;appender name="log" class="ch.qos.logback.core.FileAppender"&gt;
- &lt;File&gt;target/test.log&lt;/File&gt;
- &lt;Append&gt;false&lt;/Append&gt;
- &lt;layout class="ch.qos.logback.classic.PatternLayout"&gt;
- &lt;Pattern&gt;%d{HH:mm:ss.SSS} %-5level %class{36}:%L %M - %msg%n&lt;/Pattern&gt;
- &lt;/layout&gt;
- &lt;/appender&gt;
-
- &lt;root&gt;
- &lt;level value="trace" /&gt;
- &lt;appender-ref ref="log" /&gt;
- &lt;/root&gt;
-&lt;/configuration&gt;
-</pre>
- <p>
- Here is the output that results from the Java classes and configuration above.
- </p>
-<p class="source">00:07:57.725 TRACE com.test.TestService:22 retrieveMessage - entry
-00:07:57.738 TRACE com.test.TestService:57 getKey - entry
-00:07:57.739 TRACE com.test.TestService:59 getKey - exit with (0)
-00:07:57.741 TRACE com.test.TestService:47 getMessage - entry with (0)
-00:07:57.741 TRACE com.test.TestService:51 getMessage - exit with (Hello, World)
-00:07:57.742 TRACE com.test.TestService:26 retrieveMessage - exit with (Hello, World)
-00:07:57.742 TRACE com.test.TestService:22 retrieveMessage - entry
-00:07:57.742 TRACE com.test.TestService:57 getKey - entry
-00:07:57.743 TRACE com.test.TestService:59 getKey - exit with (1)
-00:07:57.745 TRACE com.test.TestService:47 getMessage - entry with (1)
-00:07:57.745 TRACE com.test.TestService:51 getMessage - exit with (Goodbye Cruel World)
-00:07:57.746 TRACE com.test.TestService:26 retrieveMessage - exit with (Goodbye Cruel World)
-00:07:57.746 TRACE com.test.TestService:32 exampleException - entry
-00:07:57.750 ERROR com.test.TestService:40 exampleException - catching
-java.lang.ArrayIndexOutOfBoundsException: 3
- at com.test.TestService.exampleException(TestService.java:35)
- at com.test.AppTest.testApp(AppTest.java:39)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at junit.framework.TestCase.runTest(TestCase.java:154)
- at junit.framework.TestCase.runBare(TestCase.java:127)
- at junit.framework.TestResult$1.protect(TestResult.java:106)
- at junit.framework.TestResult.runProtected(TestResult.java:124)
- at junit.framework.TestResult.run(TestResult.java:109)
- at junit.framework.TestCase.run(TestCase.java:118)
- at junit.framework.TestSuite.runTest(TestSuite.java:208)
- at junit.framework.TestSuite.run(TestSuite.java:203)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at org.apache.maven.surefire.junit.JUnitTestSet.execute(JUnitTestSet.java:213)
- at org.apache.maven.surefire.suite.AbstractDirectoryTestSuite.executeTestSet(AbstractDirectoryTestSuite.java:140)
- at org.apache.maven.surefire.suite.AbstractDirectoryTestSuite.execute(AbstractDirectoryTestSuite.java:127)
- at org.apache.maven.surefire.Surefire.run(Surefire.java:177)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at org.apache.maven.surefire.booter.SurefireBooter.runSuitesInProcess(SurefireBooter.java:338)
- at org.apache.maven.surefire.booter.SurefireBooter.main(SurefireBooter.java:997)
-00:07:57.750 TRACE com.test.TestService:42 exampleException - exit</p>
-
- <p>Simply changing the root logger level to DEBUG in the example
- above will reduce the output considerably.
- </p>
- <p class="source">00:28:06.004 ERROR com.test.TestService:40 exampleException - catching
-java.lang.ArrayIndexOutOfBoundsException: 3
- at com.test.TestService.exampleException(TestService.java:35)
- at com.test.AppTest.testApp(AppTest.java:39)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at junit.framework.TestCase.runTest(TestCase.java:154)
- at junit.framework.TestCase.runBare(TestCase.java:127)
- at junit.framework.TestResult$1.protect(TestResult.java:106)
- at junit.framework.TestResult.runProtected(TestResult.java:124)
- at junit.framework.TestResult.run(TestResult.java:109)
- at junit.framework.TestCase.run(TestCase.java:118)
- at junit.framework.TestSuite.runTest(TestSuite.java:208)
- at junit.framework.TestSuite.run(TestSuite.java:203)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at org.apache.maven.surefire.junit.JUnitTestSet.execute(JUnitTestSet.java:213)
- at org.apache.maven.surefire.suite.AbstractDirectoryTestSuite.executeTestSet(AbstractDirectoryTestSuite.java:140)
- at org.apache.maven.surefire.suite.AbstractDirectoryTestSuite.execute(AbstractDirectoryTestSuite.java:127)
- at org.apache.maven.surefire.Surefire.run(Surefire.java:177)
- at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
- at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
- at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
- at java.lang.reflect.Method.invoke(Method.java:585)
- at org.apache.maven.surefire.booter.SurefireBooter.runSuitesInProcess(SurefireBooter.java:338)
- at org.apache.maven.surefire.booter.SurefireBooter.main(SurefireBooter.java:997) </p>
-
- <!-- .............................................................. -->
-
- <h2><a name="event_logger"></a>Event Logging</h2>
-
- <p>The EventLogger class provides a simple mechanism for logging events that occur in an application.
- While the EventLogger is useful as a way of initiating events that should be processed by an audit
- Logging system, it does not implement any of the features an audit logging system would require
- such as guaranteed delivery.</p>
-
- <p>The recommended way of using the EventLogger in a typical web application is to populate
- the SLF4J MDC with data that is related to the entire lifespan of the request such as the user's id,
- the user's ip address, the product name, etc. This can easily be done in a servlet filter where
- the MDC can also be cleared at the end of the request. When an event that needs to be recorded
- occurs an EventData object should be created and populated. Then call EventLogger.logEvent(data)
- where data is a reference to the EventData object.</p>
-
- <pre class="prettyprint source">import org.slf4j.MDC;
-import org.apache.commons.lang.time.DateUtils;
-
-import javax.servlet.Filter;
-import javax.servlet.FilterConfig;
-import javax.servlet.ServletException;
-import javax.servlet.ServletRequest;
-import javax.servlet.ServletResponse;
-import javax.servlet.FilterChain;
-import javax.servlet.http.HttpSession;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.Cookie;
-import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
-import java.util.TimeZone;
-
-public class RequestFilter implements Filter
-{
- private FilterConfig filterConfig;
- private static String TZ_NAME = "timezoneOffset";
-
- public void init(FilterConfig filterConfig) throws ServletException {
- this.filterConfig = filterConfig;
- }
-
- /**
- * Sample filter that populates the MDC on every request.
- */
- public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse,
- FilterChain filterChain) throws IOException, ServletException {
- HttpServletRequest request = (HttpServletRequest)servletRequest;
- HttpServletResponse response = (HttpServletResponse)servletResponse;
- MDC.put("ipAddress", request.getRemoteAddr());
- HttpSession session = request.getSession(false);
- TimeZone timeZone = null;
- if (session != null) {
- // Something should set this after authentication completes
- String loginId = (String)session.getAttribute("LoginId");
- if (loginId != null) {
- MDC.put("loginId", loginId);
- }
- // This assumes there is some javascript on the user's page to create the cookie.
- if (session.getAttribute(TZ_NAME) == null) {
- if (request.getCookies() != null) {
- for (Cookie cookie : request.getCookies()) {
- if (TZ_NAME.equals(cookie.getName())) {
- int tzOffsetMinutes = Integer.parseInt(cookie.getValue());
- timeZone = TimeZone.getTimeZone("GMT");
- timeZone.setRawOffset((int)(tzOffsetMinutes * DateUtils.MILLIS_PER_MINUTE));
- request.getSession().setAttribute(TZ_NAME, tzOffsetMinutes);
- cookie.setMaxAge(0);
- response.addCookie(cookie);
- }
- }
- }
- }
- }
- MDC.put("hostname", servletRequest.getServerName());
- MDC.put("productName", filterConfig.getInitParameter("ProductName"));
- MDC.put("locale", servletRequest.getLocale().getDisplayName());
- if (timeZone == null) {
- timeZone = TimeZone.getDefault();
- }
- MDC.put("timezone", timeZone.getDisplayName());
- filterChain.doFilter(servletRequest, servletResponse);
- MDC.clear();
- }
-
- public void destroy() {
- }
-} </pre>
-
- <p>Sample class that uses EventLogger.</p>
- <pre class="prettyprint source">import org.slf4j.ext.EventData;
-import org.slf4j.ext.EventLogger;
-
-import java.util.Date;
-import java.util.UUID;
-
-public class MyApp {
-
- public String doFundsTransfer(Account toAccount, Account fromAccount, long amount) {
- toAccount.deposit(amount);
- fromAccount.withdraw(amount);
- EventData data = new EventData();
- data.setEventDateTime(new Date());
- data.setEventType("transfer");
- String confirm = UUID.randomUUID().toString();
- data.setEventId(confirm);
- data.put("toAccount", toAccount);
- data.put("fromAccount", fromAccount);
- data.put("amount", amount);
- EventLogger.logEvent(data);
- return confirm;
- }
-} </pre>
-
- <p>The EventLogger class uses a Logger named "EventLogger". EventLogger uses a logging level
- of INFO. The following shows a configuration using Logback.</p>
- <pre class="prettyprint source">&lt;configuration&gt;
- &lt;appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender"&gt;
- &lt;layout class="ch.qos.logback.classic.PatternLayout"&gt;
- &lt;Pattern&gt;%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n&lt;/Pattern&gt;
- &lt;/layout&gt;
- &lt;/appender&gt;
-
- &lt;appender name="events" class="ch.qos.logback.core.ConsoleAppender"&gt;
- &lt;layout class="ch.qos.logback.classic.PatternLayout"&gt;
- &lt;Pattern&gt;%d{HH:mm:ss.SSS} %X - %msg%n&lt;/Pattern&gt;
- &lt;/layout&gt;
- &lt;/appender&gt;
-
- &lt;logger name="EventLogger" additivity="false"&gt;
- &lt;level value="INFO"/&gt;
- &lt;appender appender-ref="events"/&gt;
- &lt;/logger&gt;
-
- &lt;root level="DEBUG"&gt;
- &lt;appender-ref ref="STDOUT" /&gt;
- &lt;/root&gt;
-
-&lt;/configuration&gt; </pre>
-
- <!-- .............................................................. -->
-
- <h2><a name="javaagent"></a>Adding logging with Java agent</h2>
-
- <p><b>NOTE: BETA RELEASE, NOT PRODUCTION QUALITY</b> </p>
-
- <p>Quickstart for the impatient:</p>
-
- <ol>
- <li>Use Java 5 or later.</li>
- <li>Download slf4j-ext-${project.version}.jar and javassist.jar, and put them
- both in the same directory.</li>
- <li>Ensure your application is properly configured with
- slf4j-api-${project.version}.jar and a suitable backend.</li>
-
- <li>Instead of "java ..." use "java --javaagent:PATH/slf4j-ext-${project.version}.jar=time,verbose,level=info ..."
- <br/>
- (replace PATH with the path to the jar)
- </li>
- <li>That's it!</li>
- </ol>
-
- <p>In some applications logging is used to trace the actual
- execution of the application as opposed to log an occasional event.
- One approach is using the <a href="#extended_logger">extended
- logger</a> to add statements as appropriately, but another is to use
- a tool which modifies compiled bytecode to add these statements!
- Many exist, and the one included in slf4j-ext is not intended to
- compete with these, but merely provide a quick way to get very basic
- trace information from a given application.
- </p>
-
- <p>Java 5 added the Java Instrumentation mechanism, which allows you
- to provide "Java agents" that can inspect and modify the byte code
- of the classes as they are loaded. This allows the original class
- files to remain unchanged, and the transformations done on the byte
- codes depend on the needs at launch time.
- </p>
-
- <p>Given the well-known "Hello World" example:</p>
-
- <pre class="prettyprint source">public class HelloWorld {
- public static void main(String args[]) {
- System.out.println("Hello World");
- }
-}</pre>
-
- <p>a typical transformation would be similar to: (imports omitted)</p>
-
- <pre class="prettyprint source">public class LoggingHelloWorld {
- final static Logger _log = LoggerFactory.getLogger(LoggingHelloWorld.class.getName());
-
- public static void main(String args[]) {
- if (_log.isInfoEnabled()) {
- _log.info("> main(args=" + Arrays.asList(args) + ")");
- }
- System.out.println("Hello World");
- if (_log.isInfoEnabled()) {
- _log.info("&lt; main()");
- }
- }
-}</pre>
-
- <p>which in turn produces the following result when run similar to
- "java LoggingHelloWorld 1 2 3 4":
- </p>
-
- <p class="source">1 [main] INFO LoggingHelloWorld - > main(args=[1, 2, 3, 4])
-Hello World
-1 [main] INFO LoggingHelloWorld - &lt; main()</p>
-
- <p>The same effect could have been had by using this command (with
- the relative path to javassist.jar and
- slf4j-ext-${project.version}.jar being ../jars):</p>
-
- <p class="source">java -javaagent:../jars/slf4j-ext-${project.version}.jar HelloWorld 1 2 3 4</p>
-
- <p></p>
-
-
- <h3>How to use</h3>
- <p>The javaagent may take one or more options separated by comma. The following options
- are currently supported:</p>
-
- <dl>
- <dt><b>level</b>=X</dt>
- <dd>The log level to use for the generated log statements. X is
- one of "info", "debug" or "trace". Default is "info".</dd>
-
- <dt><b>time</b></dt>
- <dd>Print out the current date at program start, and again when
- the program ends plus the execution time in milliseconds.</dd>
-
- <dt><b>verbose</b></dt>
- <dd>Print out when a class is processed as part of being loaded</dd>
-
- <dt><b>ignore</b>=X:Y:...</dt>
- <dd>(Advanced) Provide full list of colon separated prefixes of
- class names NOT to add logging to. The default list is
- "org/slf4j/:ch/qos/logback/:org/apache/log4j/". This does not override the fact that a class must be able to access the
- slf4j-api classes in order to do logging, so if these classes are not visible to a given class it is not instrumented.
- </dd>
- </dl>
-
-
- <p>Some classes may misbehave when being rendered with "object.toString()" so they may be explicitly disabled
- in the logback configuration file permanently. For instance the ToStringBuilder in the Apache Jakarta commons lang
- package is a prime candidate for this. For logback add this snippet to logback.xml:
- <pre>&lt;logger name="org.apache.commons.lang.builder" level="OFF" /&gt;</pre>
- </p>
-
-
-
- <p>Note: These are not finalized yet, and may change.</p>
-
- <h3>Locations of jar files</h3>
-
- <p>The javassist library is used for the actual byte code
- manipulation and must be available to be able to add any logging
- statements. slf4j-ext-${project.version} has been configured to
- look for the following:
- </p>
-
- <ul>
- <li>"javassist-3.4.GA.jar" relatively to
- slf4j-ext-${project.version}.jar as would be if Maven had downloaded
- both from the repository and slf4j-ext-${project.version}.jar was
- referenced directly in the Maven repository in the
- "-javaagent"-argument.</li>
- <li>"javassist-3.4.GA.jar" in the same directory as slf4j-ext</li>
- <li>"javassist.jar" in the same directory as slf4j-ext</li>
- </ul>
-
- <p>A warning message is printed if the javassist library was not
- found by the agent, and options requiring byte code transformations will not work.
- </p>
-
-
- <h3>Misc notes</h3>
-
- <ul>
- <li>A java agent is not invoked on any classes already loaded by the
- class loader.</li>
- <li>Exceptions in the java agent that would normally have been
- printed, may be silently swallowed by the JVM.</li>
- <li>The javaagent only logs to System.err.</li>
- <li>The name of the logger variable is fixed (to a value unlikely to be used) so if that
- name is already used, a failure occurs. This should be changed to determine
- an unused name and use that instead.</li>
- <li>Empty methods are not instrumented (an incorrect check for an interface). They should be</li>
-
- </ul>
-
- <p>(The agent is an adaption of the java.util.logging version
- described in <a
- href="http://today.java.net/pub/a/today/2008/04/24/add-logging-at-class-load-time-with-instrumentation.html"
- >http://today.java.net/pub/a/today/2008/04/24/add-logging-at-class-load-time-with-instrumentation.html</a>)
- </p>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-</div>
-</body>
-</html>
-
diff --git a/slf4j-site/src/site/pages/faq.html b/slf4j-site/src/site/pages/faq.html
deleted file mode 100755
index 1767e2b2..00000000
--- a/slf4j-site/src/site/pages/faq.html
+++ /dev/null
@@ -1,1615 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J FAQ</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
- </head>
- <body onload="prettyPrint(); decorate();">
-
- <script type="text/javascript" src="js/prettify.js"></script>
- <script type="text/javascript">prefix='';</script>
-
- <script type="text/javascript" src="templates/header.js"></script>
- <script type="text/javascript" src="js/jquery-min.js"></script>
- <script type="text/javascript" src="js/decorator.js"></script>
-
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
-
- <div id="content">
-
- <h2><a name="top">Frequently Asked Questions about SLF4J</a></h2>
-
- <p><b>Generalities</b></p>
-
- <ol type="1">
- <li><a href="#what_is">What is SLF4J?</a></li>
-
- <li><a href="#when">When should SLF4J be used?</a></li>
-
- <li><a href="#yet_another_facade"> Is SLF4J yet another loggingfacade?</a></li>
-
- <li><a href="#why_new_project"> If SLF4J fixes JCL, then why
- wasn't the fix made in JCL instead of creating a new project?
- </a>
- </li>
-
- <li><a href="#need_to_recompile"> When using SLF4J, do I have to
- recompile my application to switch to a different logging
- system?
- </a>
- </li>
-
- <li><a href="#requirements">What are SLF4J's requirements?</a></li>
-
- <li><a href="#compatibility">Are SLF4J versions backward
- compatible?</a></li>
-
- <li><a href="#IllegalAccessError">I am getting
- <code>IllegalAccessError</code> exceptions when using SLF4J. Why
- is that?</a></li>
-
-
- <li>
- <a href="#license">Why is SLF4J licensed under X11 type
- license instead of the Apache Software License?
- </a>
- </li>
-
- <li>
- <a href="#where_is_binding">Where can I get a particular
- SLF4J binding?
- </a>
- </li>
-
- <li>
- <a href="#configure_logging">Should my library attempt to
- configure logging?
- </a>
- </li>
-
- <li>
- <a href="#optional_dependency">In order to reduce the number of
- dependencies of our software we would like to make SLF4J an
- optional dependency. Is that a good idea?
- </a>
- </li>
-
- <li>
- <a href="#maven2">What about Maven transitive
- dependencies?
- </a>
- </li>
-
- <li>
- <a href="#excludingJCL">How do I exclude commons-logging as a
- Maven dependency?
- </a>
- </li>
- </ol>
-
-
- <b>About the SLF4J API</b>
-
- <ol type="1">
-
- <li>
- <a href="#string_or_object"> Why don't the printing methods
- in the Logger interface accept message of type Object, but only
- messages of type String?
- </a>
- </li>
-
- <li>
- <a href="#exception_message">
- Can I log an exception without an accompanying message?
- </a>
- </li>
-
-
- <li>
- <a href="#logging_performance"> What is the fastest way of
- (not) logging?
- </a>
- </li>
-
- <li>
- <a href="#string_contents"> How can I log the string contents
- of a single (possibly complex) object?
- </a>
- </li>
-
-
- <li><a href="#fatal"> Why doesn't the
- <code>org.slf4j.Logger</code> interface have methods for the
- FATAL level? </a></li>
-
- <li><a href="#trace">Why was the TRACE level introduced only in
- SLF4J version 1.4.0? </a></li>
-
- <li><a href="#i18n">Does the SLF4J logging API support I18N
- (internationalization)? </a></li>
-
-
- <li><a href="#noLoggerFactory">Is it possible to retrieve loggers
- without going through the static methods in
- <code>LoggerFactory</code>? </a></li>
-
- <li><a href="#paramException">In the presence of an
- exception/throwable, is it possible to parameterize a logging
- statement?</a></li>
-
- </ol>
-
-
-
- <b>Implementing the SLF4J API</b>
-
- <ol type="1">
-
- <li><a href="#slf4j_compatible">How do I make my logging
- framework SLF4J compatible? </a></li>
-
- <li><a href="#marker_interface">How can my logging system add
- support for the <code>Marker</code> interface? </a></li>
-
- <li><a href="#version_checks">How does SLF4J's version check
- mechanism work? </a></li>
-
-
- </ol>
-
-
- <b>General questions about logging</b>
-
-
- <ol type="1">
-
- <li><a href="#declared_static"> Should Logger members of a class
- be declared as static? </a></li>
-
-
- <li><a href="#declaration_pattern">Is there a recommended idiom
- for declaring a loggers in a class?</a></li>
-
- </ol>
-
- <h2>Generalities</h2>
-
- <dl>
- <dt class="doAnchor" name="what_is">What is SLF4J?</dt>
- <dd>
- <p>SLF4J is a simple facade for logging systems allowing the
- end-user to plug-in the desired logging system at deployment
- time.
- </p>
- </dd>
-
- <dt class="doAnchor" name="when">When should SLF4J be used?</dt>
-
- <dd>
- <p>In short, libraries and other embedded components should
- consider SLF4J for their logging needs because libraries cannot
- afford to impose their choice of logging framework on the
- end-user. On the other hand, it does not necessarily make sense
- for stand-alone applications to use SLF4J. Stand-alone
- applications can invoke the logging framework of their choice
- directly. In the case of logback, the question is moot because
- logback exposes its logger API via SLF4J.
- </p>
-
- <p>SLF4J is only a facade, meaning that it does not provide a
- complete logging solution. Operations such as configuring
- appenders or setting logging levels cannot be performed with
- SLF4J. Thus, at some point in time, any non-trivial
- application will need to directly invoke the underlying
- logging system. In other words, complete independence from the
- API underlying logging system is not possible for a
- stand-alone application. Nevertheless, SLF4J reduces the
- impact of this dependence to near-painless levels.
- </p>
-
- <p>Suppose that your CRM application uses log4j for its
- logging. However, one of your important clients request that
- logging be performed through JDK 1.4 logging. If your
- application is riddled with thousands of direct log4j calls,
- migration to JDK 1.4 would be a relatively lengthy and
- error-prone process. Even worse, you would potentially need to
- maintain two versions of your CRM software. Had you been
- invoking SLF4J API instead of log4j, the migration could be
- completed in a matter of minutes by replacing one jar file with
- another.
- </p>
-
- <p>SLF4J lets component developers to defer the choice of the
- logging system to the end-user but eventually a choice needs
- to be made.
- </p>
-
-
-
- </dd>
-
- <dt class="doAnchor" name="yet_another_facade">Is SLF4J yet
- another logging facade?</dt>
-
- <dd>
- <p>SLF4J is conceptually very similar to JCL. As such, it can
- be thought of as yet another logging facade. However, SLF4J is
- much simpler in design and arguably more robust. In a
- nutshell, SLF4J avoid the class loader issues that plague JCL.
- </p>
-
-
-
- </dd>
- <dt class="doAnchor" name="why_new_project">If SLF4J fixes JCL,
- then why wasn't the fix made in JCL instead of creating a new
- project?
- </dt>
-
- <dd>
- <p>This is a very good question. First, SLF4J static binding
- approach is very simple, perhaps even laughably so. It was
- not easy to convince developers of the validity of that
- approach. It is only after SLF4J was released and started to
- become accepted did it gain respectability in the relevant
- community.
- </p>
-
- <p>Second, SLF4J offers two enhancements which tend to be
- underestimated. Parameterized log messages solve an important
- problem associated with logging performance, in a pragmatic
- way. Marker objects, which are supported by the
- <code>org.slf4j.Logger</code> interface, pave the way for
- adoption of advanced logging systems and still leave the door
- open to switching back to more traditional logging systems if
- need be.
- </p>
-
-
- </dd>
-
- <dt class="doAnchor" name="need_to_recompile">When using SLF4J, do
- I have to recompile my application to switch to a different
- logging system?
- </dt>
-
- <dd>
- <p>No, you do not need to recompile your application. You can
- switch to a different logging system by removing the previous
- SLF4J binding and replacing it with the binding of your choice.
- </p>
-
- <p>For example, if you were using the NOP implementation and
- would like to switch to log4j version 1.2, simply replace
- <em>slf4j-nop.jar</em> with <em>slf4j-log4j12.jar</em> on
- your class path but do not forget to add log4j-1.2.x.jar as
- well. Want to switch to JDK 1.4 logging? Just replace
- <em>slf4j-log4j12.jar</em> with <em>slf4j-jdk14.jar</em>.
- </p>
-
-
- </dd>
-
- <dt class="doAnchor" name="requirements">What are SLF4J's
- requirements?
- </dt>
-
- <dd>
-
- <p>As of version 1.7.0, SLF4J requires JDK 1.5 or later. Earlier
- SLF4J versions, namely SLF4J 1.4, 1.5. and 1.6, required JDK
- 1.4.
- </p>
-
- <p>&nbsp;</p>
-
- <table class="bodyTable striped">
- <tr align="left">
- <th>Binding</th>
- <th>Requirements</th>
- </tr>
-
- <tr>
- <td>slf4j-nop</td>
- <td>JDK 1.5</td>
- </tr>
- <tr>
- <td>slf4j-simple</td>
- <td>JDK 1.5</td>
- </tr>
-
- <tr>
- <td>slf4j-log4j12</td>
- <td align="left">JDK 1.5, plus any other library
- dependencies required by the log4j appenders in use</td>
- </tr>
- <tr>
- <td>slf4j-jdk14</td>
- <td>JDK 1.5 or later</td>
- </tr>
- <tr>
- <td>logback-classic</td>
- <td>JDK 1.5 or later, plus any other library dependencies
- required by the logback appenders in use</td>
- </tr>
-
- </table>
-
-
- </dd>
-
- <!-- ==================================================== -->
- <!-- entry has order dependees -->
-
- <dt class="doAnchor" name="compatibility">Are SLF4J versions
- backward compatible?
- </dt>
-
- <dd>
- <p>From the clients perspective, the SLF4J API is backward
- compatible for all versions. This means than you can upgrade
- from SLF4J version 1.0 to any later version without
- problems. Code compiled with <em>slf4j-api-versionN.jar</em>
- will work with <em>slf4j-api-versionM.jar</em> for any versionN
- and any versionM. <b>To date, binary compatibility in slf4j-api
- has never been broken.</b></p>
-
- <p>However, while the SLF4J API is very stable from the client's
- perspective, SLF4J bindings, e.g. slf4j-simple.jar or
- slf4j-log4j12.jar, may require a specific version of slf4j-api.
- Mixing different versions of slf4j artifacts can be problematic
- and is strongly discouraged. For instance, if you are using
- slf4j-api-1.5.6.jar, then you should also use
- slf4j-simple-1.5.6.jar, using slf4j-simple-1.4.2.jar will not
- work.
- </p>
-
- <p>At initialization time, if SLF4J suspects that there may be a
- version mismatch problem, it emits a warning about the said
- mismatch.
- </p>
-
-
- </dd>
-
- <!-- ==================================================== -->
-
- <dt class="doAnchor" name="IllegalAccessError">I am getting
- <code>IllegalAccessError</code> exceptions when using SLF4J. Why
- is that?
- </dt>
-
- <dd>
-
- <p>Here are the exception details.</p>
-
- <pre class="source">Exception in thread "main" java.lang.IllegalAccessError: tried to access field
-org.slf4j.impl.StaticLoggerBinder.SINGLETON from class org.slf4j.LoggerFactory
- at org.slf4j.LoggerFactory.&lt;clinit>(LoggerFactory.java:60)</pre>
-
- <p>This error is caused by the static initializer of the
- <code>LoggerFactory</code> class attempting to directly access
- the SINGLETON field of
- <code>org.slf4j.impl.StaticLoggerBinder</code>. While this was
- allowed in SLF4J 1.5.5 and earlier, in 1.5.6 and later the
- SINGLETON field has been marked as private access.
- </p>
-
-
- <p>If you get the exception shown above, then you are using an
- older version of slf4j-api, e.g. 1.4.3, with a new version of a
- slf4j binding, e.g. 1.5.6. Typically, this occurs when your
- Maven <em>pom.ml</em> file incorporates hibernate 3.3.0 which
- declares a dependency on slf4j-api version 1.4.2. If your
- <em>pom.xml</em> declares a dependency on an slf4j binding, say
- slf4j-log4j12 version 1.5.6, then you will get illegal access
- errors.
- </p>
-
- <p>To see which version of slf4j-api is pulled in by Maven, use
- the maven dependency plugin as follows.</p>
-
- <p class="source">mvn dependency:tree</p>
-
- <p>If you are using Eclipse, please do not rely on the dependency
- tree shown by <a
- href="http://m2eclipse.codehaus.org/">m2eclipse</a>.</p>
-
- <p>In your <em>pom.xml</em> file, explicitly declaring a
- dependency on slf4j-api matching the version of the declared
- binding will make the problem go away.
- </p>
-
- <p>Please also read the FAQ entry on <a
- href="#compatibility">backward compatibility</a> for a more
- general explanation.</p>
-
-
- </dd>
-
-
- <!-- ==================================================== -->
-
- <dt class="doAnchor" name="license">Why is SLF4J licensed under
- X11 type license instead of the Apache Software License?
- </dt>
-
- <dd>
- <p>SLF4J is licensed under a permissive X11 type license
- instead of the <a
- href="http://www.apache.org/licenses/">ASL</a> or the <a
- href="http://www.gnu.org/copyleft/lesser.html">LGPL</a>
- because the X11 license is deemed by both the Apache Software
- Foundation as well as the Free Software Foundation as
- compatible with their respective licenses.
- </p>
-
-
- </dd>
-
- <!-- ==================================================== -->
- <dt class="doAnchor" name="where_is_binding">Where can I get a
- particular SLF4J binding?
- </dt>
-
- <dd>
-
- <p>SLF4J bindings for <a
- href="api/org/slf4j/impl/SimpleLogger.html">SimpleLogger</a>,
- <a href="api/org/slf4j/impl/NOPLogger.html">NOPLogger</a>, <a
- href="api/org/slf4j/impl/Log4jLoggerAdapter.html">Log4jLoggerAdapter</a>
- and <a
- href="api/org/slf4j/impl/JDK14LoggerAdapter.html">JDK14LoggerAdapter</a>
- are contained within the files <em>slf4j-nop.jar</em>,
- <em>slf4j-simple.jar</em>, <em>slf4j-log4j12.jar</em>, and
- <em>slf4j-jdk14.jar</em>. These files ship with the <a
- href="download.html">official SLF4J distribution</a>. Please
- note that all bindings depend on <em>slf4j-api.jar</em>.
- </p>
-
- <p>The binding for logback-classic ships with the <a
- href="http://logback.qos.ch/download.html">logback
- distribution</a>. However, as with all other bindings, the
- logback-classic binding requires <em>slf4j-api.jar</em>.
- </p>
-
-
- </dd>
-
- <dt class="doAnchor" name="configure_logging">Should my library
- attempt to configure logging?
- </dt>
-
- <dd>
- <p><b>Embedded components such as libraries not only do not need
- to configure the underlying logging framework, they really
- should not do so</b>. They should invoke SLF4J to log but should
- let the end-user configure the logging environment. When
- embedded components try to configure logging on their own, they
- often override the end-user's wishes. At the end of the day, it
- is the end-user who has to read the logs and process them. She
- should be the person to decide how she wants her logging
- configured.
- </p>
-
-
- </dd>
-
- <!-- ======================================================= -->
-
- <dt class="doAnchor" name="optional_dependency">In order to reduce
- the number of dependencies of our software we would like to make
- SLF4J an optional dependency. Is that a good idea?
- </dt>
-
- <dd>
- <p><a
- href="http://stackoverflow.com/questions/978670/is-it-worth-wrapping-a-logging-framework-in-an-additional-layer">This
- question pops up</a> whenever a software project reaches a point
- where it needs to devise a logging strategy.
- </p>
-
- <p>Let Wombat be a software library with very few
- dependencies. If SLF4J is chosen as Wombat's logging API, then a
- new dependency on <em>slf4j-api.jar</em> will be added to
- Wombat's list of dependencies. Given that writing a logging
- wrapper does not seem that hard, some developers will be tempted
- to wrap SLF4J and link with it only if it is already present on
- the classpath, making SLF4J an optional dependency of Wombat. In
- addition to solving the dependency problem, the wrapper will
- isolate Wombat from SLF4J's API ensuring that logging in Wombat
- is future-proof.
- </p>
-
- <p>On the other hand, any SLF4J-wrapper by definition depends on
- SLF4J. It is bound to have the same general API. If in the
- future a new and significantly different logging API comes
- along, code that uses the wrapper will be equally difficult to
- migrate to the new API as code that used SLF4J directly. Thus,
- the wrapper is not likely to future-proof your code, but to make
- it more complex by adding an additional indirection on top of
- SLF4J, which is an indirection in itself.
- </p>
-
- <p><span class="label">increased vulnerability</span> It is
- actually worse than that. Wrappers will need to depend on
- certain internal SLF4J interfaces which change from time to
- time, contrary to the client-facing API which never
- changes. Thus, wrappers are usually dependent on the major
- version they were compiled with. A wrapper compiled against
- SLF4J version 1.5.x will not work with SLF4J 1.6 whereas client
- code using <code>org.slf4j.Logger</code>,
- <code>LoggerFactory</code>, <code>MarkerFactory</code>,
- <code>org.slf4j.Marker</code>, and <code>MDC</code> will work
- fine with any SLF4J version from version 1.0 and onwards.
- </p>
-
- <p>It is reasonable to assume that in most projects Wombat will
- be one dependency among many. If each library had its own
- logging wrapper, then each wrapper would presumably need to be
- configured separately. Thus, instead of having to deal with one
- logging framework, namely SLF4J, the user of Wombat would have
- to detail with Wombat's logging wrapper as well. The problem
- will be compounded by each framework that comes up with its own
- wrapper in order to make SLF4J optional. (Configuring or
- dealing with the intricacies of five different logging wrappers
- is not exactly exciting nor endearing.)
- </p>
-
- <p>The <a
- href="http://velocity.apache.org/engine/devel/developer-guide.html#Configuring_Logging">logging
- strategy adopted by the Velocity project</a> is a good example
- of the "custom logging abstraction" anti-pattern. By adopting an
- independent logging abstraction strategy, Velocity developers
- have made life harder for themselves, but more importantly, they
- made life harder for their users.
- </p>
-
- <p>Some projects try to detect the presence of SLF4J on the
- class path and switch to it if present. While this approach
- seems transparent enough, it will result in erroneous location
- information. Underlying logging frameworks will print the
- location (class name and line number) of the wrapper instead of
- the real caller. Then there is the question of API coverage as
- SLF4J support MDC and markers in addition to parameterized
- logging. While one can come up with a seemingly working
- SLF4J-wrapper within hours, many technical issues will emerge
- over time which Wombat developers will have to deal with. Note
- that SLF4J has evolved over several years and has 260 bug
- reports filed against it.</p>
-
- <p>For the above reasons, developers of frameworks should resist
- the temptation to write their own logging wrapper. Not only is
- it a waste of time of the developer, it will actually make life
- more difficult for the users of said frameworks and make logging
- code paradoxically more vulnerable to change.
- </p>
- </dd>
-
-
- <!-- ======================================================= -->
-
- <dt class="doAnchor" name="maven2">What about Maven transitive
- dependencies?
- </dt>
-
- <dd>
- <p>As an author of a library built with Maven, you might want to
- test your application using a binding, say slf4j-log4j12 or
- logback-classic, without forcing log4j or logback-classic as a
- dependency upon your users. This is rather easy to accomplish.
- </p>
-
- <p>Given that your library's code depends on the SLF4J API, you
- will need to declare slf4j-api as a compile-time (default scope)
- dependency.
- </p>
- <pre class="prettyprint source">&lt;dependency&gt;
- &lt;groupId&gt;org.slf4j&lt;/groupId&gt;
- &lt;artifactId&gt;slf4j-api&lt;/artifactId&gt;
- &lt;version&gt;${project.version}&lt;/version&gt;
-&lt;/dependency&gt;</pre>
-
- <p>Limiting the transitivity of the SLF4J binding used in your
- tests can be accomplished by declaring the scope of the
- SLF4J-binding dependency as "test". Here is an example:</p>
-
- <pre class="prettyprint source">&lt;dependency&gt;
- &lt;groupId&gt;org.slf4j&lt;/groupId&gt;
- &lt;artifactId&gt;slf4j-log4j12&lt;/artifactId&gt;
- &lt;version&gt;${project.version}&lt;/version&gt;
- <b>&lt;scope&gt;test&lt;/scope&gt;</b>
-&lt;/dependency&gt;</pre>
-
- <p>Thus, as far as your users are concerned you are exporting
- slf4j-api as a transitive dependency of your library, but not
- any SLF4J-binding or any underlying logging system.
- </p>
-
- <p>Note that as of SLF4J version 1.6, in the absence of an SLF4J
- binding, slf4j-api will default to a no-operation
- implementation.
- </p>
-
-
-
- </dd>
-
- <!-- ====================================================== -->
- <dt class="doAnchor" name="excludingJCL">How do I exclude
- commons-logging as a Maven dependency?
- </dt>
-
- <dd>
- <p><b>alternative 1) explicit exclusion</b></p>
-
- <p>Many software projects using Maven declare commons-logging as
- a dependency. Therefore, if you wish to migrate to SLF4J or use
- jcl-over-slf4j, you would need to exclude commons-logging in all
- of your project's dependencies which transitively depend on
- commons-logging. <a
- href="http://maven.apache.org/guides/introduction/introduction-to-optional-and-excludes-dependencies.html">Dependency
- exclusion</a> is described in the Maven documentation. Excluding
- commons-logging explicitly for multiple dependencies distributed
- on several <em>pom.xml</em> files can be a cumbersome and a
- relatively error prone process.
- </p>
-
- <p><b>alternative 2) provided scope</b></p>
-
- <p>Commons-logging can be rather simply and conveniently
- excluded as a dependency by declaring it in the
- <em>provided</em> scope within the pom.xml file of your
- project. The actual commons-logging classes would be provided by
- jcl-over-slf4j. This translates into the following pom file
- snippet:</p>
-
- <pre class="prettyprint source">&lt;dependency>
- &lt;groupId>commons-logging&lt;/groupId>
- &lt;artifactId>commons-logging&lt;/artifactId>
- &lt;version>1.1.1&lt;/version>
- &lt;scope>provided&lt;/scope>
-&lt;/dependency>
-
-&lt;dependency>
- &lt;groupId>org.slf4j&lt;/groupId>
- &lt;artifactId>jcl-over-slf4j&lt;/artifactId>
- &lt;version>${project.version}&lt;/version>
-&lt;/dependency></pre>
-
- <p>The first dependency declaration essentially states that
- commons-logging will be "somehow" provided by your
- environment. The second declaration includes jcl-over-slf4j into
- your project. As jcl-over-slf4j is a perfect binary-compatible
- replacement for commons-logging, the first assertion becomes
- true.
- </p>
-
- <p>Unfortunately, while declaring commons-logging in the
- provided scope gets the job done, your IDE, e.g. Eclipse, will
- still place <em>commons-logging.jar</em> on your project's class
- path as seen by your IDE. You would need to make sure that
- <em>jcl-over-slf4j.jar</em> is visible before
- <em>commons-logging.jar</em> by your IDE.
- </p>
-
- <p><b>alternative 3) empty artifacts</b></p>
-
- <p>An alternative approach is to depend on an <b>empty</b>
- <em>commons-logging.jar</em> artifact. This clever <a
- href="http://day-to-day-stuff.blogspot.com/2007/10/announcement-version-99-does-not-exist.html">approach
- first was imagined</a> and initially supported by Erik van
- Oosten.
- </p>
-
- <p>The empty artifact is available from a <a
- href="http://version99.qos.ch">http://version99.qos.ch</a> a
- high-availability Maven repository, replicated on several hosts
- located in different geographical regions.</p>
-
- <p>The following declaration adds the version99 repository to
- the set of remote repositories searched by Maven. This
- repository contains empty artifacts for commons-logging and
- log4j. By the way, if you use the version99 repository, please
- drop us a line at &lt;version99 AT qos.ch&gt;.
- </p>
-
- <pre class="prettyprint source">&lt;repositories>
- &lt;repository>
- &lt;id>version99&lt;/id>
- &lt;!-- highly available repository serving empty artifacts --&gt;
- &lt;url>http://version99.qos.ch/&lt;/url>
- &lt;/repository>
-&lt;/repositories></pre>
-
- <p>Declaring version 99-empty of commons-logging in the
- <code>&lt;dependencyManagement></code> section of your project
- will direct all transitive dependencies for commons-logging to
- import version 99-empty, thus nicely addressing the
- commons-logging exclusion problem. The classes for commons-logging
- will be provided by jcl-over-slf4j. The following lines declare
- commons-logging version 99-empty (in the dependency management
- section) and declare jcl-over-slf4j as a dependency.
- </p>
-
-<pre class="prettyprint source">&lt;dependencyManagement>
- &lt;dependencies>
- &lt;dependency>
- &lt;groupId>commons-logging&lt;/groupId>
- &lt;artifactId>commons-logging&lt;/artifactId>
- &lt;version><b>99-empty</b>&lt;/version>
- &lt;/dependency>
- ... other declarations...
- &lt;/dependencies>
-&lt;/dependencyManagement>
-
-&lt;!-- Do not forget to declare a dependency on jcl-over-slf4j in the --&gt;
-&lt;!-- dependencies section. Note that the dependency on commons-logging --&gt;
-&lt;!-- will be imported transitively. You don't have to declare it yourself. --&gt;
-&lt;dependencies>
- &lt;dependency>
- &lt;groupId>org.slf4j&lt;/groupId>
- &lt;artifactId>jcl-over-slf4j&lt;/artifactId>
- &lt;version>${project.version}&lt;/version>
- &lt;/dependency>
- ... other dependency declarations
-&lt;/dependencies>
-</pre>
-
-
- </dd>
-
-
-
- </dl>
-
-
- <h2>About the SLF4J API</h2>
-
- <dl>
-
- <dt class="doAnchor" name="string_or_object">Why don't the
- printing methods in the Logger interface accept message of type
- Object, but only messages of type String?
- </dt>
-
- <dd>
-
- <p>In SLF4J 1.0beta4, the printing methods such as debug(),
- info(), warn(), error() in the <a
- href="api/org/slf4j/Logger.html">Logger interface</a> were
- modified so as to accept only messages of type String
- instead of Object.
- </p>
-
- <p>Thus, the set of printing methods for the DEBUG level
- became:</p>
-
- <pre class="prettyprint source">debug(String msg);
-debug(String format, Object arg);
-debug(String format, Object arg1, Object arg2);
-debug(String msg, Throwable t);</pre>
-
- <p>Previously, the first argument in the above methods was of
- type <code>Object</code>.</p>
-
- <p>This change enforces the notion that logging systems are
- about decorating and handling messages of type String, and not
- any arbitrary type (Object).
- </p>
-
- <p>Just as importantly, the new set of method signatures offer
- a clearer differentiation between the overloaded methods
- whereas previously the choice of the invoked method due to
- Java overloading rules were not always easy to follow.</p>
-
- <p>It was also easy to make mistakes. For example, previously
- it was legal to write:</p>
-
- <pre class="prettyprint source">logger.debug(new Exception("some error"));</pre>
-
- <p>Unfortunately, the above call did not print the stack trace
- of the exception. Thus, a potentially crucial piece of
- information could be lost. When the first parameter is
- restricted to be of type String, then only the method
- </p>
-
- <pre class="prettyprint source">debug(String msg, Throwable t);</pre>
-
- <p>can be used to log exceptions. Note that this method
- ensures that every logged exception is accompanied with a
- descriptive message.</p>
-
-
- </dd>
-
- <!-- ====================================================== -->
-
- <dt class="doAnchor" name="exception_message">Can I log an
- exception without an accompanying message?
- </dt>
-
- <dd>
- <p>In short, no.</p>
-
- <p>If <code>e</code> is an <code>Exception</code>, and you
- would like to log an exception at the ERROR level, you must
- add an accompanying message. For example,</p>
-
- <pre class="prettyprint source">logger.error("some accompanying message", e);</pre>
-
- <p>You might legitimately argue that not all exceptions have a
- meaningful message to accompany them. Moreover, a good exception
- should already contain a self explanatory description. The
- accompanying message may therefore be considered redundant.
- </p>
-
-
- <p>While these are valid arguments, there are three opposing
- arguments also worth considering. First, on many, albeit not
- all occasions, the accompanying message can convey useful
- information nicely complementing the description contained
- in the exception. Frequently, at the point where the
- exception is logged, the developer has access to more
- contextual information than at the point where the exception
- is thrown. Second, it is not difficult to imagine more or
- less generic messages, e.g. "Exception caught", "Exception
- follows", that can be used as the first argument for
- <code>error(String msg, Throwable t)</code> invocations.
- Third, most log output formats display the message on a
- line, followed by the exception on a separate line. Thus,
- the message line would look inconsistent without a message.
- </p>
-
- <p>In short, if the user were allowed to log an exception
- without an accompanying message, it would be the job of the
- logging system to invent a message. This is actually what
- the <a href="http://tinyurl.com/cr9kg">throwing(String
- sourceClass, String sourceMethod, Throwable thrown)</a>
- method in java.util.logging package does. (It decides on its
- own that accompanying message is the string "THROW".)
- </p>
-
- <p>It may initially appear strange to require an accompanying
- message to log an exception. Nevertheless, this is common
- practice in <em>all</em> log4j derived systems such as
- java.util.logging, logkit, etc. and of course log4j itself. It
- seems that the current consensus considers requiring an
- accompanying message as a good a thing (TM).
- </p>
-
- </dd>
-
- <!-- ====================================================== -->
-
-
- <dt class="doAnchor" name="logging_performance">What is the
- fastest way of (not) logging?
- </dt>
-
- <dd>
- <p>SLF4J supports an advanced feature called parameterized
- logging which can significantly boost logging performance for
- <em>disabled</em> logging statement.</p>
-
- <p> For some Logger <code>logger</code>, writing,</p>
- <pre class="prettyprint source">logger.debug("Entry number: " + i + " is " + String.valueOf(entry[i]));</pre>
-
- <p>incurs the cost of constructing the message parameter, that
- is converting both integer <code>i</code> and
- <code>entry[i]</code> to a String, and concatenating
- intermediate strings. This, regardless of whether the message
- will be logged or not.
- </p>
-
- <p>One possible way to avoid the cost of parameter
- construction is by surrounding the log statement with a
- test. Here is an example.</p>
-
- <pre class="prettyprint source">if(logger.isDebugEnabled()) {
- logger.debug("Entry number: " + i + " is " + String.valueOf(entry[i]));
-}</pre>
-
-
- <p>This way you will not incur the cost of parameter
- construction if debugging is disabled for
- <code>logger</code>. On the other hand, if the logger is
- enabled for the DEBUG level, you will incur the cost of
- evaluating whether the logger is enabled or not, twice: once in
- <code>debugEnabled</code> and once in <code>debug</code>. This
- is an insignificant overhead because evaluating a logger takes
- less than 1% of the time it takes to actually log a statement.
- </p>
-
- <p><b>Better yet, use parameterized messages</b></p>
-
- <p>There exists a very convenient alternative based on message
- formats. Assuming <code>entry</code> is an object, you can write:
- </p>
-
-
- <pre class="prettyprint source">Object entry = new SomeObject();
-logger.debug("The entry is {}.", entry);</pre>
-
- <p>After evaluating whether to log or not, and only if the
- decision is affirmative, will the logger implementation format
- the message and replace the '{}' pair with the string value of
- <code>entry</code>. In other words, this form does not incur
- the cost of parameter construction in case the log statement is
- disabled.
- </p>
-
- <p>The following two lines will yield the exact same
- output. However, the second form will outperform the first
- form by a factor of at least 30, in case of a
- <em>disabled</em> logging statement.
- </p>
-
- <pre class="prettyprint source">logger.debug("The new entry is "+entry+".");
-logger.debug("The new entry is {}.", entry);</pre>
-
-
- <p>A <a
- href="apidocs/org/slf4j/Logger.html#debug(java.lang.String,%20java.lang.Object%2C%20java.lang.Object)">two
- argument</a> variant is also available. For example, you can
- write:</p>
-
-
- <pre class="prettyprint source">logger.debug("The new entry is {}. It replaces {}.", entry, oldEntry);</pre>
-
- <p>If three or more arguments need to be passed, you can make
- use of the <a
- href="apidocs/org/slf4j/Logger.html#debug(java.lang.String%2C%20java.lang.Object...)"><code>Object...</code>
- variant</a> of the printing methods. For example, you can
- write:</p>
-
- <pre class="prettyprint source">logger.debug("Value {} was inserted between {} and {}.", newVal, below, above);</pre>
-
- <p>This form incurs the hidden cost of construction of an
- Object[] (object array) which is usually very small. The one and
- two argument variants do not incur this hidden cost and exist
- solely for this reason (efficiency). The slf4j-api would be
- smaller/cleaner with only the Object... variant.</p>
-
-
- <p>Array type arguments, including multi-dimensional arrays,
- are also supported.</p>
-
- <p>SLF4J uses its own message formatting implementation which
- differs from that of the Java platform. This is justified by
- the fact that SLF4J's implementation performs about 10 times
- faster but at the cost of being non-standard and less
- flexible.
- </p>
-
- <p><b>Escaping the "{}" pair</b></p>
-
- <p>The "{}" pair is called the <em>formatting anchor</em>. It
- serves to designate the location where arguments need to be
- substituted within the message pattern.
- </p>
-
- <p>SLF4J only cares about the <em>formatting anchor</em>, that
- is the '{' character immediately followed by '}'. Thus, in
- case your message contains the '{' or the '}' character, you
- do not have to do anything special unless the '}' character
- immediately follows '}'. For example,
- </p>
-
- <pre class="prettyprint source">logger.debug("Set {1,2} differs from {}", "3");</pre>
-
- <p>which will print as "Set {1,2} differs from 3". </p>
-
- <p>You could have even written,</p>
- <pre class="prettyprint source">logger.debug("Set {1,2} differs from {{}}", "3");</pre>
- <p>which would have printed as "Set {1,2} differs from {3}". </p>
-
- <p>In the extremely rare case where the the "{}" pair occurs
- naturally within your text and you wish to disable the special
- meaning of the formatting anchor, then you need to escape the
- '{' character with '\', that is the backslash character. Only
- the '{' character should be escaped. There is no need to
- escape the '}' character. For example,
- </p>
-
- <pre class="prettyprint source">logger.debug("Set \\{} differs from {}", "3");</pre>
-
- <p>will print as "Set {} differs from 3". Note that within
- Java code, the backslash character needs to be written as
- '\\'.</p>
-
- <p>In the rare case where the "\{}" occurs naturally in the
- message, you can double escape the formatting anchor so that
- it retains its original meaning. For example,</p>
-
-
- <pre class="prettyprint source">logger.debug("File name is C:\\\\{}.", "file.zip");</pre>
- <p>will print as "File name is C:\file.zip".</p>
-
- </dd>
-
- <!-- ================================================= -->
-
- <dt class="doAnchor" name="string_contents">How can I log the
- string contents of a single (possibly complex) object?</dt>
-
- <dd>
- <p> In relatively rare cases where the message to be logged
- is the string form of an object, then the parameterized
- printing method of the appropriate level can be
- used. Assuming <code>complexObject</code> is an object of
- certain complexity, for a log statement of level DEBUG, you
- can write:
- </p>
-
- <pre class="prettyprint source">logger.debug("{}", complexObject);</pre>
-
-
- <p>The logging system will invoke
- <code>complexObject.toString()</code> method only after it
- has ascertained that the log statement was
- enabled. Otherwise, the cost of
- <code>complexObject.toString()</code> conversion will be
- advantageously avoided.
- </p>
-
-
-
- </dd>
-
- <!-- ================================================= -->
-
-
- <dt class="doAnchor" name="fatal">Why doesn't the
- <code>org.slf4j.Logger</code> interface have methods for the FATAL
- level?
- </dt>
-
- <dd>
- <p>The <a href="apidocs/org/slf4j/Marker.html">Marker</a>
- interface, part of the <code>org.slf4j</code> package, renders
- the FATAL level largely redundant. If a given error requires
- attention beyond that allocated for ordinary errors, simply mark
- the logging statement with a specially designated marker which
- can be named "FATAL" or any other name to your liking.
- </p>
-
- <p>Here is an example,</p>
-
-<pre class="prettyprint">import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.slf4j.Marker;
-import org.slf4j.MarkerFactory;
-
-class Bar {
- void foo() {
- <b>Marker fatal = MarkerFactory.getMarker("FATAL");</b>
- Logger logger = LoggerFactory.getLogger("aLogger");
-
- try {
- ... obtain a JDBC connection
- } catch (JDBException e) {
- logger.error(<b>fatal</b>, "Failed to obtain JDBC connection", e);
- }
- }
-}</pre>
-
-
- <p>While markers are part of the SLF4J API, only logback
- supports markers off the shelf. For example, if you add the
- <code>%marker</code> conversion word to its pattern, logback's
- <code>PatternLayout</code> will add marker data to its
- output. Marker data can be used to <a
- href="http://logback.qos.ch/manual/filters.html">filter
- messages</a> or even <a
- href="http://logback.qos.ch/manual/appenders.html#OnMarkerEvaluator">trigger</a>
- an outgoing email <a
- href="http://logback.qos.ch/recipes/emailPerTransaction.html">at
- the end of an individual transaction</a>.
- </p>
-
- <p>In combination with logging frameworks such as log4j and
- java.util.logging which do not support markers, marker data will
- be silently ignored.</p>
-
- <p>Markers add a new dimension with infinite possible values for
- processing log statements compared to five values, namely ERROR,
- WARN, INFO, DEBUG and TRACE, allowed by levels. At present time,
- only logback supports marker data. However, nothing prevents
- other logging frameworks from making use of marker data.
- </p>
-
- </dd>
-
- <!-- ======================================================= -->
- <dt class="doAnchor" name="trace">Why was the TRACE level
- introduced only in SLF4J version 1.4.0?</dt>
-
- <dd>
-
- <p>The addition of the TRACE level has been frequently and
- hotly debated request. By studying various projects, we
- observed that the TRACE level was used to disable logging
- output from certain classes <em>without</em> needing to
- configure logging for those classes. Indeed, the TRACE level
- is by default disabled in log4j and logback as well most other
- logging systems. The same result can be achieved by adding the
- appropriate directives in configuration files.
- </p>
-
- <p>Thus, in many of cases the TRACE level carried the same
- semantic meaning as DEBUG. In such cases, the TRACE level
- merely saves a few configuration directives. In other, more
- interesting occasions, where TRACE carries a different meaning
- than DEBUG, <a href="api/org/slf4j/Marker.html">Marker</a>
- objects can be put to use to convey the desired
- meaning. However, if you can't be bothered with markers and
- wish to use a logging level lower than DEBUG, the TRACE level
- can get the job done.
- </p>
-
- <p>Note that while the cost of evaluating a disabled log
- request is in the order of a few <code>nanoseconds</code>, the
- use of the TRACE level (or any other level for that matter) is
- discouraged in tight loops where the log request might be
- evaluated millions of times. If the log request is enabled,
- then it will overwhelm the target destination with massive
- output. If the request is disabled, it will waste resources.
- </p>
-
- <p>In short, although we still discourage the use of the TRACE
- level because alternatives exist or because in many cases log
- requests of level TRACE are wasteful, given that people kept
- asking for it, we decided to bow to popular demand.
- </p>
-
-
- </dd>
-
- <!-- ================================================= -->
- <dt class="doAnchor" name="i18n">Does the SLF4J logging API
- support I18N (internationalization)?
- </dt>
-
- <dd>
- <p>Yes, as of version 1.5.9, SLF4J ships with a package called
- <code>org.slf4j.cal10n</code> which adds <a
- href="localization.html">localized/internationalized logging</a>
- support as a thin layer built upon the <a
- href="http://cal10n.qos.ch">CAL10N API</a>.</p>
-
-
- </dd>
-
- <!-- ================================================= -->
-
- <dt class="doAnchor" name="noLoggerFactory">Is it possible to
- retrieve loggers without going through the static methods in
- <code>LoggerFactory</code>?
- </dt>
-
- <dd>
-
- <p>Yes. <code>LoggerFactory</code> is essentially a wrapper
- around an <a
- href="xref/org/slf4j/ILoggerFactory.html"><code>ILoggerFactory</code></a>
- instance. The <code>ILoggerFactory</code> instance in use is
- determined according to the static binding conventions of the
- SLF4J framework. See the <a
- href="xref/org/slf4j/LoggerFactory.html#217">getSingleton()</a>
- method in <code>LoggerFactory</code> for details.
- </p>
-
- <p>However, nothing prevents you from using your own
- <code>ILoggerFactory</code> instance. Note that you can also
- obtain a reference to the <code>ILoggerFactory</code> that the
- <code>LoggerFactory</code> class is using by invoking the <a
- href="apidocs/org/slf4j/LoggerFactory.html#getILoggerFactory()">
- <code>LoggerFactory.getILoggerFactory()</code></a> method.
- </p>
-
- <p>Thus, if SLF4J binding conventions do not fit your needs, or
- if you need additional flexibility, then do consider using the
- <code>ILoggerFactory</code> interface as an alternative to
- inventing your own logging API.</p>
- </dd>
-
- <!-- ================================================= -->
-
- <dt class="doAnchor" name="paramException">In the presence of an
- exception/throwable, is it possible to parameterize a logging
- statement?</dt>
-
-
- <dd>
- <p>Yes, as of SLF4J 1.6.0, but not in previous versions. The
- SLF4J API supports parametrization in the presence of an
- exception, assuming the exception is the last parameter. Thus,
- </p>
- <pre class="prettyprint">String s = "Hello world";
-try {
- Integer i = Integer.valueOf(s);
-} catch (NumberFormatException e) {
- logger.error("Failed to format {}", s, e);
-}</pre>
-
- <p>will print the <code>NumberFormatException</code> with its
- stack trace as expected. The java compiler will invoke the <a
- href="http://www.slf4j.org/apidocs/org/slf4j/Logger.html#error%28java.lang.String,%20java.lang.Object,%20java.lang.Object%29">error
- method taking a String and two Object arguments</a>. SLF4J, in
- accordance with the programmer's most probable intention, will
- interpret <code>NumberFormatException</code> instance as a
- throwable instead of an unused <code>Object</code> parameter. In
- SLF4J versions prior to 1.6.0, the
- <code>NumberFormatException</code> instance was simply ignored.
- </p>
-
- <p>If the exception is not the last argument, it will be treated
- as a plain object and its stack trace will NOT be printed.
- However, such situations should not occur in practice.
- </p>
-
- </dd>
- </dl>
-
-
-
- <h2>Implementing the SLF4J API</h2>
-
- <dl>
-
- <!-- ============================================================= -->
-
- <dt class="doAnchor" name="slf4j_compatible">How do I make my
- logging framework SLF4J compatible?
- </dt>
-
-
- <dd>
-
- <p>Adding supporting for the SLF4J is surprisingly
- easy. Essentially, you coping an existing binding and tailoring
- it a little (as explained below) does the trick.
- </p>
-
- <p>Assuming your logging system has notion of a
- logger, called say <code>MyLogger</code>, you need to provide
- an adapter for <code>MyLogger</code> to
- <code>org.slf4j.Logger</code> interface. Refer to slf4j-jcl,
- slf4j-jdk14, and slf4j-log4j12 modules for examples of
- adapters.
- </p>
-
- <p>Once you have written an appropriate adapter, say
- <code>MyLoggerAdapter</code>, you need to provide a factory
- class implementing the <code>org.slf4j.ILoggerFactory</code>
- interface. This factory should return instances
- <code>MyLoggerAdapter</code>. Let <code>MyLoggerFactory</code>
- be the name of your factory class.
- </p>
-
- <p>Once you have the adapter, namely
- <code>MyLoggerAdapter</code>, and a factory, namely
- <code>MyLoggerFactory</code>, the last remaining step is to
- modify the <code>StaticLoggerBinder</code> class so that it
- returns an new instance of <code>MyLoggerFactory</code>. You
- will also need to modify the
- <code>loggerFactoryClassStr</code> variable.
- </p>
-
- <p>For Marker or MDC support, you could use the one of the
- existing NOP implementations.
- </p>
-
- <p>In summary, to create an SLF4J binding for your logging
- system, follow these steps:</p>
-
- <ol>
- <li>start with a copy of an existing module,</li>
- <li>create an adapter between your logging system and
- <code>org.slf4j.Logger</code> interface
- </li>
- <li>create a factory for the adapter created in the previous step,</li>
- <li>modify <code>StaticLoggerBinder</code> class to use the
- factory you created in the previous step</li>
- </ol>
-
-
- </dd>
-
- <!-- ============================================================= -->
-
- <dt class="doAnchor" name="marker_interface">How can my logging
- system add support for the <code>Marker</code> interface?
- </dt>
- <dd>
-
- <p>Markers constitute a revolutionary concept which is
- supported by logback but not other existing logging
- systems. Consequently, SLF4J conforming logging systems are
- allowed to ignore marker data passed by the user.
- </p>
-
- <p>However, even though marker data may be ignored, the user
- must still be allowed to specify marker data. Otherwise, users
- would not be able to switch between logging systems that
- support markers and those that do not.
- </p>
-
- <p>The <code>MarkerIgnoringBase</code> class can serve as a
- base for adapters or native implementations of logging
- systems lacking marker support. In
- <code>MarkerIgnoringBase</code>, methods taking marker data
- simply invoke the corresponding method without the Marker
- argument, discarding any Marker data passed as
- argument. Your SLF4J adapters can extend
- <code>MarkerIgnoringBase</code> to quickly implement the
- methods in <code>org.slf4j.Logger</code> which take a
- <code>Marker</code> as the first argument.
- </p>
-
-
- </dd>
-
- <!-- ============================================================= -->
-
- <dt class="doAnchor" name="version_checks">How does SLF4J's
- version check mechanism work?
- </dt>
-
- <dd>
- <p>The version check performed by SLF4J API during its
- initialization is an <em>elective</em> process. Conforming SLF4J
- implementations may choose <em>not</em> to participate, in which
- case, no version check will be performed.
- </p>
-
- <p>However, if an SLF4J implementation decides to participate,
- than it needs to declare a variable called
- REQUESTED_API_VERSION within its copy of the
- <code>StaticLoggerBinder</code> class. The value of this
- variable should be equal to the version of the slf4j-api.jar
- it is compiled with. If the implementation is upgraded to a
- newer version of slf4j-api, than you also need to update the
- value of REQUESTED_API_VERSION.
- </p>
-
- <p>For each version, SLF4J API maintains a list of compatible
- versions. SLF4J will emit a version mismatch warning only if
- the requested version is not found in the compatibility
- list. So even if your SLF4J binding has a different release
- schedule than SLF4J, assuming you update the SLF4J version you
- use every 6 to 12 months, you can still participate in the
- version check without incurring a mismatch warning. For
- example, logback has a different release schedule but still
- participates in version checks.</p>
-
- <p><b>As of SLF4J 1.5.5</b>, all bindings shipped within the
- SLF4J distribution, e.g. slf4j-log4j12, slf4j-simple and
- slf4j-jdk14, declare the REQUESTED_API_VERSION field with a
- value equal to their SLF4J version. It follows that, for example
- if slf4j-simple-1.5.8.jar is mixed with slf4j-api-1.6.0.jar,
- given that 1.5.8 is not on the compatibility list of SLF4J
- version 1.6.x, a version mismatch warning will be issued.
- </p>
-
- <p>Note that SLF4J versions prior to 1.5.5 did not have a
- version check mechanism. Only slf4j-api-1.5.5.jar and later can
- emit version mismatch warnings.
- </p>
-
-
- </dd>
-
- </dl>
-
- <h2>General questions about logging</h2>
-
-
-
- <dl>
-
- <!-- ============================================================= -->
- <dt class="doAnchor" name="declared_static">Should Logger members
- of a class be declared as static?
- </dt>
- <dd>
-
- <p>We <code>used</code> to recommend that loggers members be
- declared as instance variables instead of static. After further
- analysis, <b>we no longer recommend one approach over the
- other.</b>
- </p>
-
- <p>Here is a summary of the pros and cons of each approach.
- </p>
-
- <table class="bodyTable">
- <tr valign="top">
- <th width="50%">Advantages for declaring loggers as static</th>
- <th width="50%">Disadvantages for declaring loggers as static</th>
- </tr>
- <tr valign="top" class="alt">
- <td>
- <ol>
- <li>common and well-established idiom</li>
- <li>less CPU overhead: loggers are retrieved and
- assigned only once, at hosting class
- initialization</li>
- <li>less memory overhead: logger declaration will
- consume one reference per class</li>
- </ol>
- </td>
-
- <td> <!-- static con -->
- <ol>
- <li>For libraries shared between applications, not
- possible to take advantage of repository selectors. It
- should be noted that if the SLF4J binding and the
- underlying API ships with each application (not shared
- between applications), then each application will still
- have its own logging environment.
- </li>
- <li>not IOC-friendly</li>
- </ol>
- </td>
- </tr>
-
- <tr>
- <th width="50%">Advantages for declaring loggers as instance variables</th>
- <th width="50%">Disadvantages for declaring loggers as
- instance variables</th>
- </tr>
-
- <tr class="alt" valign="top">
- <td> <!-- instance pros -->
- <ol>
- <li>Possible to take advantage of repository selectors
- even for libraries shared between applications. However,
- repository selectors only work if the underlying logging
- system is logback-classic. Repository selectors do not
- work for the SLF4J+log4j combination.
- </li>
- <li>IOC-friendly</li>
- </ol>
- </td>
-
- <td> <!-- instance cons -->
- <ol>
- <li>Less common idiom than declaring loggers as static
- variables</li>
-
- <li>higher CPU overhead: loggers are retrieved and
- assigned for each instance of the hosting class</li>
-
- <li>higher memory overhead: logger declaration will
- consume one reference per instance of the hosting class</li>
- </ol>
- </td>
- </tr>
- </table>
-
-
- <h3>Explanation</h3>
-
- <p>Static logger members cost a single variable reference for
- all instances of the class whereas an instance logger member
- will cost a variable reference for every instance of the
- class. For simple classes instantiated thousands of times
- there might be a noticeable difference.
- </p>
-
- <p>However, more recent logging systems, e.g log4j or logback,
- support a distinct logger context for each application running
- in the application server. Thus, even if a single copy of
- <em>log4j.jar</em> or <em>logback-classic.jar</em> is deployed
- in the server, the logging system will be able to differentiate
- between applications and offer a distinct logging environment
- for each application.
- </p>
-
- <p>More specifically, each time a logger is retrieved by
- invoking <code>LoggerFactory.getLogger()</code> method, the
- underlying logging system will return an instance appropriate
- for the current application. Please note that within the
- <em>same</em> application retrieving a logger by a given name
- will always return the same logger. For a given name, a
- different logger will be returned only for different
- applications.
- </p>
-
- <p>If the logger is static, then it will only be retrieved once
- when the hosting class is loaded into memory. If the hosting
- class is used in only in one application, there is not much to
- be concerned about. However, if the hosting class is shared
- between several applications, then all instances of the shared
- class will log into the context of the application which
- happened to first load the shared class into memory - hardly the
- behavior expected by the user.
- </p>
-
- <p>Unfortunately, for non-native implementations of the SLF4J
- API, namely with slf4j-log4j12, log4j's repository selector will
- not be able to do its job properly because slf4j-log4j12, a
- non-native SLF4J binding, will store logger instances in a map,
- short-circuiting context-dependent logger retrieval. For native
- SLF4J implementations, such as logback-classic, repository
- selectors will work as expected.
- </p>
-
- <p>The Apache Commons wiki contains an <a
- href="http://wiki.apache.org/jakarta-commons/Logging/StaticLog">informative
- article</a> covering the same question.</p>
-
- <p><b>Logger serialization</b></p>
-
- <p>Contrary to static variables, instance variables are
- serialized by default. As of SLF4J version 1.5.3, logger
- instances survive serialization. Thus, serialization of the host
- class no longer requires any special action, even when loggers
- are declared as instance variables. In previous versions, logger
- instances needed to be declared as <code>transient</code> in the
- host class. </p>
-
- <p><b>Summary</b></p>
-
- <p>In summary, declaring logger members as static variables
- requires less CPU time and have a slightly smaller memory
- footprint. On the other hand, declaring logger members as
- instance variables requires more CPU time and have a slightly
- higher memory overhead. However, instance variables make it
- possible to create a distinct logger environment for each
- application, even for loggers declared in shared
- libraries. Perhaps more important than previously mentioned
- considerations, instance variables are IOC-friendly whereas
- static variables are not.
- </p>
-
- <p>See also <a
- href="http://wiki.apache.org/jakarta-commons/Logging/StaticLog">related
- discussion</a> in the commons-logging wiki.
- </p>
-
- </dd>
- </dl>
-
- <!-- ============================================================= -->
- <dl>
- <dt class="doAnchor" name="declaration_pattern">Is there a
- recommended idiom for declaring a logger in a class?
- </dt>
-
- <dd>
- <p>The following is the recommended logger declaration
- idiom. For reasons <a href="#declared_static">explained
- above</a>, it is left to the user to determine whether loggers
- are declared as static variables or not.</p>
-
- <pre class="prettyprint source">package some.package;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class MyClass {
- <b>final (static) Logger logger = LoggerFactory.getLogger(MyClass.class);</b>
- ... etc
-}</pre>
-
- <p>Unfortunately, give that the name of the hosting class is
- part of the logger declaration, the above logger declaration
- idiom is not is <em>not</em> resistant to cut-and-pasting
- between classes.
- </p>
- </dd>
- </dl>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/inde_base.html b/slf4j-site/src/site/pages/inde_base.html
deleted file mode 100644
index 2addd7b4..00000000
--- a/slf4j-site/src/site/pages/inde_base.html
+++ /dev/null
@@ -1,28 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/2000/REC-xhtml1-20000126/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
-<meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
-<title>SLF4J</title>
-<link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
-</head>
-<body>
- <script>
-prefix='';
-</script>
-
-<script src="templates/header.js"></script>
-<div id="left">
- <script src="templates/left.js"></script>
-</div>
-<div id="right">
- <script src="templates/right.js"></script>
-</div>
-<div id="content">
-
-
-
-
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/index.html b/slf4j-site/src/site/pages/index.html
deleted file mode 100755
index b684a9fd..00000000
--- a/slf4j-site/src/site/pages/index.html
+++ /dev/null
@@ -1,170 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
-
- <script type="text/javascript">prefix='';</script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <noscript>Please turn on Javascript to view this menu</noscript>
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <!--
- <div id="right">
- <script src="templates/right.js" type="text/javascript"></script>
- </div>
- -->
- <div id="content">
-
-
- <h1>Simple Logging Facade for Java (SLF4J)</h1>
-
- <p>The Simple Logging Facade for Java (SLF4J) serves as a simple
- facade or abstraction for various logging frameworks
- (e.g. java.util.logging, logback, log4j) allowing the end user to
- plug in the desired logging framework at <em>deployment</em>
- time. </p>
-
- <p>Before you start using SLF4J, we highly recommend that you read
- the two-page <a href="manual.html">SLF4J user manual</a>.
- </p>
-
- <p>Note that SLF4J-enabling your library implies the addition of
- only a single mandatory dependency, namely <em>slf4j-api.jar</em>.
- If no binding is found on the class path, then SLF4J will default to
- a no-operation implementation.
- </p>
-
- <p>In case you wish to migrate your Java source files to SLF4J,
- consider our <a href="migrator.html">migrator tool</a> which can
- migrate your project to use the SLF4J API in just a few minutes.</p>
-
- <p>In case an externally-maintained component you depend on uses a
- logging API other than SLF4J, such as commons logging, log4j or
- java.util.logging, have a look at SLF4J's binary-support for <a
- href="legacy.html">legacy APIs</a>.
- </p>
-
- <h3>Projects depending on SLF4J</h3>
-
- <p>Here is a non-exhaustive list of projects known to depend on
- SLF4J, in alphabetical order:
- </p>
-
- <table border="0">
- <tr>
- <td valign="top">
- <ul>
- <li><a href="http://activemq.apache.org/">Apache ActiveMQ</a></li>
- <li><a href="http://arhiva.apache.org/">Apache Archiva</a></li>
- <li><a href="http://camel.apache.org/">Apache Camel</a></li>
- <li><a href="http://directory.apache.org/">Apache Directory</a></li>
- <li><a href="http://mina.apache.org/ftpserver/">Apache FTPServer</a></li>
- <li><a href="http://geronimo.apache.org/">Apache Geronimo</a></li>
- <li><a href="http://incubator.apache.org/graffito/">Apache Graffito</a></li>
- <li><a href="http://jackrabbit.apache.org/">Apache Jackrabbit</a></li>
- <li><a href="http://mina.apache.org/">Apache Mina</a></li>
- <li><a href="http://cwiki.apache.org/qpid/">Apache Qpid</a></li>
- <li><a href="http://servicemix.apache.org/">Apache ServiceMix</a></li>
- </ul>
- </td>
-
- <td valign="top">
- <ul>
- <li><a href="http://incubator.apache.org/sling/site/index.html">Apache Sling</a></li>
- <li><a href="http://lucene.apache.org/solr/">Apache Solr</a></li>
- <li><a href="http://tapestry.apache.org/">Apache Tapestry</a></li>
- <li><a href="http://incubator.apache.org/wicket/">Apache Wicket</a></li>
- <li><a href="http://aperture.sourceforge.net/">Aperture</a></li>
- <li><a href="http://apogee.nuxeo.org/">Apogee</a></li>
- <li><a href="http://www.jfrog.org/sites/artifactory/latest/">Artifactory</a></li>
- <li><a href="http://docs.safehaus.org/display/ASYNCWEB/Home">AsyncWeb</a></li>
- <li><a href="http://www.bitronix.be/">Bitronix</a></li>
- <li><a href="http://www.dbunit.org/">DbUnit</a></li>
- <li><a href="http://displaytag.sourceforge.net/11/">Display tag</a></li>
-
- </ul>
-
- </td>
-
- <td valign="top">
- <ul>
- <li><a href="http://ehcache.org/">Ehcache</a></li>
- <li><a href="http://groovy.codehaus.org/GMaven">GMaven</a></li>
- <li><a href="http://www.gradle.org/">Gradle</a></li>
- <li><a href="http://www.icegreen.com/greenmail/">GreenMail</a></li>
- <li><a href="http://gumtree.codehaus.org/">GumTree</a></li>
- <li><a href="http://www.h2database.com/">H2 Database</a></li>
- <li><a href="http://ha-jdbc.sourceforge.net/">HA-JDBC</a></li>
- <li><a href="http://www.hibernate.org/">Hibernate</a></li>
- <li><a href="http://code.google.com/p/igenko/">Igenko</a></li>
- <li><a href="http://jabsorb.org/">Jabsorb</a></li>
- <li><a href="http://jetty.mortbay.org/">Jetty v6</a></li>
- </ul>
- </td>
- </tr>
-
- <tr>
-
- <td valign="top">
- <ul>
- <li><a href="http://www.topmind.biz/html/index.php">jLynx</a></li>
- <li><a href="http://code.google.com/p/jmesa/">JMesa</a></li>
- <li><a href="http://www.artofsolving.com/opensource/jodconverter">JODConverter</a></li>
- <li><a href="http://jtrac.info/dependencies.html">JTrac</a></li>
- <li><a href="http://jwebunit.sourceforge.net/2.x/">JWebUnit 2.x</a></li>
- <li><a href="http://www.jquantlib.org/index.php/Main_Page">JQuantLib</a></li>
- <li><a href="http://www.liferay.com/web/guest/home">LIFERAY</a></li>
- <li><a href="http://liftweb.net/">Lift</a></li>
- <li><a href="http://log4jdbc.sourceforge.net">log4jdbc</a></li>
- <li><a href="http://www.magnolia.info/en/magnolia.html">Magnolia</a></li>
- <li><a href="http://mrcp4j.sourceforge.net/">MRCP4J</a></li>
- </ul>
- </td>
-
-
- <td valign="top">
- <ul>
- <li><a href="http://www.mindquarry.com/">Mindquarry</a></li>
- <li><a href="http://mugshot.org/">Mugshot</a></li>
- <li><a href="http://mule.codehaus.org/display/MULE/Home">Mule</a></li>
- <li><a href="http://nexus.sonatype.org/repository.html">Nexus</a></li>
- <li><a href="http://www.novocode.com/naf/">Novocode</a></li>
- <li><a href="http://www.unidata.ucar.edu/software/netcdf-java/">NetCDF</a></li>
- <li><a href="http://code.google.com/p/openmeetings/">OpenMeetings</a></li>
- <li><a href="http://www.openrdf.org/">OpenRDF</a></li>
- <li><a href="http://docs.safehaus.org/display/PENROSE/Home">Penrose</a></li>
- <li><a href="http://pzfilereader.sourceforge.net/">PZFileReader</a></li>
- <li><a href="http://www.quartz-scheduler.org/">Quartz Scheduler</a></li>
- </ul>
- </td>
-
- <td valign="top">
- <ul>
- <li><a href="http://www.quickfixj.org/">QuickFIX/J</a></li>
- <li><a href="http://sonar.codehaus.org/">Sonar</a></li>
- <li><a href="http://smsj.sourceforge.net/dependencies.html">SMSJ</a></li>
- <li><a href="http://www.springframework.org/osgi">Spring-OSGi</a></li>
- <li><a href="http://static.springsource.org/s2-dmserver/2.0.x/user-guide/htmlsingle/user-guide.html">SpringSource dm Server&#8482;</a></li>
- <li><a href="http://streambase.com/">StreamBase</a></li>
- <li><a href="http://www.timefinder.de/">TimeFinder</a></li>
- <li><a href="http://www.wtfigo.org/index.html">WTFIGO</a></li>
- <li><a href="http://yaslibrary.sourceforge.net/index.shtml">YASL</a></li>
- <li><a href="http://xooctory.xoocode.org/">Xooctory</a></li>
- <li><a href="http://xwiki.org">XWiki</a></li>
- </ul>
- </td>
- </tr>
- </table>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/js/decorator.js b/slf4j-site/src/site/pages/js/decorator.js
deleted file mode 100644
index 362712eb..00000000
--- a/slf4j-site/src/site/pages/js/decorator.js
+++ /dev/null
@@ -1,101 +0,0 @@
-
-
-// <h3><a name="LoggerContext" href="#LoggerContext"><span
-// class="anchor"/></a>Logger context</h3>
-
-function decorate() {
- var anchor = findAnchorInURL(document.URL);
- decoratePropertiesInTables(anchor);
- decorateDoAnchor(anchor);
- decorateConversionWordInTables(anchor);
-}
-
-// ----------------------------------------------
-function findAnchorInURL(url) {
-
- if(url == null) return null
- var index = url.lastIndexOf("#");
- if(index != -1 && (index+1) < url.length)
- return url.substr(index+1);
- else
- return null;
-}
-
-// ----------------------------------------------
-function decoratePropertiesInTables(anchor) {
-
- //if(1==1) return;
- var elems = $('tr td:first-child span.prop');
-
- for(var i = 0; i < elems.length; i++) {
- var e = elems[i];
- var p = e.parentNode;
- if(p == null) continue;
-
- var tmpHTML = p.innerHTML;
- var propName = e.innerHTML;
- var nameAttr = $(e).attr('name')
-
- if(nameAttr == null) {
- var containerAttr = $(e).attr('container')
- if(containerAttr != null)
- nameAttr = containerAttr+capitaliseFirstLetter(propName);
- else
- nameAttr = propName;
- }
-
- p.innerHTML = "<a name='" + nameAttr + "' href='#" + nameAttr +
- "'><span class='anchor'/></a><b>" +tmpHTML +"</b>";
- scrollIfMatch(p, nameAttr, anchor);
- } // for
-}
-
-function decorateConversionWordInTables(anchor) {
- var elems = $('tr td.word');
- for(var i = 0; i < elems.length; i++) {
- var e = elems[i];
- var tmpHTML = e.innerHTML;
- var nameAttr = $(e).attr('name')
- if(nameAttr == null)
- continue;
- e.innerHTML = "<a name='" + nameAttr + "' href='#" + nameAttr +
- "'><span class='anchor'/></a>" +tmpHTML;
- scrollIfMatch(e, nameAttr, anchor);
- }
-}
-
-
-function decorateDoAnchor(anchor) {
- var elems = $('.doAnchor');
- for(var i = 0; i < elems.length; i++) {
- var e = elems[i];
- var tmpHTML = e.innerHTML;
- var nameAttr = $(e).attr('name')
- if(nameAttr == null) {
- nameAttr = camelCase($.trim(tmpHTML))
- }
- e.innerHTML = "<a name='" + nameAttr + "' href='#" + nameAttr +
- "'><span class='anchor'/></a>" +tmpHTML;
- scrollIfMatch(e, nameAttr, anchor);
- }
-}
-
-function scrollIfMatch(element, nameAttr, anchor) {
- if(anchor != null && nameAttr.toString() == anchor)
- element.scrollIntoView(true);
-
-
-}
-
-function capitaliseFirstLetter(str) {
- return str.charAt(0).toUpperCase() + str.slice(1);
-}
-
-
-function camelCase(str) {
- var res = str.trim().replace(/\s\w/g, function(match) {
- return match.trim().toUpperCase();
- });
- return res;
-}
-
diff --git a/slf4j-site/src/site/pages/js/jquery-min.js b/slf4j-site/src/site/pages/js/jquery-min.js
deleted file mode 100644
index 16ad06c5..00000000
--- a/slf4j-site/src/site/pages/js/jquery-min.js
+++ /dev/null
@@ -1,4 +0,0 @@
-/*! jQuery v1.7.2 jquery.com | jquery.org/license */
-(function(a,b){function cy(a){return f.isWindow(a)?a:a.nodeType===9?a.defaultView||a.parentWindow:!1}function cu(a){if(!cj[a]){var b=c.body,d=f("<"+a+">").appendTo(b),e=d.css("display");d.remove();if(e==="none"||e===""){ck||(ck=c.createElement("iframe"),ck.frameBorder=ck.width=ck.height=0),b.appendChild(ck);if(!cl||!ck.createElement)cl=(ck.contentWindow||ck.contentDocument).document,cl.write((f.support.boxModel?"<!doctype html>":"")+"<html><body>"),cl.close();d=cl.createElement(a),cl.body.appendChild(d),e=f.css(d,"display"),b.removeChild(ck)}cj[a]=e}return cj[a]}function ct(a,b){var c={};f.each(cp.concat.apply([],cp.slice(0,b)),function(){c[this]=a});return c}function cs(){cq=b}function cr(){setTimeout(cs,0);return cq=f.now()}function ci(){try{return new a.ActiveXObject("Microsoft.XMLHTTP")}catch(b){}}function ch(){try{return new a.XMLHttpRequest}catch(b){}}function cb(a,c){a.dataFilter&&(c=a.dataFilter(c,a.dataType));var d=a.dataTypes,e={},g,h,i=d.length,j,k=d[0],l,m,n,o,p;for(g=1;g<i;g++){if(g===1)for(h in a.converters)typeof h=="string"&&(e[h.toLowerCase()]=a.converters[h]);l=k,k=d[g];if(k==="*")k=l;else if(l!=="*"&&l!==k){m=l+" "+k,n=e[m]||e["* "+k];if(!n){p=b;for(o in e){j=o.split(" ");if(j[0]===l||j[0]==="*"){p=e[j[1]+" "+k];if(p){o=e[o],o===!0?n=p:p===!0&&(n=o);break}}}}!n&&!p&&f.error("No conversion from "+m.replace(" "," to ")),n!==!0&&(c=n?n(c):p(o(c)))}}return c}function ca(a,c,d){var e=a.contents,f=a.dataTypes,g=a.responseFields,h,i,j,k;for(i in g)i in d&&(c[g[i]]=d[i]);while(f[0]==="*")f.shift(),h===b&&(h=a.mimeType||c.getResponseHeader("content-type"));if(h)for(i in e)if(e[i]&&e[i].test(h)){f.unshift(i);break}if(f[0]in d)j=f[0];else{for(i in d){if(!f[0]||a.converters[i+" "+f[0]]){j=i;break}k||(k=i)}j=j||k}if(j){j!==f[0]&&f.unshift(j);return d[j]}}function b_(a,b,c,d){if(f.isArray(b))f.each(b,function(b,e){c||bD.test(a)?d(a,e):b_(a+"["+(typeof e=="object"?b:"")+"]",e,c,d)});else if(!c&&f.type(b)==="object")for(var e in b)b_(a+"["+e+"]",b[e],c,d);else d(a,b)}function b$(a,c){var d,e,g=f.ajaxSettings.flatOptions||{};for(d in c)c[d]!==b&&((g[d]?a:e||(e={}))[d]=c[d]);e&&f.extend(!0,a,e)}function bZ(a,c,d,e,f,g){f=f||c.dataTypes[0],g=g||{},g[f]=!0;var h=a[f],i=0,j=h?h.length:0,k=a===bS,l;for(;i<j&&(k||!l);i++)l=h[i](c,d,e),typeof l=="string"&&(!k||g[l]?l=b:(c.dataTypes.unshift(l),l=bZ(a,c,d,e,l,g)));(k||!l)&&!g["*"]&&(l=bZ(a,c,d,e,"*",g));return l}function bY(a){return function(b,c){typeof b!="string"&&(c=b,b="*");if(f.isFunction(c)){var d=b.toLowerCase().split(bO),e=0,g=d.length,h,i,j;for(;e<g;e++)h=d[e],j=/^\+/.test(h),j&&(h=h.substr(1)||"*"),i=a[h]=a[h]||[],i[j?"unshift":"push"](c)}}}function bB(a,b,c){var d=b==="width"?a.offsetWidth:a.offsetHeight,e=b==="width"?1:0,g=4;if(d>0){if(c!=="border")for(;e<g;e+=2)c||(d-=parseFloat(f.css(a,"padding"+bx[e]))||0),c==="margin"?d+=parseFloat(f.css(a,c+bx[e]))||0:d-=parseFloat(f.css(a,"border"+bx[e]+"Width"))||0;return d+"px"}d=by(a,b);if(d<0||d==null)d=a.style[b];if(bt.test(d))return d;d=parseFloat(d)||0;if(c)for(;e<g;e+=2)d+=parseFloat(f.css(a,"padding"+bx[e]))||0,c!=="padding"&&(d+=parseFloat(f.css(a,"border"+bx[e]+"Width"))||0),c==="margin"&&(d+=parseFloat(f.css(a,c+bx[e]))||0);return d+"px"}function bo(a){var b=c.createElement("div");bh.appendChild(b),b.innerHTML=a.outerHTML;return b.firstChild}function bn(a){var b=(a.nodeName||"").toLowerCase();b==="input"?bm(a):b!=="script"&&typeof a.getElementsByTagName!="undefined"&&f.grep(a.getElementsByTagName("input"),bm)}function bm(a){if(a.type==="checkbox"||a.type==="radio")a.defaultChecked=a.checked}function bl(a){return typeof a.getElementsByTagName!="undefined"?a.getElementsByTagName("*"):typeof a.querySelectorAll!="undefined"?a.querySelectorAll("*"):[]}function bk(a,b){var c;b.nodeType===1&&(b.clearAttributes&&b.clearAttributes(),b.mergeAttributes&&b.mergeAttributes(a),c=b.nodeName.toLowerCase(),c==="object"?b.outerHTML=a.outerHTML:c!=="input"||a.type!=="checkbox"&&a.type!=="radio"?c==="option"?b.selected=a.defaultSelected:c==="input"||c==="textarea"?b.defaultValue=a.defaultValue:c==="script"&&b.text!==a.text&&(b.text=a.text):(a.checked&&(b.defaultChecked=b.checked=a.checked),b.value!==a.value&&(b.value=a.value)),b.removeAttribute(f.expando),b.removeAttribute("_submit_attached"),b.removeAttribute("_change_attached"))}function bj(a,b){if(b.nodeType===1&&!!f.hasData(a)){var c,d,e,g=f._data(a),h=f._data(b,g),i=g.events;if(i){delete h.handle,h.events={};for(c in i)for(d=0,e=i[c].length;d<e;d++)f.event.add(b,c,i[c][d])}h.data&&(h.data=f.extend({},h.data))}}function bi(a,b){return f.nodeName(a,"table")?a.getElementsByTagName("tbody")[0]||a.appendChild(a.ownerDocument.createElement("tbody")):a}function U(a){var b=V.split("|"),c=a.createDocumentFragment();if(c.createElement)while(b.length)c.createElement(b.pop());return c}function T(a,b,c){b=b||0;if(f.isFunction(b))return f.grep(a,function(a,d){var e=!!b.call(a,d,a);return e===c});if(b.nodeType)return f.grep(a,function(a,d){return a===b===c});if(typeof b=="string"){var d=f.grep(a,function(a){return a.nodeType===1});if(O.test(b))return f.filter(b,d,!c);b=f.filter(b,d)}return f.grep(a,function(a,d){return f.inArray(a,b)>=0===c})}function S(a){return!a||!a.parentNode||a.parentNode.nodeType===11}function K(){return!0}function J(){return!1}function n(a,b,c){var d=b+"defer",e=b+"queue",g=b+"mark",h=f._data(a,d);h&&(c==="queue"||!f._data(a,e))&&(c==="mark"||!f._data(a,g))&&setTimeout(function(){!f._data(a,e)&&!f._data(a,g)&&(f.removeData(a,d,!0),h.fire())},0)}function m(a){for(var b in a){if(b==="data"&&f.isEmptyObject(a[b]))continue;if(b!=="toJSON")return!1}return!0}function l(a,c,d){if(d===b&&a.nodeType===1){var e="data-"+c.replace(k,"-$1").toLowerCase();d=a.getAttribute(e);if(typeof d=="string"){try{d=d==="true"?!0:d==="false"?!1:d==="null"?null:f.isNumeric(d)?+d:j.test(d)?f.parseJSON(d):d}catch(g){}f.data(a,c,d)}else d=b}return d}function h(a){var b=g[a]={},c,d;a=a.split(/\s+/);for(c=0,d=a.length;c<d;c++)b[a[c]]=!0;return b}var c=a.document,d=a.navigator,e=a.location,f=function(){function J(){if(!e.isReady){try{c.documentElement.doScroll("left")}catch(a){setTimeout(J,1);return}e.ready()}}var e=function(a,b){return new e.fn.init(a,b,h)},f=a.jQuery,g=a.$,h,i=/^(?:[^#<]*(<[\w\W]+>)[^>]*$|#([\w\-]*)$)/,j=/\S/,k=/^\s+/,l=/\s+$/,m=/^<(\w+)\s*\/?>(?:<\/\1>)?$/,n=/^[\],:{}\s]*$/,o=/\\(?:["\\\/bfnrt]|u[0-9a-fA-F]{4})/g,p=/"[^"\\\n\r]*"|true|false|null|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?/g,q=/(?:^|:|,)(?:\s*\[)+/g,r=/(webkit)[ \/]([\w.]+)/,s=/(opera)(?:.*version)?[ \/]([\w.]+)/,t=/(msie) ([\w.]+)/,u=/(mozilla)(?:.*? rv:([\w.]+))?/,v=/-([a-z]|[0-9])/ig,w=/^-ms-/,x=function(a,b){return(b+"").toUpperCase()},y=d.userAgent,z,A,B,C=Object.prototype.toString,D=Object.prototype.hasOwnProperty,E=Array.prototype.push,F=Array.prototype.slice,G=String.prototype.trim,H=Array.prototype.indexOf,I={};e.fn=e.prototype={constructor:e,init:function(a,d,f){var g,h,j,k;if(!a)return this;if(a.nodeType){this.context=this[0]=a,this.length=1;return this}if(a==="body"&&!d&&c.body){this.context=c,this[0]=c.body,this.selector=a,this.length=1;return this}if(typeof a=="string"){a.charAt(0)!=="<"||a.charAt(a.length-1)!==">"||a.length<3?g=i.exec(a):g=[null,a,null];if(g&&(g[1]||!d)){if(g[1]){d=d instanceof e?d[0]:d,k=d?d.ownerDocument||d:c,j=m.exec(a),j?e.isPlainObject(d)?(a=[c.createElement(j[1])],e.fn.attr.call(a,d,!0)):a=[k.createElement(j[1])]:(j=e.buildFragment([g[1]],[k]),a=(j.cacheable?e.clone(j.fragment):j.fragment).childNodes);return e.merge(this,a)}h=c.getElementById(g[2]);if(h&&h.parentNode){if(h.id!==g[2])return f.find(a);this.length=1,this[0]=h}this.context=c,this.selector=a;return this}return!d||d.jquery?(d||f).find(a):this.constructor(d).find(a)}if(e.isFunction(a))return f.ready(a);a.selector!==b&&(this.selector=a.selector,this.context=a.context);return e.makeArray(a,this)},selector:"",jquery:"1.7.2",length:0,size:function(){return this.length},toArray:function(){return F.call(this,0)},get:function(a){return a==null?this.toArray():a<0?this[this.length+a]:this[a]},pushStack:function(a,b,c){var d=this.constructor();e.isArray(a)?E.apply(d,a):e.merge(d,a),d.prevObject=this,d.context=this.context,b==="find"?d.selector=this.selector+(this.selector?" ":"")+c:b&&(d.selector=this.selector+"."+b+"("+c+")");return d},each:function(a,b){return e.each(this,a,b)},ready:function(a){e.bindReady(),A.add(a);return this},eq:function(a){a=+a;return a===-1?this.slice(a):this.slice(a,a+1)},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},slice:function(){return this.pushStack(F.apply(this,arguments),"slice",F.call(arguments).join(","))},map:function(a){return this.pushStack(e.map(this,function(b,c){return a.call(b,c,b)}))},end:function(){return this.prevObject||this.constructor(null)},push:E,sort:[].sort,splice:[].splice},e.fn.init.prototype=e.fn,e.extend=e.fn.extend=function(){var a,c,d,f,g,h,i=arguments[0]||{},j=1,k=arguments.length,l=!1;typeof i=="boolean"&&(l=i,i=arguments[1]||{},j=2),typeof i!="object"&&!e.isFunction(i)&&(i={}),k===j&&(i=this,--j);for(;j<k;j++)if((a=arguments[j])!=null)for(c in a){d=i[c],f=a[c];if(i===f)continue;l&&f&&(e.isPlainObject(f)||(g=e.isArray(f)))?(g?(g=!1,h=d&&e.isArray(d)?d:[]):h=d&&e.isPlainObject(d)?d:{},i[c]=e.extend(l,h,f)):f!==b&&(i[c]=f)}return i},e.extend({noConflict:function(b){a.$===e&&(a.$=g),b&&a.jQuery===e&&(a.jQuery=f);return e},isReady:!1,readyWait:1,holdReady:function(a){a?e.readyWait++:e.ready(!0)},ready:function(a){if(a===!0&&!--e.readyWait||a!==!0&&!e.isReady){if(!c.body)return setTimeout(e.ready,1);e.isReady=!0;if(a!==!0&&--e.readyWait>0)return;A.fireWith(c,[e]),e.fn.trigger&&e(c).trigger("ready").off("ready")}},bindReady:function(){if(!A){A=e.Callbacks("once memory");if(c.readyState==="complete")return setTimeout(e.ready,1);if(c.addEventListener)c.addEventListener("DOMContentLoaded",B,!1),a.addEventListener("load",e.ready,!1);else if(c.attachEvent){c.attachEvent("onreadystatechange",B),a.attachEvent("onload",e.ready);var b=!1;try{b=a.frameElement==null}catch(d){}c.documentElement.doScroll&&b&&J()}}},isFunction:function(a){return e.type(a)==="function"},isArray:Array.isArray||function(a){return e.type(a)==="array"},isWindow:function(a){return a!=null&&a==a.window},isNumeric:function(a){return!isNaN(parseFloat(a))&&isFinite(a)},type:function(a){return a==null?String(a):I[C.call(a)]||"object"},isPlainObject:function(a){if(!a||e.type(a)!=="object"||a.nodeType||e.isWindow(a))return!1;try{if(a.constructor&&!D.call(a,"constructor")&&!D.call(a.constructor.prototype,"isPrototypeOf"))return!1}catch(c){return!1}var d;for(d in a);return d===b||D.call(a,d)},isEmptyObject:function(a){for(var b in a)return!1;return!0},error:function(a){throw new Error(a)},parseJSON:function(b){if(typeof b!="string"||!b)return null;b=e.trim(b);if(a.JSON&&a.JSON.parse)return a.JSON.parse(b);if(n.test(b.replace(o,"@").replace(p,"]").replace(q,"")))return(new Function("return "+b))();e.error("Invalid JSON: "+b)},parseXML:function(c){if(typeof c!="string"||!c)return null;var d,f;try{a.DOMParser?(f=new DOMParser,d=f.parseFromString(c,"text/xml")):(d=new ActiveXObject("Microsoft.XMLDOM"),d.async="false",d.loadXML(c))}catch(g){d=b}(!d||!d.documentElement||d.getElementsByTagName("parsererror").length)&&e.error("Invalid XML: "+c);return d},noop:function(){},globalEval:function(b){b&&j.test(b)&&(a.execScript||function(b){a.eval.call(a,b)})(b)},camelCase:function(a){return a.replace(w,"ms-").replace(v,x)},nodeName:function(a,b){return a.nodeName&&a.nodeName.toUpperCase()===b.toUpperCase()},each:function(a,c,d){var f,g=0,h=a.length,i=h===b||e.isFunction(a);if(d){if(i){for(f in a)if(c.apply(a[f],d)===!1)break}else for(;g<h;)if(c.apply(a[g++],d)===!1)break}else if(i){for(f in a)if(c.call(a[f],f,a[f])===!1)break}else for(;g<h;)if(c.call(a[g],g,a[g++])===!1)break;return a},trim:G?function(a){return a==null?"":G.call(a)}:function(a){return a==null?"":(a+"").replace(k,"").replace(l,"")},makeArray:function(a,b){var c=b||[];if(a!=null){var d=e.type(a);a.length==null||d==="string"||d==="function"||d==="regexp"||e.isWindow(a)?E.call(c,a):e.merge(c,a)}return c},inArray:function(a,b,c){var d;if(b){if(H)return H.call(b,a,c);d=b.length,c=c?c<0?Math.max(0,d+c):c:0;for(;c<d;c++)if(c in b&&b[c]===a)return c}return-1},merge:function(a,c){var d=a.length,e=0;if(typeof c.length=="number")for(var f=c.length;e<f;e++)a[d++]=c[e];else while(c[e]!==b)a[d++]=c[e++];a.length=d;return a},grep:function(a,b,c){var d=[],e;c=!!c;for(var f=0,g=a.length;f<g;f++)e=!!b(a[f],f),c!==e&&d.push(a[f]);return d},map:function(a,c,d){var f,g,h=[],i=0,j=a.length,k=a instanceof e||j!==b&&typeof j=="number"&&(j>0&&a[0]&&a[j-1]||j===0||e.isArray(a));if(k)for(;i<j;i++)f=c(a[i],i,d),f!=null&&(h[h.length]=f);else for(g in a)f=c(a[g],g,d),f!=null&&(h[h.length]=f);return h.concat.apply([],h)},guid:1,proxy:function(a,c){if(typeof c=="string"){var d=a[c];c=a,a=d}if(!e.isFunction(a))return b;var f=F.call(arguments,2),g=function(){return a.apply(c,f.concat(F.call(arguments)))};g.guid=a.guid=a.guid||g.guid||e.guid++;return g},access:function(a,c,d,f,g,h,i){var j,k=d==null,l=0,m=a.length;if(d&&typeof d=="object"){for(l in d)e.access(a,c,l,d[l],1,h,f);g=1}else if(f!==b){j=i===b&&e.isFunction(f),k&&(j?(j=c,c=function(a,b,c){return j.call(e(a),c)}):(c.call(a,f),c=null));if(c)for(;l<m;l++)c(a[l],d,j?f.call(a[l],l,c(a[l],d)):f,i);g=1}return g?a:k?c.call(a):m?c(a[0],d):h},now:function(){return(new Date).getTime()},uaMatch:function(a){a=a.toLowerCase();var b=r.exec(a)||s.exec(a)||t.exec(a)||a.indexOf("compatible")<0&&u.exec(a)||[];return{browser:b[1]||"",version:b[2]||"0"}},sub:function(){function a(b,c){return new a.fn.init(b,c)}e.extend(!0,a,this),a.superclass=this,a.fn=a.prototype=this(),a.fn.constructor=a,a.sub=this.sub,a.fn.init=function(d,f){f&&f instanceof e&&!(f instanceof a)&&(f=a(f));return e.fn.init.call(this,d,f,b)},a.fn.init.prototype=a.fn;var b=a(c);return a},browser:{}}),e.each("Boolean Number String Function Array Date RegExp Object".split(" "),function(a,b){I["[object "+b+"]"]=b.toLowerCase()}),z=e.uaMatch(y),z.browser&&(e.browser[z.browser]=!0,e.browser.version=z.version),e.browser.webkit&&(e.browser.safari=!0),j.test(" ")&&(k=/^[\s\xA0]+/,l=/[\s\xA0]+$/),h=e(c),c.addEventListener?B=function(){c.removeEventListener("DOMContentLoaded",B,!1),e.ready()}:c.attachEvent&&(B=function(){c.readyState==="complete"&&(c.detachEvent("onreadystatechange",B),e.ready())});return e}(),g={};f.Callbacks=function(a){a=a?g[a]||h(a):{};var c=[],d=[],e,i,j,k,l,m,n=function(b){var d,e,g,h,i;for(d=0,e=b.length;d<e;d++)g=b[d],h=f.type(g),h==="array"?n(g):h==="function"&&(!a.unique||!p.has(g))&&c.push(g)},o=function(b,f){f=f||[],e=!a.memory||[b,f],i=!0,j=!0,m=k||0,k=0,l=c.length;for(;c&&m<l;m++)if(c[m].apply(b,f)===!1&&a.stopOnFalse){e=!0;break}j=!1,c&&(a.once?e===!0?p.disable():c=[]:d&&d.length&&(e=d.shift(),p.fireWith(e[0],e[1])))},p={add:function(){if(c){var a=c.length;n(arguments),j?l=c.length:e&&e!==!0&&(k=a,o(e[0],e[1]))}return this},remove:function(){if(c){var b=arguments,d=0,e=b.length;for(;d<e;d++)for(var f=0;f<c.length;f++)if(b[d]===c[f]){j&&f<=l&&(l--,f<=m&&m--),c.splice(f--,1);if(a.unique)break}}return this},has:function(a){if(c){var b=0,d=c.length;for(;b<d;b++)if(a===c[b])return!0}return!1},empty:function(){c=[];return this},disable:function(){c=d=e=b;return this},disabled:function(){return!c},lock:function(){d=b,(!e||e===!0)&&p.disable();return this},locked:function(){return!d},fireWith:function(b,c){d&&(j?a.once||d.push([b,c]):(!a.once||!e)&&o(b,c));return this},fire:function(){p.fireWith(this,arguments);return this},fired:function(){return!!i}};return p};var i=[].slice;f.extend({Deferred:function(a){var b=f.Callbacks("once memory"),c=f.Callbacks("once memory"),d=f.Callbacks("memory"),e="pending",g={resolve:b,reject:c,notify:d},h={done:b.add,fail:c.add,progress:d.add,state:function(){return e},isResolved:b.fired,isRejected:c.fired,then:function(a,b,c){i.done(a).fail(b).progress(c);return this},always:function(){i.done.apply(i,arguments).fail.apply(i,arguments);return this},pipe:function(a,b,c){return f.Deferred(function(d){f.each({done:[a,"resolve"],fail:[b,"reject"],progress:[c,"notify"]},function(a,b){var c=b[0],e=b[1],g;f.isFunction(c)?i[a](function(){g=c.apply(this,arguments),g&&f.isFunction(g.promise)?g.promise().then(d.resolve,d.reject,d.notify):d[e+"With"](this===i?d:this,[g])}):i[a](d[e])})}).promise()},promise:function(a){if(a==null)a=h;else for(var b in h)a[b]=h[b];return a}},i=h.promise({}),j;for(j in g)i[j]=g[j].fire,i[j+"With"]=g[j].fireWith;i.done(function(){e="resolved"},c.disable,d.lock).fail(function(){e="rejected"},b.disable,d.lock),a&&a.call(i,i);return i},when:function(a){function m(a){return function(b){e[a]=arguments.length>1?i.call(arguments,0):b,j.notifyWith(k,e)}}function l(a){return function(c){b[a]=arguments.length>1?i.call(arguments,0):c,--g||j.resolveWith(j,b)}}var b=i.call(arguments,0),c=0,d=b.length,e=Array(d),g=d,h=d,j=d<=1&&a&&f.isFunction(a.promise)?a:f.Deferred(),k=j.promise();if(d>1){for(;c<d;c++)b[c]&&b[c].promise&&f.isFunction(b[c].promise)?b[c].promise().then(l(c),j.reject,m(c)):--g;g||j.resolveWith(j,b)}else j!==a&&j.resolveWith(j,d?[a]:[]);return k}}),f.support=function(){var b,d,e,g,h,i,j,k,l,m,n,o,p=c.createElement("div"),q=c.documentElement;p.setAttribute("className","t"),p.innerHTML=" <link/><table></table><a href='/a' style='top:1px;float:left;opacity:.55;'>a</a><input type='checkbox'/>",d=p.getElementsByTagName("*"),e=p.getElementsByTagName("a")[0];if(!d||!d.length||!e)return{};g=c.createElement("select"),h=g.appendChild(c.createElement("option")),i=p.getElementsByTagName("input")[0],b={leadingWhitespace:p.firstChild.nodeType===3,tbody:!p.getElementsByTagName("tbody").length,htmlSerialize:!!p.getElementsByTagName("link").length,style:/top/.test(e.getAttribute("style")),hrefNormalized:e.getAttribute("href")==="/a",opacity:/^0.55/.test(e.style.opacity),cssFloat:!!e.style.cssFloat,checkOn:i.value==="on",optSelected:h.selected,getSetAttribute:p.className!=="t",enctype:!!c.createElement("form").enctype,html5Clone:c.createElement("nav").cloneNode(!0).outerHTML!=="<:nav></:nav>",submitBubbles:!0,changeBubbles:!0,focusinBubbles:!1,deleteExpando:!0,noCloneEvent:!0,inlineBlockNeedsLayout:!1,shrinkWrapBlocks:!1,reliableMarginRight:!0,pixelMargin:!0},f.boxModel=b.boxModel=c.compatMode==="CSS1Compat",i.checked=!0,b.noCloneChecked=i.cloneNode(!0).checked,g.disabled=!0,b.optDisabled=!h.disabled;try{delete p.test}catch(r){b.deleteExpando=!1}!p.addEventListener&&p.attachEvent&&p.fireEvent&&(p.attachEvent("onclick",function(){b.noCloneEvent=!1}),p.cloneNode(!0).fireEvent("onclick")),i=c.createElement("input"),i.value="t",i.setAttribute("type","radio"),b.radioValue=i.value==="t",i.setAttribute("checked","checked"),i.setAttribute("name","t"),p.appendChild(i),j=c.createDocumentFragment(),j.appendChild(p.lastChild),b.checkClone=j.cloneNode(!0).cloneNode(!0).lastChild.checked,b.appendChecked=i.checked,j.removeChild(i),j.appendChild(p);if(p.attachEvent)for(n in{submit:1,change:1,focusin:1})m="on"+n,o=m in p,o||(p.setAttribute(m,"return;"),o=typeof p[m]=="function"),b[n+"Bubbles"]=o;j.removeChild(p),j=g=h=p=i=null,f(function(){var d,e,g,h,i,j,l,m,n,q,r,s,t,u=c.getElementsByTagName("body")[0];!u||(m=1,t="padding:0;margin:0;border:",r="position:absolute;top:0;left:0;width:1px;height:1px;",s=t+"0;visibility:hidden;",n="style='"+r+t+"5px solid #000;",q="<div "+n+"display:block;'><div style='"+t+"0;display:block;overflow:hidden;'></div></div>"+"<table "+n+"' cellpadding='0' cellspacing='0'>"+"<tr><td></td></tr></table>",d=c.createElement("div"),d.style.cssText=s+"width:0;height:0;position:static;top:0;margin-top:"+m+"px",u.insertBefore(d,u.firstChild),p=c.createElement("div"),d.appendChild(p),p.innerHTML="<table><tr><td style='"+t+"0;display:none'></td><td>t</td></tr></table>",k=p.getElementsByTagName("td"),o=k[0].offsetHeight===0,k[0].style.display="",k[1].style.display="none",b.reliableHiddenOffsets=o&&k[0].offsetHeight===0,a.getComputedStyle&&(p.innerHTML="",l=c.createElement("div"),l.style.width="0",l.style.marginRight="0",p.style.width="2px",p.appendChild(l),b.reliableMarginRight=(parseInt((a.getComputedStyle(l,null)||{marginRight:0}).marginRight,10)||0)===0),typeof p.style.zoom!="undefined"&&(p.innerHTML="",p.style.width=p.style.padding="1px",p.style.border=0,p.style.overflow="hidden",p.style.display="inline",p.style.zoom=1,b.inlineBlockNeedsLayout=p.offsetWidth===3,p.style.display="block",p.style.overflow="visible",p.innerHTML="<div style='width:5px;'></div>",b.shrinkWrapBlocks=p.offsetWidth!==3),p.style.cssText=r+s,p.innerHTML=q,e=p.firstChild,g=e.firstChild,i=e.nextSibling.firstChild.firstChild,j={doesNotAddBorder:g.offsetTop!==5,doesAddBorderForTableAndCells:i.offsetTop===5},g.style.position="fixed",g.style.top="20px",j.fixedPosition=g.offsetTop===20||g.offsetTop===15,g.style.position=g.style.top="",e.style.overflow="hidden",e.style.position="relative",j.subtractsBorderForOverflowNotVisible=g.offsetTop===-5,j.doesNotIncludeMarginInBodyOffset=u.offsetTop!==m,a.getComputedStyle&&(p.style.marginTop="1%",b.pixelMargin=(a.getComputedStyle(p,null)||{marginTop:0}).marginTop!=="1%"),typeof d.style.zoom!="undefined"&&(d.style.zoom=1),u.removeChild(d),l=p=d=null,f.extend(b,j))});return b}();var j=/^(?:\{.*\}|\[.*\])$/,k=/([A-Z])/g;f.extend({cache:{},uuid:0,expando:"jQuery"+(f.fn.jquery+Math.random()).replace(/\D/g,""),noData:{embed:!0,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000",applet:!0},hasData:function(a){a=a.nodeType?f.cache[a[f.expando]]:a[f.expando];return!!a&&!m(a)},data:function(a,c,d,e){if(!!f.acceptData(a)){var g,h,i,j=f.expando,k=typeof c=="string",l=a.nodeType,m=l?f.cache:a,n=l?a[j]:a[j]&&j,o=c==="events";if((!n||!m[n]||!o&&!e&&!m[n].data)&&k&&d===b)return;n||(l?a[j]=n=++f.uuid:n=j),m[n]||(m[n]={},l||(m[n].toJSON=f.noop));if(typeof c=="object"||typeof c=="function")e?m[n]=f.extend(m[n],c):m[n].data=f.extend(m[n].data,c);g=h=m[n],e||(h.data||(h.data={}),h=h.data),d!==b&&(h[f.camelCase(c)]=d);if(o&&!h[c])return g.events;k?(i=h[c],i==null&&(i=h[f.camelCase(c)])):i=h;return i}},removeData:function(a,b,c){if(!!f.acceptData(a)){var d,e,g,h=f.expando,i=a.nodeType,j=i?f.cache:a,k=i?a[h]:h;if(!j[k])return;if(b){d=c?j[k]:j[k].data;if(d){f.isArray(b)||(b in d?b=[b]:(b=f.camelCase(b),b in d?b=[b]:b=b.split(" ")));for(e=0,g=b.length;e<g;e++)delete d[b[e]];if(!(c?m:f.isEmptyObject)(d))return}}if(!c){delete j[k].data;if(!m(j[k]))return}f.support.deleteExpando||!j.setInterval?delete j[k]:j[k]=null,i&&(f.support.deleteExpando?delete a[h]:a.removeAttribute?a.removeAttribute(h):a[h]=null)}},_data:function(a,b,c){return f.data(a,b,c,!0)},acceptData:function(a){if(a.nodeName){var b=f.noData[a.nodeName.toLowerCase()];if(b)return b!==!0&&a.getAttribute("classid")===b}return!0}}),f.fn.extend({data:function(a,c){var d,e,g,h,i,j=this[0],k=0,m=null;if(a===b){if(this.length){m=f.data(j);if(j.nodeType===1&&!f._data(j,"parsedAttrs")){g=j.attributes;for(i=g.length;k<i;k++)h=g[k].name,h.indexOf("data-")===0&&(h=f.camelCase(h.substring(5)),l(j,h,m[h]));f._data(j,"parsedAttrs",!0)}}return m}if(typeof a=="object")return this.each(function(){f.data(this,a)});d=a.split(".",2),d[1]=d[1]?"."+d[1]:"",e=d[1]+"!";return f.access(this,function(c){if(c===b){m=this.triggerHandler("getData"+e,[d[0]]),m===b&&j&&(m=f.data(j,a),m=l(j,a,m));return m===b&&d[1]?this.data(d[0]):m}d[1]=c,this.each(function(){var b=f(this);b.triggerHandler("setData"+e,d),f.data(this,a,c),b.triggerHandler("changeData"+e,d)})},null,c,arguments.length>1,null,!1)},removeData:function(a){return this.each(function(){f.removeData(this,a)})}}),f.extend({_mark:function(a,b){a&&(b=(b||"fx")+"mark",f._data(a,b,(f._data(a,b)||0)+1))},_unmark:function(a,b,c){a!==!0&&(c=b,b=a,a=!1);if(b){c=c||"fx";var d=c+"mark",e=a?0:(f._data(b,d)||1)-1;e?f._data(b,d,e):(f.removeData(b,d,!0),n(b,c,"mark"))}},queue:function(a,b,c){var d;if(a){b=(b||"fx")+"queue",d=f._data(a,b),c&&(!d||f.isArray(c)?d=f._data(a,b,f.makeArray(c)):d.push(c));return d||[]}},dequeue:function(a,b){b=b||"fx";var c=f.queue(a,b),d=c.shift(),e={};d==="inprogress"&&(d=c.shift()),d&&(b==="fx"&&c.unshift("inprogress"),f._data(a,b+".run",e),d.call(a,function(){f.dequeue(a,b)},e)),c.length||(f.removeData(a,b+"queue "+b+".run",!0),n(a,b,"queue"))}}),f.fn.extend({queue:function(a,c){var d=2;typeof a!="string"&&(c=a,a="fx",d--);if(arguments.length<d)return f.queue(this[0],a);return c===b?this:this.each(function(){var b=f.queue(this,a,c);a==="fx"&&b[0]!=="inprogress"&&f.dequeue(this,a)})},dequeue:function(a){return this.each(function(){f.dequeue(this,a)})},delay:function(a,b){a=f.fx?f.fx.speeds[a]||a:a,b=b||"fx";return this.queue(b,function(b,c){var d=setTimeout(b,a);c.stop=function(){clearTimeout(d)}})},clearQueue:function(a){return this.queue(a||"fx",[])},promise:function(a,c){function m(){--h||d.resolveWith(e,[e])}typeof a!="string"&&(c=a,a=b),a=a||"fx";var d=f.Deferred(),e=this,g=e.length,h=1,i=a+"defer",j=a+"queue",k=a+"mark",l;while(g--)if(l=f.data(e[g],i,b,!0)||(f.data(e[g],j,b,!0)||f.data(e[g],k,b,!0))&&f.data(e[g],i,f.Callbacks("once memory"),!0))h++,l.add(m);m();return d.promise(c)}});var o=/[\n\t\r]/g,p=/\s+/,q=/\r/g,r=/^(?:button|input)$/i,s=/^(?:button|input|object|select|textarea)$/i,t=/^a(?:rea)?$/i,u=/^(?:autofocus|autoplay|async|checked|controls|defer|disabled|hidden|loop|multiple|open|readonly|required|scoped|selected)$/i,v=f.support.getSetAttribute,w,x,y;f.fn.extend({attr:function(a,b){return f.access(this,f.attr,a,b,arguments.length>1)},removeAttr:function(a){return this.each(function(){f.removeAttr(this,a)})},prop:function(a,b){return f.access(this,f.prop,a,b,arguments.length>1)},removeProp:function(a){a=f.propFix[a]||a;return this.each(function(){try{this[a]=b,delete this[a]}catch(c){}})},addClass:function(a){var b,c,d,e,g,h,i;if(f.isFunction(a))return this.each(function(b){f(this).addClass(a.call(this,b,this.className))});if(a&&typeof a=="string"){b=a.split(p);for(c=0,d=this.length;c<d;c++){e=this[c];if(e.nodeType===1)if(!e.className&&b.length===1)e.className=a;else{g=" "+e.className+" ";for(h=0,i=b.length;h<i;h++)~g.indexOf(" "+b[h]+" ")||(g+=b[h]+" ");e.className=f.trim(g)}}}return this},removeClass:function(a){var c,d,e,g,h,i,j;if(f.isFunction(a))return this.each(function(b){f(this).removeClass(a.call(this,b,this.className))});if(a&&typeof a=="string"||a===b){c=(a||"").split(p);for(d=0,e=this.length;d<e;d++){g=this[d];if(g.nodeType===1&&g.className)if(a){h=(" "+g.className+" ").replace(o," ");for(i=0,j=c.length;i<j;i++)h=h.replace(" "+c[i]+" "," ");g.className=f.trim(h)}else g.className=""}}return this},toggleClass:function(a,b){var c=typeof a,d=typeof b=="boolean";if(f.isFunction(a))return this.each(function(c){f(this).toggleClass(a.call(this,c,this.className,b),b)});return this.each(function(){if(c==="string"){var e,g=0,h=f(this),i=b,j=a.split(p);while(e=j[g++])i=d?i:!h.hasClass(e),h[i?"addClass":"removeClass"](e)}else if(c==="undefined"||c==="boolean")this.className&&f._data(this,"__className__",this.className),this.className=this.className||a===!1?"":f._data(this,"__className__")||""})},hasClass:function(a){var b=" "+a+" ",c=0,d=this.length;for(;c<d;c++)if(this[c].nodeType===1&&(" "+this[c].className+" ").replace(o," ").indexOf(b)>-1)return!0;return!1},val:function(a){var c,d,e,g=this[0];{if(!!arguments.length){e=f.isFunction(a);return this.each(function(d){var g=f(this),h;if(this.nodeType===1){e?h=a.call(this,d,g.val()):h=a,h==null?h="":typeof h=="number"?h+="":f.isArray(h)&&(h=f.map(h,function(a){return a==null?"":a+""})),c=f.valHooks[this.type]||f.valHooks[this.nodeName.toLowerCase()];if(!c||!("set"in c)||c.set(this,h,"value")===b)this.value=h}})}if(g){c=f.valHooks[g.type]||f.valHooks[g.nodeName.toLowerCase()];if(c&&"get"in c&&(d=c.get(g,"value"))!==b)return d;d=g.value;return typeof d=="string"?d.replace(q,""):d==null?"":d}}}}),f.extend({valHooks:{option:{get:function(a){var b=a.attributes.value;return!b||b.specified?a.value:a.text}},select:{get:function(a){var b,c,d,e,g=a.selectedIndex,h=[],i=a.options,j=a.type==="select-one";if(g<0)return null;c=j?g:0,d=j?g+1:i.length;for(;c<d;c++){e=i[c];if(e.selected&&(f.support.optDisabled?!e.disabled:e.getAttribute("disabled")===null)&&(!e.parentNode.disabled||!f.nodeName(e.parentNode,"optgroup"))){b=f(e).val();if(j)return b;h.push(b)}}if(j&&!h.length&&i.length)return f(i[g]).val();return h},set:function(a,b){var c=f.makeArray(b);f(a).find("option").each(function(){this.selected=f.inArray(f(this).val(),c)>=0}),c.length||(a.selectedIndex=-1);return c}}},attrFn:{val:!0,css:!0,html:!0,text:!0,data:!0,width:!0,height:!0,offset:!0},attr:function(a,c,d,e){var g,h,i,j=a.nodeType;if(!!a&&j!==3&&j!==8&&j!==2){if(e&&c in f.attrFn)return f(a)[c](d);if(typeof a.getAttribute=="undefined")return f.prop(a,c,d);i=j!==1||!f.isXMLDoc(a),i&&(c=c.toLowerCase(),h=f.attrHooks[c]||(u.test(c)?x:w));if(d!==b){if(d===null){f.removeAttr(a,c);return}if(h&&"set"in h&&i&&(g=h.set(a,d,c))!==b)return g;a.setAttribute(c,""+d);return d}if(h&&"get"in h&&i&&(g=h.get(a,c))!==null)return g;g=a.getAttribute(c);return g===null?b:g}},removeAttr:function(a,b){var c,d,e,g,h,i=0;if(b&&a.nodeType===1){d=b.toLowerCase().split(p),g=d.length;for(;i<g;i++)e=d[i],e&&(c=f.propFix[e]||e,h=u.test(e),h||f.attr(a,e,""),a.removeAttribute(v?e:c),h&&c in a&&(a[c]=!1))}},attrHooks:{type:{set:function(a,b){if(r.test(a.nodeName)&&a.parentNode)f.error("type property can't be changed");else if(!f.support.radioValue&&b==="radio"&&f.nodeName(a,"input")){var c=a.value;a.setAttribute("type",b),c&&(a.value=c);return b}}},value:{get:function(a,b){if(w&&f.nodeName(a,"button"))return w.get(a,b);return b in a?a.value:null},set:function(a,b,c){if(w&&f.nodeName(a,"button"))return w.set(a,b,c);a.value=b}}},propFix:{tabindex:"tabIndex",readonly:"readOnly","for":"htmlFor","class":"className",maxlength:"maxLength",cellspacing:"cellSpacing",cellpadding:"cellPadding",rowspan:"rowSpan",colspan:"colSpan",usemap:"useMap",frameborder:"frameBorder",contenteditable:"contentEditable"},prop:function(a,c,d){var e,g,h,i=a.nodeType;if(!!a&&i!==3&&i!==8&&i!==2){h=i!==1||!f.isXMLDoc(a),h&&(c=f.propFix[c]||c,g=f.propHooks[c]);return d!==b?g&&"set"in g&&(e=g.set(a,d,c))!==b?e:a[c]=d:g&&"get"in g&&(e=g.get(a,c))!==null?e:a[c]}},propHooks:{tabIndex:{get:function(a){var c=a.getAttributeNode("tabindex");return c&&c.specified?parseInt(c.value,10):s.test(a.nodeName)||t.test(a.nodeName)&&a.href?0:b}}}}),f.attrHooks.tabindex=f.propHooks.tabIndex,x={get:function(a,c){var d,e=f.prop(a,c);return e===!0||typeof e!="boolean"&&(d=a.getAttributeNode(c))&&d.nodeValue!==!1?c.toLowerCase():b},set:function(a,b,c){var d;b===!1?f.removeAttr(a,c):(d=f.propFix[c]||c,d in a&&(a[d]=!0),a.setAttribute(c,c.toLowerCase()));return c}},v||(y={name:!0,id:!0,coords:!0},w=f.valHooks.button={get:function(a,c){var d;d=a.getAttributeNode(c);return d&&(y[c]?d.nodeValue!=="":d.specified)?d.nodeValue:b},set:function(a,b,d){var e=a.getAttributeNode(d);e||(e=c.createAttribute(d),a.setAttributeNode(e));return e.nodeValue=b+""}},f.attrHooks.tabindex.set=w.set,f.each(["width","height"],function(a,b){f.attrHooks[b]=f.extend(f.attrHooks[b],{set:function(a,c){if(c===""){a.setAttribute(b,"auto");return c}}})}),f.attrHooks.contenteditable={get:w.get,set:function(a,b,c){b===""&&(b="false"),w.set(a,b,c)}}),f.support.hrefNormalized||f.each(["href","src","width","height"],function(a,c){f.attrHooks[c]=f.extend(f.attrHooks[c],{get:function(a){var d=a.getAttribute(c,2);return d===null?b:d}})}),f.support.style||(f.attrHooks.style={get:function(a){return a.style.cssText.toLowerCase()||b},set:function(a,b){return a.style.cssText=""+b}}),f.support.optSelected||(f.propHooks.selected=f.extend(f.propHooks.selected,{get:function(a){var b=a.parentNode;b&&(b.selectedIndex,b.parentNode&&b.parentNode.selectedIndex);return null}})),f.support.enctype||(f.propFix.enctype="encoding"),f.support.checkOn||f.each(["radio","checkbox"],function(){f.valHooks[this]={get:function(a){return a.getAttribute("value")===null?"on":a.value}}}),f.each(["radio","checkbox"],function(){f.valHooks[this]=f.extend(f.valHooks[this],{set:function(a,b){if(f.isArray(b))return a.checked=f.inArray(f(a).val(),b)>=0}})});var z=/^(?:textarea|input|select)$/i,A=/^([^\.]*)?(?:\.(.+))?$/,B=/(?:^|\s)hover(\.\S+)?\b/,C=/^key/,D=/^(?:mouse|contextmenu)|click/,E=/^(?:focusinfocus|focusoutblur)$/,F=/^(\w*)(?:#([\w\-]+))?(?:\.([\w\-]+))?$/,G=function(
-a){var b=F.exec(a);b&&(b[1]=(b[1]||"").toLowerCase(),b[3]=b[3]&&new RegExp("(?:^|\\s)"+b[3]+"(?:\\s|$)"));return b},H=function(a,b){var c=a.attributes||{};return(!b[1]||a.nodeName.toLowerCase()===b[1])&&(!b[2]||(c.id||{}).value===b[2])&&(!b[3]||b[3].test((c["class"]||{}).value))},I=function(a){return f.event.special.hover?a:a.replace(B,"mouseenter$1 mouseleave$1")};f.event={add:function(a,c,d,e,g){var h,i,j,k,l,m,n,o,p,q,r,s;if(!(a.nodeType===3||a.nodeType===8||!c||!d||!(h=f._data(a)))){d.handler&&(p=d,d=p.handler,g=p.selector),d.guid||(d.guid=f.guid++),j=h.events,j||(h.events=j={}),i=h.handle,i||(h.handle=i=function(a){return typeof f!="undefined"&&(!a||f.event.triggered!==a.type)?f.event.dispatch.apply(i.elem,arguments):b},i.elem=a),c=f.trim(I(c)).split(" ");for(k=0;k<c.length;k++){l=A.exec(c[k])||[],m=l[1],n=(l[2]||"").split(".").sort(),s=f.event.special[m]||{},m=(g?s.delegateType:s.bindType)||m,s=f.event.special[m]||{},o=f.extend({type:m,origType:l[1],data:e,handler:d,guid:d.guid,selector:g,quick:g&&G(g),namespace:n.join(".")},p),r=j[m];if(!r){r=j[m]=[],r.delegateCount=0;if(!s.setup||s.setup.call(a,e,n,i)===!1)a.addEventListener?a.addEventListener(m,i,!1):a.attachEvent&&a.attachEvent("on"+m,i)}s.add&&(s.add.call(a,o),o.handler.guid||(o.handler.guid=d.guid)),g?r.splice(r.delegateCount++,0,o):r.push(o),f.event.global[m]=!0}a=null}},global:{},remove:function(a,b,c,d,e){var g=f.hasData(a)&&f._data(a),h,i,j,k,l,m,n,o,p,q,r,s;if(!!g&&!!(o=g.events)){b=f.trim(I(b||"")).split(" ");for(h=0;h<b.length;h++){i=A.exec(b[h])||[],j=k=i[1],l=i[2];if(!j){for(j in o)f.event.remove(a,j+b[h],c,d,!0);continue}p=f.event.special[j]||{},j=(d?p.delegateType:p.bindType)||j,r=o[j]||[],m=r.length,l=l?new RegExp("(^|\\.)"+l.split(".").sort().join("\\.(?:.*\\.)?")+"(\\.|$)"):null;for(n=0;n<r.length;n++)s=r[n],(e||k===s.origType)&&(!c||c.guid===s.guid)&&(!l||l.test(s.namespace))&&(!d||d===s.selector||d==="**"&&s.selector)&&(r.splice(n--,1),s.selector&&r.delegateCount--,p.remove&&p.remove.call(a,s));r.length===0&&m!==r.length&&((!p.teardown||p.teardown.call(a,l)===!1)&&f.removeEvent(a,j,g.handle),delete o[j])}f.isEmptyObject(o)&&(q=g.handle,q&&(q.elem=null),f.removeData(a,["events","handle"],!0))}},customEvent:{getData:!0,setData:!0,changeData:!0},trigger:function(c,d,e,g){if(!e||e.nodeType!==3&&e.nodeType!==8){var h=c.type||c,i=[],j,k,l,m,n,o,p,q,r,s;if(E.test(h+f.event.triggered))return;h.indexOf("!")>=0&&(h=h.slice(0,-1),k=!0),h.indexOf(".")>=0&&(i=h.split("."),h=i.shift(),i.sort());if((!e||f.event.customEvent[h])&&!f.event.global[h])return;c=typeof c=="object"?c[f.expando]?c:new f.Event(h,c):new f.Event(h),c.type=h,c.isTrigger=!0,c.exclusive=k,c.namespace=i.join("."),c.namespace_re=c.namespace?new RegExp("(^|\\.)"+i.join("\\.(?:.*\\.)?")+"(\\.|$)"):null,o=h.indexOf(":")<0?"on"+h:"";if(!e){j=f.cache;for(l in j)j[l].events&&j[l].events[h]&&f.event.trigger(c,d,j[l].handle.elem,!0);return}c.result=b,c.target||(c.target=e),d=d!=null?f.makeArray(d):[],d.unshift(c),p=f.event.special[h]||{};if(p.trigger&&p.trigger.apply(e,d)===!1)return;r=[[e,p.bindType||h]];if(!g&&!p.noBubble&&!f.isWindow(e)){s=p.delegateType||h,m=E.test(s+h)?e:e.parentNode,n=null;for(;m;m=m.parentNode)r.push([m,s]),n=m;n&&n===e.ownerDocument&&r.push([n.defaultView||n.parentWindow||a,s])}for(l=0;l<r.length&&!c.isPropagationStopped();l++)m=r[l][0],c.type=r[l][1],q=(f._data(m,"events")||{})[c.type]&&f._data(m,"handle"),q&&q.apply(m,d),q=o&&m[o],q&&f.acceptData(m)&&q.apply(m,d)===!1&&c.preventDefault();c.type=h,!g&&!c.isDefaultPrevented()&&(!p._default||p._default.apply(e.ownerDocument,d)===!1)&&(h!=="click"||!f.nodeName(e,"a"))&&f.acceptData(e)&&o&&e[h]&&(h!=="focus"&&h!=="blur"||c.target.offsetWidth!==0)&&!f.isWindow(e)&&(n=e[o],n&&(e[o]=null),f.event.triggered=h,e[h](),f.event.triggered=b,n&&(e[o]=n));return c.result}},dispatch:function(c){c=f.event.fix(c||a.event);var d=(f._data(this,"events")||{})[c.type]||[],e=d.delegateCount,g=[].slice.call(arguments,0),h=!c.exclusive&&!c.namespace,i=f.event.special[c.type]||{},j=[],k,l,m,n,o,p,q,r,s,t,u;g[0]=c,c.delegateTarget=this;if(!i.preDispatch||i.preDispatch.call(this,c)!==!1){if(e&&(!c.button||c.type!=="click")){n=f(this),n.context=this.ownerDocument||this;for(m=c.target;m!=this;m=m.parentNode||this)if(m.disabled!==!0){p={},r=[],n[0]=m;for(k=0;k<e;k++)s=d[k],t=s.selector,p[t]===b&&(p[t]=s.quick?H(m,s.quick):n.is(t)),p[t]&&r.push(s);r.length&&j.push({elem:m,matches:r})}}d.length>e&&j.push({elem:this,matches:d.slice(e)});for(k=0;k<j.length&&!c.isPropagationStopped();k++){q=j[k],c.currentTarget=q.elem;for(l=0;l<q.matches.length&&!c.isImmediatePropagationStopped();l++){s=q.matches[l];if(h||!c.namespace&&!s.namespace||c.namespace_re&&c.namespace_re.test(s.namespace))c.data=s.data,c.handleObj=s,o=((f.event.special[s.origType]||{}).handle||s.handler).apply(q.elem,g),o!==b&&(c.result=o,o===!1&&(c.preventDefault(),c.stopPropagation()))}}i.postDispatch&&i.postDispatch.call(this,c);return c.result}},props:"attrChange attrName relatedNode srcElement altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "),fixHooks:{},keyHooks:{props:"char charCode key keyCode".split(" "),filter:function(a,b){a.which==null&&(a.which=b.charCode!=null?b.charCode:b.keyCode);return a}},mouseHooks:{props:"button buttons clientX clientY fromElement offsetX offsetY pageX pageY screenX screenY toElement".split(" "),filter:function(a,d){var e,f,g,h=d.button,i=d.fromElement;a.pageX==null&&d.clientX!=null&&(e=a.target.ownerDocument||c,f=e.documentElement,g=e.body,a.pageX=d.clientX+(f&&f.scrollLeft||g&&g.scrollLeft||0)-(f&&f.clientLeft||g&&g.clientLeft||0),a.pageY=d.clientY+(f&&f.scrollTop||g&&g.scrollTop||0)-(f&&f.clientTop||g&&g.clientTop||0)),!a.relatedTarget&&i&&(a.relatedTarget=i===a.target?d.toElement:i),!a.which&&h!==b&&(a.which=h&1?1:h&2?3:h&4?2:0);return a}},fix:function(a){if(a[f.expando])return a;var d,e,g=a,h=f.event.fixHooks[a.type]||{},i=h.props?this.props.concat(h.props):this.props;a=f.Event(g);for(d=i.length;d;)e=i[--d],a[e]=g[e];a.target||(a.target=g.srcElement||c),a.target.nodeType===3&&(a.target=a.target.parentNode),a.metaKey===b&&(a.metaKey=a.ctrlKey);return h.filter?h.filter(a,g):a},special:{ready:{setup:f.bindReady},load:{noBubble:!0},focus:{delegateType:"focusin"},blur:{delegateType:"focusout"},beforeunload:{setup:function(a,b,c){f.isWindow(this)&&(this.onbeforeunload=c)},teardown:function(a,b){this.onbeforeunload===b&&(this.onbeforeunload=null)}}},simulate:function(a,b,c,d){var e=f.extend(new f.Event,c,{type:a,isSimulated:!0,originalEvent:{}});d?f.event.trigger(e,null,b):f.event.dispatch.call(b,e),e.isDefaultPrevented()&&c.preventDefault()}},f.event.handle=f.event.dispatch,f.removeEvent=c.removeEventListener?function(a,b,c){a.removeEventListener&&a.removeEventListener(b,c,!1)}:function(a,b,c){a.detachEvent&&a.detachEvent("on"+b,c)},f.Event=function(a,b){if(!(this instanceof f.Event))return new f.Event(a,b);a&&a.type?(this.originalEvent=a,this.type=a.type,this.isDefaultPrevented=a.defaultPrevented||a.returnValue===!1||a.getPreventDefault&&a.getPreventDefault()?K:J):this.type=a,b&&f.extend(this,b),this.timeStamp=a&&a.timeStamp||f.now(),this[f.expando]=!0},f.Event.prototype={preventDefault:function(){this.isDefaultPrevented=K;var a=this.originalEvent;!a||(a.preventDefault?a.preventDefault():a.returnValue=!1)},stopPropagation:function(){this.isPropagationStopped=K;var a=this.originalEvent;!a||(a.stopPropagation&&a.stopPropagation(),a.cancelBubble=!0)},stopImmediatePropagation:function(){this.isImmediatePropagationStopped=K,this.stopPropagation()},isDefaultPrevented:J,isPropagationStopped:J,isImmediatePropagationStopped:J},f.each({mouseenter:"mouseover",mouseleave:"mouseout"},function(a,b){f.event.special[a]={delegateType:b,bindType:b,handle:function(a){var c=this,d=a.relatedTarget,e=a.handleObj,g=e.selector,h;if(!d||d!==c&&!f.contains(c,d))a.type=e.origType,h=e.handler.apply(this,arguments),a.type=b;return h}}}),f.support.submitBubbles||(f.event.special.submit={setup:function(){if(f.nodeName(this,"form"))return!1;f.event.add(this,"click._submit keypress._submit",function(a){var c=a.target,d=f.nodeName(c,"input")||f.nodeName(c,"button")?c.form:b;d&&!d._submit_attached&&(f.event.add(d,"submit._submit",function(a){a._submit_bubble=!0}),d._submit_attached=!0)})},postDispatch:function(a){a._submit_bubble&&(delete a._submit_bubble,this.parentNode&&!a.isTrigger&&f.event.simulate("submit",this.parentNode,a,!0))},teardown:function(){if(f.nodeName(this,"form"))return!1;f.event.remove(this,"._submit")}}),f.support.changeBubbles||(f.event.special.change={setup:function(){if(z.test(this.nodeName)){if(this.type==="checkbox"||this.type==="radio")f.event.add(this,"propertychange._change",function(a){a.originalEvent.propertyName==="checked"&&(this._just_changed=!0)}),f.event.add(this,"click._change",function(a){this._just_changed&&!a.isTrigger&&(this._just_changed=!1,f.event.simulate("change",this,a,!0))});return!1}f.event.add(this,"beforeactivate._change",function(a){var b=a.target;z.test(b.nodeName)&&!b._change_attached&&(f.event.add(b,"change._change",function(a){this.parentNode&&!a.isSimulated&&!a.isTrigger&&f.event.simulate("change",this.parentNode,a,!0)}),b._change_attached=!0)})},handle:function(a){var b=a.target;if(this!==b||a.isSimulated||a.isTrigger||b.type!=="radio"&&b.type!=="checkbox")return a.handleObj.handler.apply(this,arguments)},teardown:function(){f.event.remove(this,"._change");return z.test(this.nodeName)}}),f.support.focusinBubbles||f.each({focus:"focusin",blur:"focusout"},function(a,b){var d=0,e=function(a){f.event.simulate(b,a.target,f.event.fix(a),!0)};f.event.special[b]={setup:function(){d++===0&&c.addEventListener(a,e,!0)},teardown:function(){--d===0&&c.removeEventListener(a,e,!0)}}}),f.fn.extend({on:function(a,c,d,e,g){var h,i;if(typeof a=="object"){typeof c!="string"&&(d=d||c,c=b);for(i in a)this.on(i,c,d,a[i],g);return this}d==null&&e==null?(e=c,d=c=b):e==null&&(typeof c=="string"?(e=d,d=b):(e=d,d=c,c=b));if(e===!1)e=J;else if(!e)return this;g===1&&(h=e,e=function(a){f().off(a);return h.apply(this,arguments)},e.guid=h.guid||(h.guid=f.guid++));return this.each(function(){f.event.add(this,a,e,d,c)})},one:function(a,b,c,d){return this.on(a,b,c,d,1)},off:function(a,c,d){if(a&&a.preventDefault&&a.handleObj){var e=a.handleObj;f(a.delegateTarget).off(e.namespace?e.origType+"."+e.namespace:e.origType,e.selector,e.handler);return this}if(typeof a=="object"){for(var g in a)this.off(g,c,a[g]);return this}if(c===!1||typeof c=="function")d=c,c=b;d===!1&&(d=J);return this.each(function(){f.event.remove(this,a,d,c)})},bind:function(a,b,c){return this.on(a,null,b,c)},unbind:function(a,b){return this.off(a,null,b)},live:function(a,b,c){f(this.context).on(a,this.selector,b,c);return this},die:function(a,b){f(this.context).off(a,this.selector||"**",b);return this},delegate:function(a,b,c,d){return this.on(b,a,c,d)},undelegate:function(a,b,c){return arguments.length==1?this.off(a,"**"):this.off(b,a,c)},trigger:function(a,b){return this.each(function(){f.event.trigger(a,b,this)})},triggerHandler:function(a,b){if(this[0])return f.event.trigger(a,b,this[0],!0)},toggle:function(a){var b=arguments,c=a.guid||f.guid++,d=0,e=function(c){var e=(f._data(this,"lastToggle"+a.guid)||0)%d;f._data(this,"lastToggle"+a.guid,e+1),c.preventDefault();return b[e].apply(this,arguments)||!1};e.guid=c;while(d<b.length)b[d++].guid=c;return this.click(e)},hover:function(a,b){return this.mouseenter(a).mouseleave(b||a)}}),f.each("blur focus focusin focusout load resize scroll unload click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup error contextmenu".split(" "),function(a,b){f.fn[b]=function(a,c){c==null&&(c=a,a=null);return arguments.length>0?this.on(b,null,a,c):this.trigger(b)},f.attrFn&&(f.attrFn[b]=!0),C.test(b)&&(f.event.fixHooks[b]=f.event.keyHooks),D.test(b)&&(f.event.fixHooks[b]=f.event.mouseHooks)}),function(){function x(a,b,c,e,f,g){for(var h=0,i=e.length;h<i;h++){var j=e[h];if(j){var k=!1;j=j[a];while(j){if(j[d]===c){k=e[j.sizset];break}if(j.nodeType===1){g||(j[d]=c,j.sizset=h);if(typeof b!="string"){if(j===b){k=!0;break}}else if(m.filter(b,[j]).length>0){k=j;break}}j=j[a]}e[h]=k}}}function w(a,b,c,e,f,g){for(var h=0,i=e.length;h<i;h++){var j=e[h];if(j){var k=!1;j=j[a];while(j){if(j[d]===c){k=e[j.sizset];break}j.nodeType===1&&!g&&(j[d]=c,j.sizset=h);if(j.nodeName.toLowerCase()===b){k=j;break}j=j[a]}e[h]=k}}}var a=/((?:\((?:\([^()]+\)|[^()]+)+\)|\[(?:\[[^\[\]]*\]|['"][^'"]*['"]|[^\[\]'"]+)+\]|\\.|[^ >+~,(\[\\]+)+|[>+~])(\s*,\s*)?((?:.|\r|\n)*)/g,d="sizcache"+(Math.random()+"").replace(".",""),e=0,g=Object.prototype.toString,h=!1,i=!0,j=/\\/g,k=/\r\n/g,l=/\W/;[0,0].sort(function(){i=!1;return 0});var m=function(b,d,e,f){e=e||[],d=d||c;var h=d;if(d.nodeType!==1&&d.nodeType!==9)return[];if(!b||typeof b!="string")return e;var i,j,k,l,n,q,r,t,u=!0,v=m.isXML(d),w=[],x=b;do{a.exec(""),i=a.exec(x);if(i){x=i[3],w.push(i[1]);if(i[2]){l=i[3];break}}}while(i);if(w.length>1&&p.exec(b))if(w.length===2&&o.relative[w[0]])j=y(w[0]+w[1],d,f);else{j=o.relative[w[0]]?[d]:m(w.shift(),d);while(w.length)b=w.shift(),o.relative[b]&&(b+=w.shift()),j=y(b,j,f)}else{!f&&w.length>1&&d.nodeType===9&&!v&&o.match.ID.test(w[0])&&!o.match.ID.test(w[w.length-1])&&(n=m.find(w.shift(),d,v),d=n.expr?m.filter(n.expr,n.set)[0]:n.set[0]);if(d){n=f?{expr:w.pop(),set:s(f)}:m.find(w.pop(),w.length===1&&(w[0]==="~"||w[0]==="+")&&d.parentNode?d.parentNode:d,v),j=n.expr?m.filter(n.expr,n.set):n.set,w.length>0?k=s(j):u=!1;while(w.length)q=w.pop(),r=q,o.relative[q]?r=w.pop():q="",r==null&&(r=d),o.relative[q](k,r,v)}else k=w=[]}k||(k=j),k||m.error(q||b);if(g.call(k)==="[object Array]")if(!u)e.push.apply(e,k);else if(d&&d.nodeType===1)for(t=0;k[t]!=null;t++)k[t]&&(k[t]===!0||k[t].nodeType===1&&m.contains(d,k[t]))&&e.push(j[t]);else for(t=0;k[t]!=null;t++)k[t]&&k[t].nodeType===1&&e.push(j[t]);else s(k,e);l&&(m(l,h,e,f),m.uniqueSort(e));return e};m.uniqueSort=function(a){if(u){h=i,a.sort(u);if(h)for(var b=1;b<a.length;b++)a[b]===a[b-1]&&a.splice(b--,1)}return a},m.matches=function(a,b){return m(a,null,null,b)},m.matchesSelector=function(a,b){return m(b,null,null,[a]).length>0},m.find=function(a,b,c){var d,e,f,g,h,i;if(!a)return[];for(e=0,f=o.order.length;e<f;e++){h=o.order[e];if(g=o.leftMatch[h].exec(a)){i=g[1],g.splice(1,1);if(i.substr(i.length-1)!=="\\"){g[1]=(g[1]||"").replace(j,""),d=o.find[h](g,b,c);if(d!=null){a=a.replace(o.match[h],"");break}}}}d||(d=typeof b.getElementsByTagName!="undefined"?b.getElementsByTagName("*"):[]);return{set:d,expr:a}},m.filter=function(a,c,d,e){var f,g,h,i,j,k,l,n,p,q=a,r=[],s=c,t=c&&c[0]&&m.isXML(c[0]);while(a&&c.length){for(h in o.filter)if((f=o.leftMatch[h].exec(a))!=null&&f[2]){k=o.filter[h],l=f[1],g=!1,f.splice(1,1);if(l.substr(l.length-1)==="\\")continue;s===r&&(r=[]);if(o.preFilter[h]){f=o.preFilter[h](f,s,d,r,e,t);if(!f)g=i=!0;else if(f===!0)continue}if(f)for(n=0;(j=s[n])!=null;n++)j&&(i=k(j,f,n,s),p=e^i,d&&i!=null?p?g=!0:s[n]=!1:p&&(r.push(j),g=!0));if(i!==b){d||(s=r),a=a.replace(o.match[h],"");if(!g)return[];break}}if(a===q)if(g==null)m.error(a);else break;q=a}return s},m.error=function(a){throw new Error("Syntax error, unrecognized expression: "+a)};var n=m.getText=function(a){var b,c,d=a.nodeType,e="";if(d){if(d===1||d===9||d===11){if(typeof a.textContent=="string")return a.textContent;if(typeof a.innerText=="string")return a.innerText.replace(k,"");for(a=a.firstChild;a;a=a.nextSibling)e+=n(a)}else if(d===3||d===4)return a.nodeValue}else for(b=0;c=a[b];b++)c.nodeType!==8&&(e+=n(c));return e},o=m.selectors={order:["ID","NAME","TAG"],match:{ID:/#((?:[\w\u00c0-\uFFFF\-]|\\.)+)/,CLASS:/\.((?:[\w\u00c0-\uFFFF\-]|\\.)+)/,NAME:/\[name=['"]*((?:[\w\u00c0-\uFFFF\-]|\\.)+)['"]*\]/,ATTR:/\[\s*((?:[\w\u00c0-\uFFFF\-]|\\.)+)\s*(?:(\S?=)\s*(?:(['"])(.*?)\3|(#?(?:[\w\u00c0-\uFFFF\-]|\\.)*)|)|)\s*\]/,TAG:/^((?:[\w\u00c0-\uFFFF\*\-]|\\.)+)/,CHILD:/:(only|nth|last|first)-child(?:\(\s*(even|odd|(?:[+\-]?\d+|(?:[+\-]?\d*)?n\s*(?:[+\-]\s*\d+)?))\s*\))?/,POS:/:(nth|eq|gt|lt|first|last|even|odd)(?:\((\d*)\))?(?=[^\-]|$)/,PSEUDO:/:((?:[\w\u00c0-\uFFFF\-]|\\.)+)(?:\((['"]?)((?:\([^\)]+\)|[^\(\)]*)+)\2\))?/},leftMatch:{},attrMap:{"class":"className","for":"htmlFor"},attrHandle:{href:function(a){return a.getAttribute("href")},type:function(a){return a.getAttribute("type")}},relative:{"+":function(a,b){var c=typeof b=="string",d=c&&!l.test(b),e=c&&!d;d&&(b=b.toLowerCase());for(var f=0,g=a.length,h;f<g;f++)if(h=a[f]){while((h=h.previousSibling)&&h.nodeType!==1);a[f]=e||h&&h.nodeName.toLowerCase()===b?h||!1:h===b}e&&m.filter(b,a,!0)},">":function(a,b){var c,d=typeof b=="string",e=0,f=a.length;if(d&&!l.test(b)){b=b.toLowerCase();for(;e<f;e++){c=a[e];if(c){var g=c.parentNode;a[e]=g.nodeName.toLowerCase()===b?g:!1}}}else{for(;e<f;e++)c=a[e],c&&(a[e]=d?c.parentNode:c.parentNode===b);d&&m.filter(b,a,!0)}},"":function(a,b,c){var d,f=e++,g=x;typeof b=="string"&&!l.test(b)&&(b=b.toLowerCase(),d=b,g=w),g("parentNode",b,f,a,d,c)},"~":function(a,b,c){var d,f=e++,g=x;typeof b=="string"&&!l.test(b)&&(b=b.toLowerCase(),d=b,g=w),g("previousSibling",b,f,a,d,c)}},find:{ID:function(a,b,c){if(typeof b.getElementById!="undefined"&&!c){var d=b.getElementById(a[1]);return d&&d.parentNode?[d]:[]}},NAME:function(a,b){if(typeof b.getElementsByName!="undefined"){var c=[],d=b.getElementsByName(a[1]);for(var e=0,f=d.length;e<f;e++)d[e].getAttribute("name")===a[1]&&c.push(d[e]);return c.length===0?null:c}},TAG:function(a,b){if(typeof b.getElementsByTagName!="undefined")return b.getElementsByTagName(a[1])}},preFilter:{CLASS:function(a,b,c,d,e,f){a=" "+a[1].replace(j,"")+" ";if(f)return a;for(var g=0,h;(h=b[g])!=null;g++)h&&(e^(h.className&&(" "+h.className+" ").replace(/[\t\n\r]/g," ").indexOf(a)>=0)?c||d.push(h):c&&(b[g]=!1));return!1},ID:function(a){return a[1].replace(j,"")},TAG:function(a,b){return a[1].replace(j,"").toLowerCase()},CHILD:function(a){if(a[1]==="nth"){a[2]||m.error(a[0]),a[2]=a[2].replace(/^\+|\s*/g,"");var b=/(-?)(\d*)(?:n([+\-]?\d*))?/.exec(a[2]==="even"&&"2n"||a[2]==="odd"&&"2n+1"||!/\D/.test(a[2])&&"0n+"+a[2]||a[2]);a[2]=b[1]+(b[2]||1)-0,a[3]=b[3]-0}else a[2]&&m.error(a[0]);a[0]=e++;return a},ATTR:function(a,b,c,d,e,f){var g=a[1]=a[1].replace(j,"");!f&&o.attrMap[g]&&(a[1]=o.attrMap[g]),a[4]=(a[4]||a[5]||"").replace(j,""),a[2]==="~="&&(a[4]=" "+a[4]+" ");return a},PSEUDO:function(b,c,d,e,f){if(b[1]==="not")if((a.exec(b[3])||"").length>1||/^\w/.test(b[3]))b[3]=m(b[3],null,null,c);else{var g=m.filter(b[3],c,d,!0^f);d||e.push.apply(e,g);return!1}else if(o.match.POS.test(b[0])||o.match.CHILD.test(b[0]))return!0;return b},POS:function(a){a.unshift(!0);return a}},filters:{enabled:function(a){return a.disabled===!1&&a.type!=="hidden"},disabled:function(a){return a.disabled===!0},checked:function(a){return a.checked===!0},selected:function(a){a.parentNode&&a.parentNode.selectedIndex;return a.selected===!0},parent:function(a){return!!a.firstChild},empty:function(a){return!a.firstChild},has:function(a,b,c){return!!m(c[3],a).length},header:function(a){return/h\d/i.test(a.nodeName)},text:function(a){var b=a.getAttribute("type"),c=a.type;return a.nodeName.toLowerCase()==="input"&&"text"===c&&(b===c||b===null)},radio:function(a){return a.nodeName.toLowerCase()==="input"&&"radio"===a.type},checkbox:function(a){return a.nodeName.toLowerCase()==="input"&&"checkbox"===a.type},file:function(a){return a.nodeName.toLowerCase()==="input"&&"file"===a.type},password:function(a){return a.nodeName.toLowerCase()==="input"&&"password"===a.type},submit:function(a){var b=a.nodeName.toLowerCase();return(b==="input"||b==="button")&&"submit"===a.type},image:function(a){return a.nodeName.toLowerCase()==="input"&&"image"===a.type},reset:function(a){var b=a.nodeName.toLowerCase();return(b==="input"||b==="button")&&"reset"===a.type},button:function(a){var b=a.nodeName.toLowerCase();return b==="input"&&"button"===a.type||b==="button"},input:function(a){return/input|select|textarea|button/i.test(a.nodeName)},focus:function(a){return a===a.ownerDocument.activeElement}},setFilters:{first:function(a,b){return b===0},last:function(a,b,c,d){return b===d.length-1},even:function(a,b){return b%2===0},odd:function(a,b){return b%2===1},lt:function(a,b,c){return b<c[3]-0},gt:function(a,b,c){return b>c[3]-0},nth:function(a,b,c){return c[3]-0===b},eq:function(a,b,c){return c[3]-0===b}},filter:{PSEUDO:function(a,b,c,d){var e=b[1],f=o.filters[e];if(f)return f(a,c,b,d);if(e==="contains")return(a.textContent||a.innerText||n([a])||"").indexOf(b[3])>=0;if(e==="not"){var g=b[3];for(var h=0,i=g.length;h<i;h++)if(g[h]===a)return!1;return!0}m.error(e)},CHILD:function(a,b){var c,e,f,g,h,i,j,k=b[1],l=a;switch(k){case"only":case"first":while(l=l.previousSibling)if(l.nodeType===1)return!1;if(k==="first")return!0;l=a;case"last":while(l=l.nextSibling)if(l.nodeType===1)return!1;return!0;case"nth":c=b[2],e=b[3];if(c===1&&e===0)return!0;f=b[0],g=a.parentNode;if(g&&(g[d]!==f||!a.nodeIndex)){i=0;for(l=g.firstChild;l;l=l.nextSibling)l.nodeType===1&&(l.nodeIndex=++i);g[d]=f}j=a.nodeIndex-e;return c===0?j===0:j%c===0&&j/c>=0}},ID:function(a,b){return a.nodeType===1&&a.getAttribute("id")===b},TAG:function(a,b){return b==="*"&&a.nodeType===1||!!a.nodeName&&a.nodeName.toLowerCase()===b},CLASS:function(a,b){return(" "+(a.className||a.getAttribute("class"))+" ").indexOf(b)>-1},ATTR:function(a,b){var c=b[1],d=m.attr?m.attr(a,c):o.attrHandle[c]?o.attrHandle[c](a):a[c]!=null?a[c]:a.getAttribute(c),e=d+"",f=b[2],g=b[4];return d==null?f==="!=":!f&&m.attr?d!=null:f==="="?e===g:f==="*="?e.indexOf(g)>=0:f==="~="?(" "+e+" ").indexOf(g)>=0:g?f==="!="?e!==g:f==="^="?e.indexOf(g)===0:f==="$="?e.substr(e.length-g.length)===g:f==="|="?e===g||e.substr(0,g.length+1)===g+"-":!1:e&&d!==!1},POS:function(a,b,c,d){var e=b[2],f=o.setFilters[e];if(f)return f(a,c,b,d)}}},p=o.match.POS,q=function(a,b){return"\\"+(b-0+1)};for(var r in o.match)o.match[r]=new RegExp(o.match[r].source+/(?![^\[]*\])(?![^\(]*\))/.source),o.leftMatch[r]=new RegExp(/(^(?:.|\r|\n)*?)/.source+o.match[r].source.replace(/\\(\d+)/g,q));o.match.globalPOS=p;var s=function(a,b){a=Array.prototype.slice.call(a,0);if(b){b.push.apply(b,a);return b}return a};try{Array.prototype.slice.call(c.documentElement.childNodes,0)[0].nodeType}catch(t){s=function(a,b){var c=0,d=b||[];if(g.call(a)==="[object Array]")Array.prototype.push.apply(d,a);else if(typeof a.length=="number")for(var e=a.length;c<e;c++)d.push(a[c]);else for(;a[c];c++)d.push(a[c]);return d}}var u,v;c.documentElement.compareDocumentPosition?u=function(a,b){if(a===b){h=!0;return 0}if(!a.compareDocumentPosition||!b.compareDocumentPosition)return a.compareDocumentPosition?-1:1;return a.compareDocumentPosition(b)&4?-1:1}:(u=function(a,b){if(a===b){h=!0;return 0}if(a.sourceIndex&&b.sourceIndex)return a.sourceIndex-b.sourceIndex;var c,d,e=[],f=[],g=a.parentNode,i=b.parentNode,j=g;if(g===i)return v(a,b);if(!g)return-1;if(!i)return 1;while(j)e.unshift(j),j=j.parentNode;j=i;while(j)f.unshift(j),j=j.parentNode;c=e.length,d=f.length;for(var k=0;k<c&&k<d;k++)if(e[k]!==f[k])return v(e[k],f[k]);return k===c?v(a,f[k],-1):v(e[k],b,1)},v=function(a,b,c){if(a===b)return c;var d=a.nextSibling;while(d){if(d===b)return-1;d=d.nextSibling}return 1}),function(){var a=c.createElement("div"),d="script"+(new Date).getTime(),e=c.documentElement;a.innerHTML="<a name='"+d+"'/>",e.insertBefore(a,e.firstChild),c.getElementById(d)&&(o.find.ID=function(a,c,d){if(typeof c.getElementById!="undefined"&&!d){var e=c.getElementById(a[1]);return e?e.id===a[1]||typeof e.getAttributeNode!="undefined"&&e.getAttributeNode("id").nodeValue===a[1]?[e]:b:[]}},o.filter.ID=function(a,b){var c=typeof a.getAttributeNode!="undefined"&&a.getAttributeNode("id");return a.nodeType===1&&c&&c.nodeValue===b}),e.removeChild(a),e=a=null}(),function(){var a=c.createElement("div");a.appendChild(c.createComment("")),a.getElementsByTagName("*").length>0&&(o.find.TAG=function(a,b){var c=b.getElementsByTagName(a[1]);if(a[1]==="*"){var d=[];for(var e=0;c[e];e++)c[e].nodeType===1&&d.push(c[e]);c=d}return c}),a.innerHTML="<a href='#'></a>",a.firstChild&&typeof a.firstChild.getAttribute!="undefined"&&a.firstChild.getAttribute("href")!=="#"&&(o.attrHandle.href=function(a){return a.getAttribute("href",2)}),a=null}(),c.querySelectorAll&&function(){var a=m,b=c.createElement("div"),d="__sizzle__";b.innerHTML="<p class='TEST'></p>";if(!b.querySelectorAll||b.querySelectorAll(".TEST").length!==0){m=function(b,e,f,g){e=e||c;if(!g&&!m.isXML(e)){var h=/^(\w+$)|^\.([\w\-]+$)|^#([\w\-]+$)/.exec(b);if(h&&(e.nodeType===1||e.nodeType===9)){if(h[1])return s(e.getElementsByTagName(b),f);if(h[2]&&o.find.CLASS&&e.getElementsByClassName)return s(e.getElementsByClassName(h[2]),f)}if(e.nodeType===9){if(b==="body"&&e.body)return s([e.body],f);if(h&&h[3]){var i=e.getElementById(h[3]);if(!i||!i.parentNode)return s([],f);if(i.id===h[3])return s([i],f)}try{return s(e.querySelectorAll(b),f)}catch(j){}}else if(e.nodeType===1&&e.nodeName.toLowerCase()!=="object"){var k=e,l=e.getAttribute("id"),n=l||d,p=e.parentNode,q=/^\s*[+~]/.test(b);l?n=n.replace(/'/g,"\\$&"):e.setAttribute("id",n),q&&p&&(e=e.parentNode);try{if(!q||p)return s(e.querySelectorAll("[id='"+n+"'] "+b),f)}catch(r){}finally{l||k.removeAttribute("id")}}}return a(b,e,f,g)};for(var e in a)m[e]=a[e];b=null}}(),function(){var a=c.documentElement,b=a.matchesSelector||a.mozMatchesSelector||a.webkitMatchesSelector||a.msMatchesSelector;if(b){var d=!b.call(c.createElement("div"),"div"),e=!1;try{b.call(c.documentElement,"[test!='']:sizzle")}catch(f){e=!0}m.matchesSelector=function(a,c){c=c.replace(/\=\s*([^'"\]]*)\s*\]/g,"='$1']");if(!m.isXML(a))try{if(e||!o.match.PSEUDO.test(c)&&!/!=/.test(c)){var f=b.call(a,c);if(f||!d||a.document&&a.document.nodeType!==11)return f}}catch(g){}return m(c,null,null,[a]).length>0}}}(),function(){var a=c.createElement("div");a.innerHTML="<div class='test e'></div><div class='test'></div>";if(!!a.getElementsByClassName&&a.getElementsByClassName("e").length!==0){a.lastChild.className="e";if(a.getElementsByClassName("e").length===1)return;o.order.splice(1,0,"CLASS"),o.find.CLASS=function(a,b,c){if(typeof b.getElementsByClassName!="undefined"&&!c)return b.getElementsByClassName(a[1])},a=null}}(),c.documentElement.contains?m.contains=function(a,b){return a!==b&&(a.contains?a.contains(b):!0)}:c.documentElement.compareDocumentPosition?m.contains=function(a,b){return!!(a.compareDocumentPosition(b)&16)}:m.contains=function(){return!1},m.isXML=function(a){var b=(a?a.ownerDocument||a:0).documentElement;return b?b.nodeName!=="HTML":!1};var y=function(a,b,c){var d,e=[],f="",g=b.nodeType?[b]:b;while(d=o.match.PSEUDO.exec(a))f+=d[0],a=a.replace(o.match.PSEUDO,"");a=o.relative[a]?a+"*":a;for(var h=0,i=g.length;h<i;h++)m(a,g[h],e,c);return m.filter(f,e)};m.attr=f.attr,m.selectors.attrMap={},f.find=m,f.expr=m.selectors,f.expr[":"]=f.expr.filters,f.unique=m.uniqueSort,f.text=m.getText,f.isXMLDoc=m.isXML,f.contains=m.contains}();var L=/Until$/,M=/^(?:parents|prevUntil|prevAll)/,N=/,/,O=/^.[^:#\[\.,]*$/,P=Array.prototype.slice,Q=f.expr.match.globalPOS,R={children:!0,contents:!0,next:!0,prev:!0};f.fn.extend({find:function(a){var b=this,c,d;if(typeof a!="string")return f(a).filter(function(){for(c=0,d=b.length;c<d;c++)if(f.contains(b[c],this))return!0});var e=this.pushStack("","find",a),g,h,i;for(c=0,d=this.length;c<d;c++){g=e.length,f.find(a,this[c],e);if(c>0)for(h=g;h<e.length;h++)for(i=0;i<g;i++)if(e[i]===e[h]){e.splice(h--,1);break}}return e},has:function(a){var b=f(a);return this.filter(function(){for(var a=0,c=b.length;a<c;a++)if(f.contains(this,b[a]))return!0})},not:function(a){return this.pushStack(T(this,a,!1),"not",a)},filter:function(a){return this.pushStack(T(this,a,!0),"filter",a)},is:function(a){return!!a&&(typeof a=="string"?Q.test(a)?f(a,this.context).index(this[0])>=0:f.filter(a,this).length>0:this.filter(a).length>0)},closest:function(a,b){var c=[],d,e,g=this[0];if(f.isArray(a)){var h=1;while(g&&g.ownerDocument&&g!==b){for(d=0;d<a.length;d++)f(g).is(a[d])&&c.push({selector:a[d],elem:g,level:h});g=g.parentNode,h++}return c}var i=Q.test(a)||typeof a!="string"?f(a,b||this.context):0;for(d=0,e=this.length;d<e;d++){g=this[d];while(g){if(i?i.index(g)>-1:f.find.matchesSelector(g,a)){c.push(g);break}g=g.parentNode;if(!g||!g.ownerDocument||g===b||g.nodeType===11)break}}c=c.length>1?f.unique(c):c;return this.pushStack(c,"closest",a)},index:function(a){if(!a)return this[0]&&this[0].parentNode?this.prevAll().length:-1;if(typeof a=="string")return f.inArray(this[0],f(a));return f.inArray(a.jquery?a[0]:a,this)},add:function(a,b){var c=typeof a=="string"?f(a,b):f.makeArray(a&&a.nodeType?[a]:a),d=f.merge(this.get(),c);return this.pushStack(S(c[0])||S(d[0])?d:f.unique(d))},andSelf:function(){return this.add(this.prevObject)}}),f.each({parent:function(a){var b=a.parentNode;return b&&b.nodeType!==11?b:null},parents:function(a){return f.dir(a,"parentNode")},parentsUntil:function(a,b,c){return f.dir(a,"parentNode",c)},next:function(a){return f.nth(a,2,"nextSibling")},prev:function(a){return f.nth(a,2,"previousSibling")},nextAll:function(a){return f.dir(a,"nextSibling")},prevAll:function(a){return f.dir(a,"previousSibling")},nextUntil:function(a,b,c){return f.dir(a,"nextSibling",c)},prevUntil:function(a,b,c){return f.dir(a,"previousSibling",c)},siblings:function(a){return f.sibling((a.parentNode||{}).firstChild,a)},children:function(a){return f.sibling(a.firstChild)},contents:function(a){return f.nodeName(a,"iframe")?a.contentDocument||a.contentWindow.document:f.makeArray(a.childNodes)}},function(a,b){f.fn[a]=function(c,d){var e=f.map(this,b,c);L.test(a)||(d=c),d&&typeof d=="string"&&(e=f.filter(d,e)),e=this.length>1&&!R[a]?f.unique(e):e,(this.length>1||N.test(d))&&M.test(a)&&(e=e.reverse());return this.pushStack(e,a,P.call(arguments).join(","))}}),f.extend({filter:function(a,b,c){c&&(a=":not("+a+")");return b.length===1?f.find.matchesSelector(b[0],a)?[b[0]]:[]:f.find.matches(a,b)},dir:function(a,c,d){var e=[],g=a[c];while(g&&g.nodeType!==9&&(d===b||g.nodeType!==1||!f(g).is(d)))g.nodeType===1&&e.push(g),g=g[c];return e},nth:function(a,b,c,d){b=b||1;var e=0;for(;a;a=a[c])if(a.nodeType===1&&++e===b)break;return a},sibling:function(a,b){var c=[];for(;a;a=a.nextSibling)a.nodeType===1&&a!==b&&c.push(a);return c}});var V="abbr|article|aside|audio|bdi|canvas|data|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",W=/ jQuery\d+="(?:\d+|null)"/g,X=/^\s+/,Y=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/ig,Z=/<([\w:]+)/,$=/<tbody/i,_=/<|&#?\w+;/,ba=/<(?:script|style)/i,bb=/<(?:script|object|embed|option|style)/i,bc=new RegExp("<(?:"+V+")[\\s/>]","i"),bd=/checked\s*(?:[^=]|=\s*.checked.)/i,be=/\/(java|ecma)script/i,bf=/^\s*<!(?:\[CDATA\[|\-\-)/,bg={option:[1,"<select multiple='multiple'>","</select>"],legend:[1,"<fieldset>","</fieldset>"],thead:[1,"<table>","</table>"],tr:[2,"<table><tbody>","</tbody></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],col:[2,"<table><tbody></tbody><colgroup>","</colgroup></table>"],area:[1,"<map>","</map>"],_default:[0,"",""]},bh=U(c);bg.optgroup=bg.option,bg.tbody=bg.tfoot=bg.colgroup=bg.caption=bg.thead,bg.th=bg.td,f.support.htmlSerialize||(bg._default=[1,"div<div>","</div>"]),f.fn.extend({text:function(a){return f.access(this,function(a){return a===b?f.text(this):this.empty().append((this[0]&&this[0].ownerDocument||c).createTextNode(a))},null,a,arguments.length)},wrapAll:function(a){if(f.isFunction(a))return this.each(function(b){f(this).wrapAll(a.call(this,b))});if(this[0]){var b=f(a,this[0].ownerDocument).eq(0).clone(!0);this[0].parentNode&&b.insertBefore(this[0]),b.map(function(){var a=this;while(a.firstChild&&a.firstChild.nodeType===1)a=a.firstChild;return a}).append(this)}return this},wrapInner:function(a){if(f.isFunction(a))return this.each(function(b){f(this).wrapInner(a.call(this,b))});return this.each(function(){var b=f(this),c=b.contents();c.length?c.wrapAll(a):b.append(a)})},wrap:function(a){var b=f.isFunction(a);return this.each(function(c){f(this).wrapAll(b?a.call(this,c):a)})},unwrap:function(){return this.parent().each(function(){f.nodeName(this,"body")||f(this).replaceWith(this.childNodes)}).end()},append:function(){return this.domManip(arguments,!0,function(a){this.nodeType===1&&this.appendChild(a)})},prepend:function(){return this.domManip(arguments,!0,function(a){this.nodeType===1&&this.insertBefore(a,this.firstChild)})},before:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,!1,function(a){this.parentNode.insertBefore(a,this)});if(arguments.length){var a=f
-.clean(arguments);a.push.apply(a,this.toArray());return this.pushStack(a,"before",arguments)}},after:function(){if(this[0]&&this[0].parentNode)return this.domManip(arguments,!1,function(a){this.parentNode.insertBefore(a,this.nextSibling)});if(arguments.length){var a=this.pushStack(this,"after",arguments);a.push.apply(a,f.clean(arguments));return a}},remove:function(a,b){for(var c=0,d;(d=this[c])!=null;c++)if(!a||f.filter(a,[d]).length)!b&&d.nodeType===1&&(f.cleanData(d.getElementsByTagName("*")),f.cleanData([d])),d.parentNode&&d.parentNode.removeChild(d);return this},empty:function(){for(var a=0,b;(b=this[a])!=null;a++){b.nodeType===1&&f.cleanData(b.getElementsByTagName("*"));while(b.firstChild)b.removeChild(b.firstChild)}return this},clone:function(a,b){a=a==null?!1:a,b=b==null?a:b;return this.map(function(){return f.clone(this,a,b)})},html:function(a){return f.access(this,function(a){var c=this[0]||{},d=0,e=this.length;if(a===b)return c.nodeType===1?c.innerHTML.replace(W,""):null;if(typeof a=="string"&&!ba.test(a)&&(f.support.leadingWhitespace||!X.test(a))&&!bg[(Z.exec(a)||["",""])[1].toLowerCase()]){a=a.replace(Y,"<$1></$2>");try{for(;d<e;d++)c=this[d]||{},c.nodeType===1&&(f.cleanData(c.getElementsByTagName("*")),c.innerHTML=a);c=0}catch(g){}}c&&this.empty().append(a)},null,a,arguments.length)},replaceWith:function(a){if(this[0]&&this[0].parentNode){if(f.isFunction(a))return this.each(function(b){var c=f(this),d=c.html();c.replaceWith(a.call(this,b,d))});typeof a!="string"&&(a=f(a).detach());return this.each(function(){var b=this.nextSibling,c=this.parentNode;f(this).remove(),b?f(b).before(a):f(c).append(a)})}return this.length?this.pushStack(f(f.isFunction(a)?a():a),"replaceWith",a):this},detach:function(a){return this.remove(a,!0)},domManip:function(a,c,d){var e,g,h,i,j=a[0],k=[];if(!f.support.checkClone&&arguments.length===3&&typeof j=="string"&&bd.test(j))return this.each(function(){f(this).domManip(a,c,d,!0)});if(f.isFunction(j))return this.each(function(e){var g=f(this);a[0]=j.call(this,e,c?g.html():b),g.domManip(a,c,d)});if(this[0]){i=j&&j.parentNode,f.support.parentNode&&i&&i.nodeType===11&&i.childNodes.length===this.length?e={fragment:i}:e=f.buildFragment(a,this,k),h=e.fragment,h.childNodes.length===1?g=h=h.firstChild:g=h.firstChild;if(g){c=c&&f.nodeName(g,"tr");for(var l=0,m=this.length,n=m-1;l<m;l++)d.call(c?bi(this[l],g):this[l],e.cacheable||m>1&&l<n?f.clone(h,!0,!0):h)}k.length&&f.each(k,function(a,b){b.src?f.ajax({type:"GET",global:!1,url:b.src,async:!1,dataType:"script"}):f.globalEval((b.text||b.textContent||b.innerHTML||"").replace(bf,"/*$0*/")),b.parentNode&&b.parentNode.removeChild(b)})}return this}}),f.buildFragment=function(a,b,d){var e,g,h,i,j=a[0];b&&b[0]&&(i=b[0].ownerDocument||b[0]),i.createDocumentFragment||(i=c),a.length===1&&typeof j=="string"&&j.length<512&&i===c&&j.charAt(0)==="<"&&!bb.test(j)&&(f.support.checkClone||!bd.test(j))&&(f.support.html5Clone||!bc.test(j))&&(g=!0,h=f.fragments[j],h&&h!==1&&(e=h)),e||(e=i.createDocumentFragment(),f.clean(a,i,e,d)),g&&(f.fragments[j]=h?e:1);return{fragment:e,cacheable:g}},f.fragments={},f.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(a,b){f.fn[a]=function(c){var d=[],e=f(c),g=this.length===1&&this[0].parentNode;if(g&&g.nodeType===11&&g.childNodes.length===1&&e.length===1){e[b](this[0]);return this}for(var h=0,i=e.length;h<i;h++){var j=(h>0?this.clone(!0):this).get();f(e[h])[b](j),d=d.concat(j)}return this.pushStack(d,a,e.selector)}}),f.extend({clone:function(a,b,c){var d,e,g,h=f.support.html5Clone||f.isXMLDoc(a)||!bc.test("<"+a.nodeName+">")?a.cloneNode(!0):bo(a);if((!f.support.noCloneEvent||!f.support.noCloneChecked)&&(a.nodeType===1||a.nodeType===11)&&!f.isXMLDoc(a)){bk(a,h),d=bl(a),e=bl(h);for(g=0;d[g];++g)e[g]&&bk(d[g],e[g])}if(b){bj(a,h);if(c){d=bl(a),e=bl(h);for(g=0;d[g];++g)bj(d[g],e[g])}}d=e=null;return h},clean:function(a,b,d,e){var g,h,i,j=[];b=b||c,typeof b.createElement=="undefined"&&(b=b.ownerDocument||b[0]&&b[0].ownerDocument||c);for(var k=0,l;(l=a[k])!=null;k++){typeof l=="number"&&(l+="");if(!l)continue;if(typeof l=="string")if(!_.test(l))l=b.createTextNode(l);else{l=l.replace(Y,"<$1></$2>");var m=(Z.exec(l)||["",""])[1].toLowerCase(),n=bg[m]||bg._default,o=n[0],p=b.createElement("div"),q=bh.childNodes,r;b===c?bh.appendChild(p):U(b).appendChild(p),p.innerHTML=n[1]+l+n[2];while(o--)p=p.lastChild;if(!f.support.tbody){var s=$.test(l),t=m==="table"&&!s?p.firstChild&&p.firstChild.childNodes:n[1]==="<table>"&&!s?p.childNodes:[];for(i=t.length-1;i>=0;--i)f.nodeName(t[i],"tbody")&&!t[i].childNodes.length&&t[i].parentNode.removeChild(t[i])}!f.support.leadingWhitespace&&X.test(l)&&p.insertBefore(b.createTextNode(X.exec(l)[0]),p.firstChild),l=p.childNodes,p&&(p.parentNode.removeChild(p),q.length>0&&(r=q[q.length-1],r&&r.parentNode&&r.parentNode.removeChild(r)))}var u;if(!f.support.appendChecked)if(l[0]&&typeof (u=l.length)=="number")for(i=0;i<u;i++)bn(l[i]);else bn(l);l.nodeType?j.push(l):j=f.merge(j,l)}if(d){g=function(a){return!a.type||be.test(a.type)};for(k=0;j[k];k++){h=j[k];if(e&&f.nodeName(h,"script")&&(!h.type||be.test(h.type)))e.push(h.parentNode?h.parentNode.removeChild(h):h);else{if(h.nodeType===1){var v=f.grep(h.getElementsByTagName("script"),g);j.splice.apply(j,[k+1,0].concat(v))}d.appendChild(h)}}}return j},cleanData:function(a){var b,c,d=f.cache,e=f.event.special,g=f.support.deleteExpando;for(var h=0,i;(i=a[h])!=null;h++){if(i.nodeName&&f.noData[i.nodeName.toLowerCase()])continue;c=i[f.expando];if(c){b=d[c];if(b&&b.events){for(var j in b.events)e[j]?f.event.remove(i,j):f.removeEvent(i,j,b.handle);b.handle&&(b.handle.elem=null)}g?delete i[f.expando]:i.removeAttribute&&i.removeAttribute(f.expando),delete d[c]}}}});var bp=/alpha\([^)]*\)/i,bq=/opacity=([^)]*)/,br=/([A-Z]|^ms)/g,bs=/^[\-+]?(?:\d*\.)?\d+$/i,bt=/^-?(?:\d*\.)?\d+(?!px)[^\d\s]+$/i,bu=/^([\-+])=([\-+.\de]+)/,bv=/^margin/,bw={position:"absolute",visibility:"hidden",display:"block"},bx=["Top","Right","Bottom","Left"],by,bz,bA;f.fn.css=function(a,c){return f.access(this,function(a,c,d){return d!==b?f.style(a,c,d):f.css(a,c)},a,c,arguments.length>1)},f.extend({cssHooks:{opacity:{get:function(a,b){if(b){var c=by(a,"opacity");return c===""?"1":c}return a.style.opacity}}},cssNumber:{fillOpacity:!0,fontWeight:!0,lineHeight:!0,opacity:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":f.support.cssFloat?"cssFloat":"styleFloat"},style:function(a,c,d,e){if(!!a&&a.nodeType!==3&&a.nodeType!==8&&!!a.style){var g,h,i=f.camelCase(c),j=a.style,k=f.cssHooks[i];c=f.cssProps[i]||i;if(d===b){if(k&&"get"in k&&(g=k.get(a,!1,e))!==b)return g;return j[c]}h=typeof d,h==="string"&&(g=bu.exec(d))&&(d=+(g[1]+1)*+g[2]+parseFloat(f.css(a,c)),h="number");if(d==null||h==="number"&&isNaN(d))return;h==="number"&&!f.cssNumber[i]&&(d+="px");if(!k||!("set"in k)||(d=k.set(a,d))!==b)try{j[c]=d}catch(l){}}},css:function(a,c,d){var e,g;c=f.camelCase(c),g=f.cssHooks[c],c=f.cssProps[c]||c,c==="cssFloat"&&(c="float");if(g&&"get"in g&&(e=g.get(a,!0,d))!==b)return e;if(by)return by(a,c)},swap:function(a,b,c){var d={},e,f;for(f in b)d[f]=a.style[f],a.style[f]=b[f];e=c.call(a);for(f in b)a.style[f]=d[f];return e}}),f.curCSS=f.css,c.defaultView&&c.defaultView.getComputedStyle&&(bz=function(a,b){var c,d,e,g,h=a.style;b=b.replace(br,"-$1").toLowerCase(),(d=a.ownerDocument.defaultView)&&(e=d.getComputedStyle(a,null))&&(c=e.getPropertyValue(b),c===""&&!f.contains(a.ownerDocument.documentElement,a)&&(c=f.style(a,b))),!f.support.pixelMargin&&e&&bv.test(b)&&bt.test(c)&&(g=h.width,h.width=c,c=e.width,h.width=g);return c}),c.documentElement.currentStyle&&(bA=function(a,b){var c,d,e,f=a.currentStyle&&a.currentStyle[b],g=a.style;f==null&&g&&(e=g[b])&&(f=e),bt.test(f)&&(c=g.left,d=a.runtimeStyle&&a.runtimeStyle.left,d&&(a.runtimeStyle.left=a.currentStyle.left),g.left=b==="fontSize"?"1em":f,f=g.pixelLeft+"px",g.left=c,d&&(a.runtimeStyle.left=d));return f===""?"auto":f}),by=bz||bA,f.each(["height","width"],function(a,b){f.cssHooks[b]={get:function(a,c,d){if(c)return a.offsetWidth!==0?bB(a,b,d):f.swap(a,bw,function(){return bB(a,b,d)})},set:function(a,b){return bs.test(b)?b+"px":b}}}),f.support.opacity||(f.cssHooks.opacity={get:function(a,b){return bq.test((b&&a.currentStyle?a.currentStyle.filter:a.style.filter)||"")?parseFloat(RegExp.$1)/100+"":b?"1":""},set:function(a,b){var c=a.style,d=a.currentStyle,e=f.isNumeric(b)?"alpha(opacity="+b*100+")":"",g=d&&d.filter||c.filter||"";c.zoom=1;if(b>=1&&f.trim(g.replace(bp,""))===""){c.removeAttribute("filter");if(d&&!d.filter)return}c.filter=bp.test(g)?g.replace(bp,e):g+" "+e}}),f(function(){f.support.reliableMarginRight||(f.cssHooks.marginRight={get:function(a,b){return f.swap(a,{display:"inline-block"},function(){return b?by(a,"margin-right"):a.style.marginRight})}})}),f.expr&&f.expr.filters&&(f.expr.filters.hidden=function(a){var b=a.offsetWidth,c=a.offsetHeight;return b===0&&c===0||!f.support.reliableHiddenOffsets&&(a.style&&a.style.display||f.css(a,"display"))==="none"},f.expr.filters.visible=function(a){return!f.expr.filters.hidden(a)}),f.each({margin:"",padding:"",border:"Width"},function(a,b){f.cssHooks[a+b]={expand:function(c){var d,e=typeof c=="string"?c.split(" "):[c],f={};for(d=0;d<4;d++)f[a+bx[d]+b]=e[d]||e[d-2]||e[0];return f}}});var bC=/%20/g,bD=/\[\]$/,bE=/\r?\n/g,bF=/#.*$/,bG=/^(.*?):[ \t]*([^\r\n]*)\r?$/mg,bH=/^(?:color|date|datetime|datetime-local|email|hidden|month|number|password|range|search|tel|text|time|url|week)$/i,bI=/^(?:about|app|app\-storage|.+\-extension|file|res|widget):$/,bJ=/^(?:GET|HEAD)$/,bK=/^\/\//,bL=/\?/,bM=/<script\b[^<]*(?:(?!<\/script>)<[^<]*)*<\/script>/gi,bN=/^(?:select|textarea)/i,bO=/\s+/,bP=/([?&])_=[^&]*/,bQ=/^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,bR=f.fn.load,bS={},bT={},bU,bV,bW=["*/"]+["*"];try{bU=e.href}catch(bX){bU=c.createElement("a"),bU.href="",bU=bU.href}bV=bQ.exec(bU.toLowerCase())||[],f.fn.extend({load:function(a,c,d){if(typeof a!="string"&&bR)return bR.apply(this,arguments);if(!this.length)return this;var e=a.indexOf(" ");if(e>=0){var g=a.slice(e,a.length);a=a.slice(0,e)}var h="GET";c&&(f.isFunction(c)?(d=c,c=b):typeof c=="object"&&(c=f.param(c,f.ajaxSettings.traditional),h="POST"));var i=this;f.ajax({url:a,type:h,dataType:"html",data:c,complete:function(a,b,c){c=a.responseText,a.isResolved()&&(a.done(function(a){c=a}),i.html(g?f("<div>").append(c.replace(bM,"")).find(g):c)),d&&i.each(d,[c,b,a])}});return this},serialize:function(){return f.param(this.serializeArray())},serializeArray:function(){return this.map(function(){return this.elements?f.makeArray(this.elements):this}).filter(function(){return this.name&&!this.disabled&&(this.checked||bN.test(this.nodeName)||bH.test(this.type))}).map(function(a,b){var c=f(this).val();return c==null?null:f.isArray(c)?f.map(c,function(a,c){return{name:b.name,value:a.replace(bE,"\r\n")}}):{name:b.name,value:c.replace(bE,"\r\n")}}).get()}}),f.each("ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".split(" "),function(a,b){f.fn[b]=function(a){return this.on(b,a)}}),f.each(["get","post"],function(a,c){f[c]=function(a,d,e,g){f.isFunction(d)&&(g=g||e,e=d,d=b);return f.ajax({type:c,url:a,data:d,success:e,dataType:g})}}),f.extend({getScript:function(a,c){return f.get(a,b,c,"script")},getJSON:function(a,b,c){return f.get(a,b,c,"json")},ajaxSetup:function(a,b){b?b$(a,f.ajaxSettings):(b=a,a=f.ajaxSettings),b$(a,b);return a},ajaxSettings:{url:bU,isLocal:bI.test(bV[1]),global:!0,type:"GET",contentType:"application/x-www-form-urlencoded; charset=UTF-8",processData:!0,async:!0,accepts:{xml:"application/xml, text/xml",html:"text/html",text:"text/plain",json:"application/json, text/javascript","*":bW},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText"},converters:{"* text":a.String,"text html":!0,"text json":f.parseJSON,"text xml":f.parseXML},flatOptions:{context:!0,url:!0}},ajaxPrefilter:bY(bS),ajaxTransport:bY(bT),ajax:function(a,c){function w(a,c,l,m){if(s!==2){s=2,q&&clearTimeout(q),p=b,n=m||"",v.readyState=a>0?4:0;var o,r,u,w=c,x=l?ca(d,v,l):b,y,z;if(a>=200&&a<300||a===304){if(d.ifModified){if(y=v.getResponseHeader("Last-Modified"))f.lastModified[k]=y;if(z=v.getResponseHeader("Etag"))f.etag[k]=z}if(a===304)w="notmodified",o=!0;else try{r=cb(d,x),w="success",o=!0}catch(A){w="parsererror",u=A}}else{u=w;if(!w||a)w="error",a<0&&(a=0)}v.status=a,v.statusText=""+(c||w),o?h.resolveWith(e,[r,w,v]):h.rejectWith(e,[v,w,u]),v.statusCode(j),j=b,t&&g.trigger("ajax"+(o?"Success":"Error"),[v,d,o?r:u]),i.fireWith(e,[v,w]),t&&(g.trigger("ajaxComplete",[v,d]),--f.active||f.event.trigger("ajaxStop"))}}typeof a=="object"&&(c=a,a=b),c=c||{};var d=f.ajaxSetup({},c),e=d.context||d,g=e!==d&&(e.nodeType||e instanceof f)?f(e):f.event,h=f.Deferred(),i=f.Callbacks("once memory"),j=d.statusCode||{},k,l={},m={},n,o,p,q,r,s=0,t,u,v={readyState:0,setRequestHeader:function(a,b){if(!s){var c=a.toLowerCase();a=m[c]=m[c]||a,l[a]=b}return this},getAllResponseHeaders:function(){return s===2?n:null},getResponseHeader:function(a){var c;if(s===2){if(!o){o={};while(c=bG.exec(n))o[c[1].toLowerCase()]=c[2]}c=o[a.toLowerCase()]}return c===b?null:c},overrideMimeType:function(a){s||(d.mimeType=a);return this},abort:function(a){a=a||"abort",p&&p.abort(a),w(0,a);return this}};h.promise(v),v.success=v.done,v.error=v.fail,v.complete=i.add,v.statusCode=function(a){if(a){var b;if(s<2)for(b in a)j[b]=[j[b],a[b]];else b=a[v.status],v.then(b,b)}return this},d.url=((a||d.url)+"").replace(bF,"").replace(bK,bV[1]+"//"),d.dataTypes=f.trim(d.dataType||"*").toLowerCase().split(bO),d.crossDomain==null&&(r=bQ.exec(d.url.toLowerCase()),d.crossDomain=!(!r||r[1]==bV[1]&&r[2]==bV[2]&&(r[3]||(r[1]==="http:"?80:443))==(bV[3]||(bV[1]==="http:"?80:443)))),d.data&&d.processData&&typeof d.data!="string"&&(d.data=f.param(d.data,d.traditional)),bZ(bS,d,c,v);if(s===2)return!1;t=d.global,d.type=d.type.toUpperCase(),d.hasContent=!bJ.test(d.type),t&&f.active++===0&&f.event.trigger("ajaxStart");if(!d.hasContent){d.data&&(d.url+=(bL.test(d.url)?"&":"?")+d.data,delete d.data),k=d.url;if(d.cache===!1){var x=f.now(),y=d.url.replace(bP,"$1_="+x);d.url=y+(y===d.url?(bL.test(d.url)?"&":"?")+"_="+x:"")}}(d.data&&d.hasContent&&d.contentType!==!1||c.contentType)&&v.setRequestHeader("Content-Type",d.contentType),d.ifModified&&(k=k||d.url,f.lastModified[k]&&v.setRequestHeader("If-Modified-Since",f.lastModified[k]),f.etag[k]&&v.setRequestHeader("If-None-Match",f.etag[k])),v.setRequestHeader("Accept",d.dataTypes[0]&&d.accepts[d.dataTypes[0]]?d.accepts[d.dataTypes[0]]+(d.dataTypes[0]!=="*"?", "+bW+"; q=0.01":""):d.accepts["*"]);for(u in d.headers)v.setRequestHeader(u,d.headers[u]);if(d.beforeSend&&(d.beforeSend.call(e,v,d)===!1||s===2)){v.abort();return!1}for(u in{success:1,error:1,complete:1})v[u](d[u]);p=bZ(bT,d,c,v);if(!p)w(-1,"No Transport");else{v.readyState=1,t&&g.trigger("ajaxSend",[v,d]),d.async&&d.timeout>0&&(q=setTimeout(function(){v.abort("timeout")},d.timeout));try{s=1,p.send(l,w)}catch(z){if(s<2)w(-1,z);else throw z}}return v},param:function(a,c){var d=[],e=function(a,b){b=f.isFunction(b)?b():b,d[d.length]=encodeURIComponent(a)+"="+encodeURIComponent(b)};c===b&&(c=f.ajaxSettings.traditional);if(f.isArray(a)||a.jquery&&!f.isPlainObject(a))f.each(a,function(){e(this.name,this.value)});else for(var g in a)b_(g,a[g],c,e);return d.join("&").replace(bC,"+")}}),f.extend({active:0,lastModified:{},etag:{}});var cc=f.now(),cd=/(\=)\?(&|$)|\?\?/i;f.ajaxSetup({jsonp:"callback",jsonpCallback:function(){return f.expando+"_"+cc++}}),f.ajaxPrefilter("json jsonp",function(b,c,d){var e=typeof b.data=="string"&&/^application\/x\-www\-form\-urlencoded/.test(b.contentType);if(b.dataTypes[0]==="jsonp"||b.jsonp!==!1&&(cd.test(b.url)||e&&cd.test(b.data))){var g,h=b.jsonpCallback=f.isFunction(b.jsonpCallback)?b.jsonpCallback():b.jsonpCallback,i=a[h],j=b.url,k=b.data,l="$1"+h+"$2";b.jsonp!==!1&&(j=j.replace(cd,l),b.url===j&&(e&&(k=k.replace(cd,l)),b.data===k&&(j+=(/\?/.test(j)?"&":"?")+b.jsonp+"="+h))),b.url=j,b.data=k,a[h]=function(a){g=[a]},d.always(function(){a[h]=i,g&&f.isFunction(i)&&a[h](g[0])}),b.converters["script json"]=function(){g||f.error(h+" was not called");return g[0]},b.dataTypes[0]="json";return"script"}}),f.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/javascript|ecmascript/},converters:{"text script":function(a){f.globalEval(a);return a}}}),f.ajaxPrefilter("script",function(a){a.cache===b&&(a.cache=!1),a.crossDomain&&(a.type="GET",a.global=!1)}),f.ajaxTransport("script",function(a){if(a.crossDomain){var d,e=c.head||c.getElementsByTagName("head")[0]||c.documentElement;return{send:function(f,g){d=c.createElement("script"),d.async="async",a.scriptCharset&&(d.charset=a.scriptCharset),d.src=a.url,d.onload=d.onreadystatechange=function(a,c){if(c||!d.readyState||/loaded|complete/.test(d.readyState))d.onload=d.onreadystatechange=null,e&&d.parentNode&&e.removeChild(d),d=b,c||g(200,"success")},e.insertBefore(d,e.firstChild)},abort:function(){d&&d.onload(0,1)}}}});var ce=a.ActiveXObject?function(){for(var a in cg)cg[a](0,1)}:!1,cf=0,cg;f.ajaxSettings.xhr=a.ActiveXObject?function(){return!this.isLocal&&ch()||ci()}:ch,function(a){f.extend(f.support,{ajax:!!a,cors:!!a&&"withCredentials"in a})}(f.ajaxSettings.xhr()),f.support.ajax&&f.ajaxTransport(function(c){if(!c.crossDomain||f.support.cors){var d;return{send:function(e,g){var h=c.xhr(),i,j;c.username?h.open(c.type,c.url,c.async,c.username,c.password):h.open(c.type,c.url,c.async);if(c.xhrFields)for(j in c.xhrFields)h[j]=c.xhrFields[j];c.mimeType&&h.overrideMimeType&&h.overrideMimeType(c.mimeType),!c.crossDomain&&!e["X-Requested-With"]&&(e["X-Requested-With"]="XMLHttpRequest");try{for(j in e)h.setRequestHeader(j,e[j])}catch(k){}h.send(c.hasContent&&c.data||null),d=function(a,e){var j,k,l,m,n;try{if(d&&(e||h.readyState===4)){d=b,i&&(h.onreadystatechange=f.noop,ce&&delete cg[i]);if(e)h.readyState!==4&&h.abort();else{j=h.status,l=h.getAllResponseHeaders(),m={},n=h.responseXML,n&&n.documentElement&&(m.xml=n);try{m.text=h.responseText}catch(a){}try{k=h.statusText}catch(o){k=""}!j&&c.isLocal&&!c.crossDomain?j=m.text?200:404:j===1223&&(j=204)}}}catch(p){e||g(-1,p)}m&&g(j,k,m,l)},!c.async||h.readyState===4?d():(i=++cf,ce&&(cg||(cg={},f(a).unload(ce)),cg[i]=d),h.onreadystatechange=d)},abort:function(){d&&d(0,1)}}}});var cj={},ck,cl,cm=/^(?:toggle|show|hide)$/,cn=/^([+\-]=)?([\d+.\-]+)([a-z%]*)$/i,co,cp=[["height","marginTop","marginBottom","paddingTop","paddingBottom"],["width","marginLeft","marginRight","paddingLeft","paddingRight"],["opacity"]],cq;f.fn.extend({show:function(a,b,c){var d,e;if(a||a===0)return this.animate(ct("show",3),a,b,c);for(var g=0,h=this.length;g<h;g++)d=this[g],d.style&&(e=d.style.display,!f._data(d,"olddisplay")&&e==="none"&&(e=d.style.display=""),(e===""&&f.css(d,"display")==="none"||!f.contains(d.ownerDocument.documentElement,d))&&f._data(d,"olddisplay",cu(d.nodeName)));for(g=0;g<h;g++){d=this[g];if(d.style){e=d.style.display;if(e===""||e==="none")d.style.display=f._data(d,"olddisplay")||""}}return this},hide:function(a,b,c){if(a||a===0)return this.animate(ct("hide",3),a,b,c);var d,e,g=0,h=this.length;for(;g<h;g++)d=this[g],d.style&&(e=f.css(d,"display"),e!=="none"&&!f._data(d,"olddisplay")&&f._data(d,"olddisplay",e));for(g=0;g<h;g++)this[g].style&&(this[g].style.display="none");return this},_toggle:f.fn.toggle,toggle:function(a,b,c){var d=typeof a=="boolean";f.isFunction(a)&&f.isFunction(b)?this._toggle.apply(this,arguments):a==null||d?this.each(function(){var b=d?a:f(this).is(":hidden");f(this)[b?"show":"hide"]()}):this.animate(ct("toggle",3),a,b,c);return this},fadeTo:function(a,b,c,d){return this.filter(":hidden").css("opacity",0).show().end().animate({opacity:b},a,c,d)},animate:function(a,b,c,d){function g(){e.queue===!1&&f._mark(this);var b=f.extend({},e),c=this.nodeType===1,d=c&&f(this).is(":hidden"),g,h,i,j,k,l,m,n,o,p,q;b.animatedProperties={};for(i in a){g=f.camelCase(i),i!==g&&(a[g]=a[i],delete a[i]);if((k=f.cssHooks[g])&&"expand"in k){l=k.expand(a[g]),delete a[g];for(i in l)i in a||(a[i]=l[i])}}for(g in a){h=a[g],f.isArray(h)?(b.animatedProperties[g]=h[1],h=a[g]=h[0]):b.animatedProperties[g]=b.specialEasing&&b.specialEasing[g]||b.easing||"swing";if(h==="hide"&&d||h==="show"&&!d)return b.complete.call(this);c&&(g==="height"||g==="width")&&(b.overflow=[this.style.overflow,this.style.overflowX,this.style.overflowY],f.css(this,"display")==="inline"&&f.css(this,"float")==="none"&&(!f.support.inlineBlockNeedsLayout||cu(this.nodeName)==="inline"?this.style.display="inline-block":this.style.zoom=1))}b.overflow!=null&&(this.style.overflow="hidden");for(i in a)j=new f.fx(this,b,i),h=a[i],cm.test(h)?(q=f._data(this,"toggle"+i)||(h==="toggle"?d?"show":"hide":0),q?(f._data(this,"toggle"+i,q==="show"?"hide":"show"),j[q]()):j[h]()):(m=cn.exec(h),n=j.cur(),m?(o=parseFloat(m[2]),p=m[3]||(f.cssNumber[i]?"":"px"),p!=="px"&&(f.style(this,i,(o||1)+p),n=(o||1)/j.cur()*n,f.style(this,i,n+p)),m[1]&&(o=(m[1]==="-="?-1:1)*o+n),j.custom(n,o,p)):j.custom(n,h,""));return!0}var e=f.speed(b,c,d);if(f.isEmptyObject(a))return this.each(e.complete,[!1]);a=f.extend({},a);return e.queue===!1?this.each(g):this.queue(e.queue,g)},stop:function(a,c,d){typeof a!="string"&&(d=c,c=a,a=b),c&&a!==!1&&this.queue(a||"fx",[]);return this.each(function(){function h(a,b,c){var e=b[c];f.removeData(a,c,!0),e.stop(d)}var b,c=!1,e=f.timers,g=f._data(this);d||f._unmark(!0,this);if(a==null)for(b in g)g[b]&&g[b].stop&&b.indexOf(".run")===b.length-4&&h(this,g,b);else g[b=a+".run"]&&g[b].stop&&h(this,g,b);for(b=e.length;b--;)e[b].elem===this&&(a==null||e[b].queue===a)&&(d?e[b](!0):e[b].saveState(),c=!0,e.splice(b,1));(!d||!c)&&f.dequeue(this,a)})}}),f.each({slideDown:ct("show",1),slideUp:ct("hide",1),slideToggle:ct("toggle",1),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(a,b){f.fn[a]=function(a,c,d){return this.animate(b,a,c,d)}}),f.extend({speed:function(a,b,c){var d=a&&typeof a=="object"?f.extend({},a):{complete:c||!c&&b||f.isFunction(a)&&a,duration:a,easing:c&&b||b&&!f.isFunction(b)&&b};d.duration=f.fx.off?0:typeof d.duration=="number"?d.duration:d.duration in f.fx.speeds?f.fx.speeds[d.duration]:f.fx.speeds._default;if(d.queue==null||d.queue===!0)d.queue="fx";d.old=d.complete,d.complete=function(a){f.isFunction(d.old)&&d.old.call(this),d.queue?f.dequeue(this,d.queue):a!==!1&&f._unmark(this)};return d},easing:{linear:function(a){return a},swing:function(a){return-Math.cos(a*Math.PI)/2+.5}},timers:[],fx:function(a,b,c){this.options=b,this.elem=a,this.prop=c,b.orig=b.orig||{}}}),f.fx.prototype={update:function(){this.options.step&&this.options.step.call(this.elem,this.now,this),(f.fx.step[this.prop]||f.fx.step._default)(this)},cur:function(){if(this.elem[this.prop]!=null&&(!this.elem.style||this.elem.style[this.prop]==null))return this.elem[this.prop];var a,b=f.css(this.elem,this.prop);return isNaN(a=parseFloat(b))?!b||b==="auto"?0:b:a},custom:function(a,c,d){function h(a){return e.step(a)}var e=this,g=f.fx;this.startTime=cq||cr(),this.end=c,this.now=this.start=a,this.pos=this.state=0,this.unit=d||this.unit||(f.cssNumber[this.prop]?"":"px"),h.queue=this.options.queue,h.elem=this.elem,h.saveState=function(){f._data(e.elem,"fxshow"+e.prop)===b&&(e.options.hide?f._data(e.elem,"fxshow"+e.prop,e.start):e.options.show&&f._data(e.elem,"fxshow"+e.prop,e.end))},h()&&f.timers.push(h)&&!co&&(co=setInterval(g.tick,g.interval))},show:function(){var a=f._data(this.elem,"fxshow"+this.prop);this.options.orig[this.prop]=a||f.style(this.elem,this.prop),this.options.show=!0,a!==b?this.custom(this.cur(),a):this.custom(this.prop==="width"||this.prop==="height"?1:0,this.cur()),f(this.elem).show()},hide:function(){this.options.orig[this.prop]=f._data(this.elem,"fxshow"+this.prop)||f.style(this.elem,this.prop),this.options.hide=!0,this.custom(this.cur(),0)},step:function(a){var b,c,d,e=cq||cr(),g=!0,h=this.elem,i=this.options;if(a||e>=i.duration+this.startTime){this.now=this.end,this.pos=this.state=1,this.update(),i.animatedProperties[this.prop]=!0;for(b in i.animatedProperties)i.animatedProperties[b]!==!0&&(g=!1);if(g){i.overflow!=null&&!f.support.shrinkWrapBlocks&&f.each(["","X","Y"],function(a,b){h.style["overflow"+b]=i.overflow[a]}),i.hide&&f(h).hide();if(i.hide||i.show)for(b in i.animatedProperties)f.style(h,b,i.orig[b]),f.removeData(h,"fxshow"+b,!0),f.removeData(h,"toggle"+b,!0);d=i.complete,d&&(i.complete=!1,d.call(h))}return!1}i.duration==Infinity?this.now=e:(c=e-this.startTime,this.state=c/i.duration,this.pos=f.easing[i.animatedProperties[this.prop]](this.state,c,0,1,i.duration),this.now=this.start+(this.end-this.start)*this.pos),this.update();return!0}},f.extend(f.fx,{tick:function(){var a,b=f.timers,c=0;for(;c<b.length;c++)a=b[c],!a()&&b[c]===a&&b.splice(c--,1);b.length||f.fx.stop()},interval:13,stop:function(){clearInterval(co),co=null},speeds:{slow:600,fast:200,_default:400},step:{opacity:function(a){f.style(a.elem,"opacity",a.now)},_default:function(a){a.elem.style&&a.elem.style[a.prop]!=null?a.elem.style[a.prop]=a.now+a.unit:a.elem[a.prop]=a.now}}}),f.each(cp.concat.apply([],cp),function(a,b){b.indexOf("margin")&&(f.fx.step[b]=function(a){f.style(a.elem,b,Math.max(0,a.now)+a.unit)})}),f.expr&&f.expr.filters&&(f.expr.filters.animated=function(a){return f.grep(f.timers,function(b){return a===b.elem}).length});var cv,cw=/^t(?:able|d|h)$/i,cx=/^(?:body|html)$/i;"getBoundingClientRect"in c.documentElement?cv=function(a,b,c,d){try{d=a.getBoundingClientRect()}catch(e){}if(!d||!f.contains(c,a))return d?{top:d.top,left:d.left}:{top:0,left:0};var g=b.body,h=cy(b),i=c.clientTop||g.clientTop||0,j=c.clientLeft||g.clientLeft||0,k=h.pageYOffset||f.support.boxModel&&c.scrollTop||g.scrollTop,l=h.pageXOffset||f.support.boxModel&&c.scrollLeft||g.scrollLeft,m=d.top+k-i,n=d.left+l-j;return{top:m,left:n}}:cv=function(a,b,c){var d,e=a.offsetParent,g=a,h=b.body,i=b.defaultView,j=i?i.getComputedStyle(a,null):a.currentStyle,k=a.offsetTop,l=a.offsetLeft;while((a=a.parentNode)&&a!==h&&a!==c){if(f.support.fixedPosition&&j.position==="fixed")break;d=i?i.getComputedStyle(a,null):a.currentStyle,k-=a.scrollTop,l-=a.scrollLeft,a===e&&(k+=a.offsetTop,l+=a.offsetLeft,f.support.doesNotAddBorder&&(!f.support.doesAddBorderForTableAndCells||!cw.test(a.nodeName))&&(k+=parseFloat(d.borderTopWidth)||0,l+=parseFloat(d.borderLeftWidth)||0),g=e,e=a.offsetParent),f.support.subtractsBorderForOverflowNotVisible&&d.overflow!=="visible"&&(k+=parseFloat(d.borderTopWidth)||0,l+=parseFloat(d.borderLeftWidth)||0),j=d}if(j.position==="relative"||j.position==="static")k+=h.offsetTop,l+=h.offsetLeft;f.support.fixedPosition&&j.position==="fixed"&&(k+=Math.max(c.scrollTop,h.scrollTop),l+=Math.max(c.scrollLeft,h.scrollLeft));return{top:k,left:l}},f.fn.offset=function(a){if(arguments.length)return a===b?this:this.each(function(b){f.offset.setOffset(this,a,b)});var c=this[0],d=c&&c.ownerDocument;if(!d)return null;if(c===d.body)return f.offset.bodyOffset(c);return cv(c,d,d.documentElement)},f.offset={bodyOffset:function(a){var b=a.offsetTop,c=a.offsetLeft;f.support.doesNotIncludeMarginInBodyOffset&&(b+=parseFloat(f.css(a,"marginTop"))||0,c+=parseFloat(f.css(a,"marginLeft"))||0);return{top:b,left:c}},setOffset:function(a,b,c){var d=f.css(a,"position");d==="static"&&(a.style.position="relative");var e=f(a),g=e.offset(),h=f.css(a,"top"),i=f.css(a,"left"),j=(d==="absolute"||d==="fixed")&&f.inArray("auto",[h,i])>-1,k={},l={},m,n;j?(l=e.position(),m=l.top,n=l.left):(m=parseFloat(h)||0,n=parseFloat(i)||0),f.isFunction(b)&&(b=b.call(a,c,g)),b.top!=null&&(k.top=b.top-g.top+m),b.left!=null&&(k.left=b.left-g.left+n),"using"in b?b.using.call(a,k):e.css(k)}},f.fn.extend({position:function(){if(!this[0])return null;var a=this[0],b=this.offsetParent(),c=this.offset(),d=cx.test(b[0].nodeName)?{top:0,left:0}:b.offset();c.top-=parseFloat(f.css(a,"marginTop"))||0,c.left-=parseFloat(f.css(a,"marginLeft"))||0,d.top+=parseFloat(f.css(b[0],"borderTopWidth"))||0,d.left+=parseFloat(f.css(b[0],"borderLeftWidth"))||0;return{top:c.top-d.top,left:c.left-d.left}},offsetParent:function(){return this.map(function(){var a=this.offsetParent||c.body;while(a&&!cx.test(a.nodeName)&&f.css(a,"position")==="static")a=a.offsetParent;return a})}}),f.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(a,c){var d=/Y/.test(c);f.fn[a]=function(e){return f.access(this,function(a,e,g){var h=cy(a);if(g===b)return h?c in h?h[c]:f.support.boxModel&&h.document.documentElement[e]||h.document.body[e]:a[e];h?h.scrollTo(d?f(h).scrollLeft():g,d?g:f(h).scrollTop()):a[e]=g},a,e,arguments.length,null)}}),f.each({Height:"height",Width:"width"},function(a,c){var d="client"+a,e="scroll"+a,g="offset"+a;f.fn["inner"+a]=function(){var a=this[0];return a?a.style?parseFloat(f.css(a,c,"padding")):this[c]():null},f.fn["outer"+a]=function(a){var b=this[0];return b?b.style?parseFloat(f.css(b,c,a?"margin":"border")):this[c]():null},f.fn[c]=function(a){return f.access(this,function(a,c,h){var i,j,k,l;if(f.isWindow(a)){i=a.document,j=i.documentElement[d];return f.support.boxModel&&j||i.body&&i.body[d]||j}if(a.nodeType===9){i=a.documentElement;if(i[d]>=i[e])return i[d];return Math.max(a.body[e],i[e],a.body[g],i[g])}if(h===b){k=f.css(a,c),l=parseFloat(k);return f.isNumeric(l)?l:k}f(a).css(c,h)},c,a,arguments.length,null)}}),a.jQuery=a.$=f,typeof define=="function"&&define.amd&&define.amd.jQuery&&define("jquery",[],function(){return f})})(window); \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/js/prettify.js b/slf4j-site/src/site/pages/js/prettify.js
deleted file mode 100644
index 8fc4c933..00000000
--- a/slf4j-site/src/site/pages/js/prettify.js
+++ /dev/null
@@ -1,23 +0,0 @@
-function H(){var x=navigator&&navigator.userAgent&&/\bMSIE 6\./.test(navigator.userAgent);H=function(){return x};return x}(function(){function x(b){b=b.split(/ /g);var a={};for(var c=b.length;--c>=0;){var d=b[c];if(d)a[d]=null}return a}var y="break continue do else for if return while ",U=y+"auto case char const default double enum extern float goto int long register short signed sizeof static struct switch typedef union unsigned void volatile ",D=U+"catch class delete false import new operator private protected public this throw true try ",
-I=D+"alignof align_union asm axiom bool concept concept_map const_cast constexpr decltype dynamic_cast explicit export friend inline late_check mutable namespace nullptr reinterpret_cast static_assert static_cast template typeid typename typeof using virtual wchar_t where ",J=D+"boolean byte extends final finally implements import instanceof null native package strictfp super synchronized throws transient ",V=J+"as base by checked decimal delegate descending event fixed foreach from group implicit in interface internal into is lock object out override orderby params readonly ref sbyte sealed stackalloc string select uint ulong unchecked unsafe ushort var ",
-K=D+"debugger eval export function get null set undefined var with Infinity NaN ",L="caller delete die do dump elsif eval exit foreach for goto if import last local my next no our print package redo require sub undef unless until use wantarray while BEGIN END ",M=y+"and as assert class def del elif except exec finally from global import in is lambda nonlocal not or pass print raise try with yield False True None ",N=y+"alias and begin case class def defined elsif end ensure false in module next nil not or redo rescue retry self super then true undef unless until when yield BEGIN END ",
-O=y+"case done elif esac eval fi function in local set then until ",W=I+V+K+L+M+N+O;function X(b){return b>="a"&&b<="z"||b>="A"&&b<="Z"}function u(b,a,c,d){b.unshift(c,d||0);try{a.splice.apply(a,b)}finally{b.splice(0,2)}}var Y=(function(){var b=["!","!=","!==","#","%","%=","&","&&","&&=","&=","(","*","*=","+=",",","-=","->","/","/=",":","::",";","<","<<","<<=","<=","=","==","===",">",">=",">>",">>=",">>>",">>>=","?","@","[","^","^=","^^","^^=","{","|","|=","||","||=","~","break","case","continue",
-"delete","do","else","finally","instanceof","return","throw","try","typeof"],a="(?:(?:(?:^|[^0-9.])\\.{1,3})|(?:(?:^|[^\\+])\\+)|(?:(?:^|[^\\-])-)";for(var c=0;c<b.length;++c){var d=b[c];a+=X(d.charAt(0))?"|\\b"+d:"|"+d.replace(/([^=<>:&])/g,"\\$1")}a+="|^)\\s*$";return new RegExp(a)})(),P=/&/g,Q=/</g,R=/>/g,Z=/\"/g;function $(b){return b.replace(P,"&amp;").replace(Q,"&lt;").replace(R,"&gt;").replace(Z,"&quot;")}function E(b){return b.replace(P,"&amp;").replace(Q,"&lt;").replace(R,"&gt;")}var aa=
-/&lt;/g,ba=/&gt;/g,ca=/&apos;/g,da=/&quot;/g,ea=/&amp;/g,fa=/&nbsp;/g;function ga(b){var a=b.indexOf("&");if(a<0)return b;for(--a;(a=b.indexOf("&#",a+1))>=0;){var c=b.indexOf(";",a);if(c>=0){var d=b.substring(a+3,c),g=10;if(d&&d.charAt(0)==="x"){d=d.substring(1);g=16}var e=parseInt(d,g);if(!isNaN(e))b=b.substring(0,a)+String.fromCharCode(e)+b.substring(c+1)}}return b.replace(aa,"<").replace(ba,">").replace(ca,"'").replace(da,'"').replace(ea,"&").replace(fa," ")}function S(b){return"XMP"===b.tagName}
-function z(b,a){switch(b.nodeType){case 1:var c=b.tagName.toLowerCase();a.push("<",c);for(var d=0;d<b.attributes.length;++d){var g=b.attributes[d];if(!g.specified)continue;a.push(" ");z(g,a)}a.push(">");for(var e=b.firstChild;e;e=e.nextSibling)z(e,a);if(b.firstChild||!/^(?:br|link|img)$/.test(c))a.push("</",c,">");break;case 2:a.push(b.name.toLowerCase(),'="',$(b.value),'"');break;case 3:case 4:a.push(E(b.nodeValue));break}}var F=null;function ha(b){if(null===F){var a=document.createElement("PRE");
-a.appendChild(document.createTextNode('<!DOCTYPE foo PUBLIC "foo bar">\n<foo />'));F=!/</.test(a.innerHTML)}if(F){var c=b.innerHTML;if(S(b))c=E(c);return c}var d=[];for(var g=b.firstChild;g;g=g.nextSibling)z(g,d);return d.join("")}function ia(b){var a=0;return function(c){var d=null,g=0;for(var e=0,h=c.length;e<h;++e){var f=c.charAt(e);switch(f){case "\t":if(!d)d=[];d.push(c.substring(g,e));var i=b-a%b;a+=i;for(;i>=0;i-=" ".length)d.push(" ".substring(0,i));g=e+1;break;
-case "\n":a=0;break;default:++a}}if(!d)return c;d.push(c.substring(g));return d.join("")}}var ja=/(?:[^<]+|<!--[\s\S]*?--\>|<!\[CDATA\[([\s\S]*?)\]\]>|<\/?[a-zA-Z][^>]*>|<)/g,ka=/^<!--/,la=/^<\[CDATA\[/,ma=/^<br\b/i;function na(b){var a=b.match(ja),c=[],d=0,g=[];if(a)for(var e=0,h=a.length;e<h;++e){var f=a[e];if(f.length>1&&f.charAt(0)==="<"){if(ka.test(f))continue;if(la.test(f)){c.push(f.substring(9,f.length-3));d+=f.length-12}else if(ma.test(f)){c.push("\n");++d}else g.push(d,f)}else{var i=ga(f);
-c.push(i);d+=i.length}}return{source:c.join(""),tags:g}}function v(b,a){var c={};(function(){var g=b.concat(a);for(var e=g.length;--e>=0;){var h=g[e],f=h[3];if(f)for(var i=f.length;--i>=0;)c[f.charAt(i)]=h}})();var d=a.length;return function(g,e){e=e||0;var h=[e,"pln"],f="",i=0,j=g;while(j.length){var o,m=null,k,l=c[j.charAt(0)];if(l){k=j.match(l[1]);m=k[0];o=l[0]}else{for(var n=0;n<d;++n){l=a[n];var p=l[2];if(p&&!p.test(f))continue;k=j.match(l[1]);if(k){m=k[0];o=l[0];break}}if(!m){o="pln";m=j.substring(0,
-1)}}h.push(e+i,o);i+=m.length;j=j.substring(m.length);if(o!=="com"&&/\S/.test(m))f=m}return h}}var oa=v([],[["pln",/^[^<]+/,null],["dec",/^<!\w[^>]*(?:>|$)/,null],["com",/^<!--[\s\S]*?(?:--\>|$)/,null],["src",/^<\?[\s\S]*?(?:\?>|$)/,null],["src",/^<%[\s\S]*?(?:%>|$)/,null],["src",/^<(script|style|xmp)\b[^>]*>[\s\S]*?<\/\1\b[^>]*>/i,null],["tag",/^<\/?\w[^<>]*>/,null]]);function pa(b){var a=oa(b);for(var c=0;c<a.length;c+=2)if(a[c+1]==="src"){var d,g;d=a[c];g=c+2<a.length?a[c+2]:b.length;var e=b.substring(d,
-g),h=e.match(/^(<[^>]*>)([\s\S]*)(<\/[^>]*>)$/);if(h)a.splice(c,2,d,"tag",d+h[1].length,"src",d+h[1].length+(h[2]||"").length,"tag")}return a}var qa=v([["atv",/^\'[^\']*(?:\'|$)/,null,"'"],["atv",/^\"[^\"]*(?:\"|$)/,null,'"'],["pun",/^[<>\/=]+/,null,"<>/="]],[["tag",/^[\w:\-]+/,/^</],["atv",/^[\w\-]+/,/^=/],["atn",/^[\w:\-]+/,null],["pln",/^\s+/,null," \t\r\n"]]);function ra(b,a){for(var c=0;c<a.length;c+=2){var d=a[c+1];if(d==="tag"){var g,e;g=a[c];e=c+2<a.length?a[c+2]:b.length;var h=b.substring(g,
-e),f=qa(h,g);u(f,a,c,2);c+=f.length-2}}return a}function r(b){var a=[],c=[];if(b.tripleQuotedStrings)a.push(["str",/^(?:\'\'\'(?:[^\'\\]|\\[\s\S]|\'{1,2}(?=[^\']))*(?:\'\'\'|$)|\"\"\"(?:[^\"\\]|\\[\s\S]|\"{1,2}(?=[^\"]))*(?:\"\"\"|$)|\'(?:[^\\\']|\\[\s\S])*(?:\'|$)|\"(?:[^\\\"]|\\[\s\S])*(?:\"|$))/,null,"'\""]);else if(b.multiLineStrings)a.push(["str",/^(?:\'(?:[^\\\']|\\[\s\S])*(?:\'|$)|\"(?:[^\\\"]|\\[\s\S])*(?:\"|$)|\`(?:[^\\\`]|\\[\s\S])*(?:\`|$))/,null,"'\"`"]);else a.push(["str",/^(?:\'(?:[^\\\'\r\n]|\\.)*(?:\'|$)|\"(?:[^\\\"\r\n]|\\.)*(?:\"|$))/,
-null,"\"'"]);c.push(["pln",/^(?:[^\'\"\`\/\#]+)/,null," \r\n"]);if(b.hashComments)a.push(["com",/^#[^\r\n]*/,null,"#"]);if(b.cStyleComments)c.push(["com",/^\/\/[^\r\n]*/,null]);if(b.regexLiterals)c.push(["str",/^\/(?:[^\\\*\/\[]|\\[\s\S]|\[(?:[^\]\\]|\\.)*(?:\]|$))+(?:\/|$)/,Y]);if(b.cStyleComments)c.push(["com",/^\/\*[\s\S]*?(?:\*\/|$)/,null]);var d=x(b.keywords);b=null;var g=v(a,c),e=v([],[["pln",/^\s+/,null," \r\n"],["pln",/^[a-z_$@][a-z_$@0-9]*/i,null],["lit",/^0x[a-f0-9]+[a-z]/i,null],["lit",
-/^(?:\d(?:_\d+)*\d*(?:\.\d*)?|\.\d+)(?:e[+\-]?\d+)?[a-z]*/i,null,"123456789"],["pun",/^[^\s\w\.$@]+/,null]]);function h(f,i){for(var j=0;j<i.length;j+=2){var o=i[j+1];if(o==="pln"){var m,k,l,n;m=i[j];k=j+2<i.length?i[j+2]:f.length;l=f.substring(m,k);n=e(l,m);for(var p=0,t=n.length;p<t;p+=2){var w=n[p+1];if(w==="pln"){var A=n[p],B=p+2<t?n[p+2]:l.length,s=f.substring(A,B);if(s===".")n[p+1]="pun";else if(s in d)n[p+1]="kwd";else if(/^@?[A-Z][A-Z$]*[a-z][A-Za-z$]*$/.test(s))n[p+1]=s.charAt(0)==="@"?"lit":
-"typ"}}u(n,i,j,2);j+=n.length-2}}return i}return function(f){var i=g(f);i=h(f,i);return i}}var G=r({keywords:W,hashComments:true,cStyleComments:true,multiLineStrings:true,regexLiterals:true});function sa(b,a){for(var c=0;c<a.length;c+=2){var d=a[c+1];if(d==="src"){var g,e;g=a[c];e=c+2<a.length?a[c+2]:b.length;var h=G(b.substring(g,e));for(var f=0,i=h.length;f<i;f+=2)h[f]+=g;u(h,a,c,2);c+=h.length-2}}return a}function ta(b,a){var c=false;for(var d=0;d<a.length;d+=2){var g=a[d+1],e,h;if(g==="atn"){e=
-a[d];h=d+2<a.length?a[d+2]:b.length;c=/^on|^style$/i.test(b.substring(e,h))}else if(g==="atv"){if(c){e=a[d];h=d+2<a.length?a[d+2]:b.length;var f=b.substring(e,h),i=f.length,j=i>=2&&/^[\"\']/.test(f)&&f.charAt(0)===f.charAt(i-1),o,m,k;if(j){m=e+1;k=h-1;o=f}else{m=e+1;k=h-1;o=f.substring(1,f.length-1)}var l=G(o);for(var n=0,p=l.length;n<p;n+=2)l[n]+=m;if(j){l.push(k,"atv");u(l,a,d+2,0)}else u(l,a,d,2)}c=false}}return a}function ua(b){var a=pa(b);a=ra(b,a);a=sa(b,a);a=ta(b,a);return a}function va(b,
-a,c){var d=[],g=0,e=null,h=null,f=0,i=0,j=ia(8);function o(k){if(k>g){if(e&&e!==h){d.push("</span>");e=null}if(!e&&h){e=h;d.push('<span class="',e,'">')}var l=E(j(b.substring(g,k))).replace(/(\r\n?|\n| ) /g,"$1&nbsp;").replace(/\r\n?|\n/g,"<br />");d.push(l);g=k}}while(true){var m;m=f<a.length?(i<c.length?a[f]<=c[i]:true):false;if(m){o(a[f]);if(e){d.push("</span>");e=null}d.push(a[f+1]);f+=2}else if(i<c.length){o(c[i]);h=c[i+1];i+=2}else break}o(b.length);if(e)d.push("</span>");return d.join("")}
-var C={};function q(b,a){for(var c=a.length;--c>=0;){var d=a[c];if(!C.hasOwnProperty(d))C[d]=b;else if("console"in window)console.log("cannot override language handler %s",d)}}q(G,["default-code"]);q(ua,["default-markup","html","htm","xhtml","xml","xsl"]);q(r({keywords:I,hashComments:true,cStyleComments:true}),["c","cc","cpp","cs","cxx","cyc"]);q(r({keywords:J,cStyleComments:true}),["java"]);q(r({keywords:O,hashComments:true,multiLineStrings:true}),["bsh","csh","sh"]);q(r({keywords:M,hashComments:true,
-multiLineStrings:true,tripleQuotedStrings:true}),["cv","py"]);q(r({keywords:L,hashComments:true,multiLineStrings:true,regexLiterals:true}),["perl","pl","pm"]);q(r({keywords:N,hashComments:true,multiLineStrings:true,regexLiterals:true}),["rb"]);q(r({keywords:K,cStyleComments:true,regexLiterals:true}),["js"]);function T(b,a){try{var c=na(b),d=c.source,g=c.tags;if(!C.hasOwnProperty(a))a=/^\s*</.test(d)?"default-markup":"default-code";var e=C[a].call({},d);return va(d,g,e)}catch(h){if("console"in window){console.log(h);
-console.trace()}return b}}function wa(b){var a=H(),c=[document.getElementsByTagName("pre"),document.getElementsByTagName("code"),document.getElementsByTagName("xmp")],d=[];for(var g=0;g<c.length;++g)for(var e=0;e<c[g].length;++e)d.push(c[g][e]);c=null;var h=0;function f(){var i=(new Date).getTime()+250;for(;h<d.length&&(new Date).getTime()<i;h++){var j=d[h];if(j.className&&j.className.indexOf("prettyprint")>=0){var o=j.className.match(/\blang-(\w+)\b/);if(o)o=o[1];var m=false;for(var k=j.parentNode;k;k=
-k.parentNode)if((k.tagName==="pre"||k.tagName==="code"||k.tagName==="xmp")&&k.className&&k.className.indexOf("prettyprint")>=0){m=true;break}if(!m){var l=ha(j);l=l.replace(/(?:\r\n?|\n)$/,"");var n=T(l,o);if(!S(j))j.innerHTML=n;else{var p=document.createElement("PRE");for(var t=0;t<j.attributes.length;++t){var w=j.attributes[t];if(w.specified)p.setAttribute(w.name,w.value)}p.innerHTML=n;j.parentNode.replaceChild(p,j);p=j}if(a&&j.tagName==="PRE"){var A=j.getElementsByTagName("br");for(var B=A.length;--B>=
-0;){var s=A[B];s.parentNode.replaceChild(document.createTextNode("\r\n"),s)}}}}}if(h<d.length)setTimeout(f,250);else if(b)b()}f()}window.PR_normalizedHtml=z;window.prettyPrintOne=T;window.prettyPrint=wa;window.PR={createSimpleLexer:v,registerLangHandler:q,sourceDecorator:r,PR_ATTRIB_NAME:"atn",PR_ATTRIB_VALUE:"atv",PR_COMMENT:"com",PR_DECLARATION:"dec",PR_KEYWORD:"kwd",PR_LITERAL:"lit",PR_PLAIN:"pln",PR_PUNCTUATION:"pun",PR_SOURCE:"src",PR_STRING:"str",PR_TAG:"tag",PR_TYPE:"typ"}})();
diff --git a/slf4j-site/src/site/pages/legacy.html b/slf4j-site/src/site/pages/legacy.html
deleted file mode 100755
index 1dfe6c55..00000000
--- a/slf4j-site/src/site/pages/legacy.html
+++ /dev/null
@@ -1,267 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>Log4j Bridge</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" media="print" href="css/print.css" />
-
-</head>
-
-<body onload="decorate();">
- <script type="text/javascript">prefix='';</script>
-
- <script type="text/javascript" src="templates/header.js"></script>
- <script type="text/javascript" src="js/jquery-min.js"></script>
- <script type="text/javascript" src="js/decorator.js"></script>
-
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
-
- <h2>Bridging legacy APIs</h2>
-
- <p>Often, some of the components you depend on rely on a logging
- API other than SLF4J. You may also assume that these components
- will not switch to SLF4J in the immediate future. To deal with
- such circumstances, SLF4J ships with several bridging modules
- which redirect calls made to log4j, JCL and java.util.logging APIs
- to behave as if they were made to the SLF4J API instead. The
- figure below illustrates the idea.
- </p>
-
- <p>Please note that for source code under your control, you really
- should use the <a href="migrator.html">slf4j-migrator</a>. The
- binary-based solutions described in this page are appropriate for
- software beyond your control.
- </p>
-
- <p></p>
- <p></p>
-
-
- <p><a href="images/legacy.png">
- <img src="images/legacy.png" alt="click to enlarge" width="800"/>
- </a></p>
-
- <p>
- </p>
-
- <h2 class="doAnchor" name="jcl-over-slf4j">Gradual migration to
- SLF4J from Jakarta Commons Logging (JCL)</h2>
-
- <h4 class="doAnchor" name="jclOverSLF4J"><em>jcl-over-slf4j.jar</em></h4>
-
- <p>To ease migration to SLF4J from JCL, SLF4J distributions
- include the jar file <em>jcl-over-slf4j.jar</em>. This jar file is
- intended as a drop-in replacement for JCL version 1.1.1. It
- implements the public API of JCL but using SLF4J underneath, hence
- the name "JCL over SLF4J."
- </p>
-
- <p>Our JCL over SLF4J implementation will allow you to migrate to
- SLF4J gradually, especially if some of the libraries your software
- depends on continue to use JCL for the foreseeable future. You can
- immediately enjoy the benefits of SLF4J's reliability and preserve
- backward compatibility at the same time. Just replace
- <em>commons-logging.jar</em> with
- <em>jcl-over-slf4j.jar</em>. Subsequently, the selection of the
- underlying logging framework will be done by SLF4J instead of JCL
- <a href="http://articles.qos.ch/classloader.html">but without the
- class loader headaches plaguing JCL</a>. The underlying logging
- framework can be any of the frameworks supported by SLF4J. Often
- times, replacing <em>commons-logging.jar</em> with
- <em>jcl-over-slf4j.jar</em> will immediately and permanently solve
- class loader issues related to commons logging.
- </p>
-
- <h3 class="doAnchor" name="slf4jJCL"><em>slf4j-jcl.jar</em></h3>
-
- <p>Some of our users after having switched to SLF4J API realize that
- in some contexts the use of JCL is mandatory and their use of SLF4J
- can be a problem. For this uncommon but important case, SLF4J offers
- a JCL binding, found in the file <em>slf4j-jcl.jar</em>. The JCL
- binding will delegate all logging calls made through SLF4J API to
- JCL. Thus, if for some reason an existing application <em>must</em>
- use JCL, your part of that application can still code against the
- SLF4J API in a manner transparent to the larger application
- environment. Your choice of SLF4J API will be invisible to the rest
- of the application which can continue to use JCL.
- </p>
-
- <h3 class="doAnchor"
- name="jclRecursion"><em>jcl-over-slf4j.jar</em> should not be
- confused with <em>slf4j-jcl.jar</em></h3>
-
-
- <p>JCL-over-SLF4J, i.e. <em>jcl-over-slf4j.jar</em>, comes in handy
- in situations where JCL needs to be supported for backward
- compatibility reasons. It can be used to fix problems associated
- with JCL, without necessarily adopting the SLF4J API, a decision
- which can be deferred to a later time.
- </p>
-
- <p>On the other hand, <em>slf4j-jcl.jar</em> is useful
- <strong>after</strong> you have already adopted the SLF4J API for
- your component which needs to be embedded in a larger application
- environment where JCL is a formal requirement. Your software
- component can still use SLF4J API without disrupting the larger
- application. Indeed, <em>slf4j-jcl.jar</em> will delegate all
- logging decisions to JCL so that the dependency on SLF4J API by your
- component will be transparent to the larger whole.
- </p>
-
- <p>Please note that <em>jcl-over-slf4j.jar</em> and
- <em>slf4j-jcl.jar</em> cannot be deployed at the same time. The
- former jar file will cause JCL to delegate the choice of the
- logging system to SLF4J and the latter jar file will cause SLF4J
- to delegate the choice of the logging system to JCL, resulting in
- an <a href="codes.html#jclDelegationLoop">infinite loop</a>.
- </p>
-
-
- <h2 class="doAnchor" name="log4j-over-slf4j">log4j-over-slf4j</h2>
-
- <p>SLF4J ship with a module called <em>log4j-over-slf4j</em>. It
- allows log4j users to migrate existing applications to SLF4J without
- changing <em>a single line of code</em> but simply by replacing the
- <em>log4j.jar</em> file with <em>log4j-over-slf4j.jar</em>, as
- described below.
- </p>
-
- <h4 class="doAnchor" name="losHow">How does it work?</h4>
-
- <p>The log4j-over-slf4j module contains replacements of most widely
- used log4j classes, namely <code>org.apache.log4j.Category</code>,
- <code>org.apache.log4j.Logger</code>,
- <code>org.apache.log4j.Priority</code>,
- <code>org.apache.log4j.Level</code>,
- <code>org.apache.log4j.MDC</code>, and
- <code>org.apache.log4j.BasicConfigurator</code>. These replacement
- classes redirect all work to their corresponding SLF4J classes.
- </p>
-
- <p>To use log4j-over-slf4j in your own application, the first step
- is to locate and then to replace <em>log4j.jar</em> with
- <em>log4j-over-slf4j.jar</em>. Note that you still need an SLF4J
- binding and its dependencies for log4j-over-slf4j to work properly.
- </p>
-
- <p>In most situations, replacing a jar file is all it takes in
- order to migrate from log4j to SLF4J.
- </p>
-
- <p>Note that as a result of this migration, log4j configuration
- files will no longer be picked up. If you need to migrate your
- log4j.properties file to logback, the <a
- href="http://logback.qos.ch/translator/">log4j translator</a> might
- be of help. For configuring logback, please refer to <a
- href="http://logback.qos.ch/manual/index.html">its manual</a>.
- </p>
-
- <h4 class="doAnchor" name="losFail">When does it not work?</h4>
-
- <p>The <em>log4j-over-slf4j</em> module will not work when the
- application calls log4j components that are not present in the
- bridge. For example, when application code directly references
- log4j appenders, filters or the PropertyConfigurator, then
- log4j-over-slf4j would be an insufficient replacement for
- log4j. However, when log4j is configured through a configuration
- file, be it <em>log4j.properties</em> or <em>log4j.xml</em>, the
- log4j-over-slf4j module should just work fine.
- </p>
-
-
-
- <h4 class="doAnchor" name="losOverhead">What about the
- overhead?</h4>
-
- <p>There overhead of using log4j-over-slf4j instead of log4j
- directly is relatively small. Given that log4j-over-slf4j
- immediately delegates all work to SLF4J, the CPU overhead should be
- negligible, in the order of a few <em>nanoseconds</em>. There is a
- memory overhead corresponding to an entry in a hashmap per logger,
- which should be usually acceptable even for very large applications
- consisting of several thousand loggers. Moreover, if you choose
- logback as your underlying logging system, and given that logback is
- both much faster and more memory-efficient than log4j, the gains
- made by using logback should compensate for the overhead of using
- log4j-over-slf4j instead of log4j directly.
- </p>
-
- <h4 class="doAnchor" name="log4jRecursion">log4j-over-slf4j.jar
- and slf4j-log4j12.jar cannot be present simultaneously
- </h4>
-
- <p>The presence of <em>slf4j-log4j12.jar</em>, that is the log4j
- binding for SLF4J, will force all SLF4J calls to be delegated to
- log4j. The presence of <em>log4j-over-slf4j.jar</em> will in turn
- delegate all log4j API calls to their SLF4J equivalents. If both
- are present simultaneously, slf4j calls will be delegated to
- log4j, and log4j calls redirected to SLF4j, resulting in an <a
- href="codes.html#log4jDelegationLoop">endless loop</a>.
- </p>
-
-
-
- <h2 class="doAnchor" name="jul-to-slf4j">jul-to-slf4j bridge</h2>
-
- <p>The jul-to-slf4j module includes a java.util.logging (jul)
- handler, namely <code>SLF4JBridgeHandler</code>, which routes all
- incoming jul records to the SLF4j API. Please see <a
- href="api/org/slf4j/bridge/SLF4JBridgeHandler.html">SLF4JBridgeHandler
- javadocs</a> for usage instructions.
- </p>
-
- <p><span class="label notice">Note on performance</span> Contrary
- to other bridging modules, namely jcl-over-slf4j and
- log4j-over-slf4j, which reimplement JCL and respectively log4j,
- the jul-to-slf4j module does not reimplement the java.util.logging
- because packages under the java.* namespace cannot be
- replaced. Instead, jul-to-slf4j translates <a
- href="http://java.sun.com/j2se/1.5.0/docs/api/java/util/logging/LogRecord.html?is-external=true">LogRecord</a>
- objects into their SLF4J equivalent. Please note this translation
- process incurs the cost of constructing a <code>LogRecord</code>
- instance regardless of whether the SLF4J logger is disabled for
- the given level or nor. <b>Consequently, j.u.l. to SLF4J
- translation can seriously increase the cost of disabled logging
- statements (60 fold or 6000%) and measurably impact the
- performance of enabled log statements (20% overall increase).</b>
- As of logback version 0.9.25, it is possible to completely
- eliminate the 60 fold translation overhead for disabled log
- statements with the help of <a
- href="http://logback.qos.ch/manual/configuration.html#LevelChangePropagator">LevelChangePropagator</a>.
- </p>
-
- <p>If you are concerned about application performance, then use of
- <code>SLF4JBridgeHandler</code> is appropriate only if any one of
- the following two conditions is true:
- </p>
- <ol>
- <li>few j.u.l. logging statements are in play </li>
- <li><code>LevelChangePropagator</code> has been installed</li>
- </ol>
-
-
- <h4 class="doAnchor" name="julRecursion">jul-to-slf4j.jar and slf4j-jdk14.jar cannot be present
- simultaneously
- </h4>
-
- <p>The presence of slf4j-jdk14.jar, that is the jul binding for
- SLF4J, will force SLF4J calls to be delegated to jul. On the other
- hand, the presence of jul-to-slf4j.jar, plus the installation of
- SLF4JBridgeHandler, by invoking "SLF4JBridgeHandler.install()" will
- route jul records to SLF4J. Thus, if both jar are present
- simultaneously (and SLF4JBridgeHandler is installed), slf4j calls
- will be delegated to jul and jul records will be routed to SLF4J,
- resulting in an endless loop.
- </p>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
- </div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/license.html b/slf4j-site/src/site/pages/license.html
deleted file mode 100644
index f895b75f..00000000
--- a/slf4j-site/src/site/pages/license.html
+++ /dev/null
@@ -1,68 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
- <html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J License</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
- <script type="text/javascript">prefix='';</script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
-
- <h1>Licensing terms for SLF4J</h1>
-
- <p>SLF4J source code and binaries are distributed under the
- MIT license.
- </p>
-
- <div class="source">
- Copyright (c) 2004-2013 QOS.ch
- All rights reserved.
-
- Permission is hereby granted, free of charge, to any person obtaining
- a copy of this software and associated documentation files (the
- "Software"), to deal in the Software without restriction, including
- without limitation the rights to use, copy, modify, merge, publish,
- distribute, sublicense, and/or sell copies of the Software, and to
- permit persons to whom the Software is furnished to do so, subject to
- the following conditions:
-
- The above copyright notice and this permission notice shall be
- included in all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- </div>
-
- <p>These terms are <em>identical</em> to those of the <a
- href="http://en.wikipedia.org/wiki/MIT_License">MIT License</a>,
- also called the X License or the X11 License, which is a simple,
- permissive non-copyleft free software license. It is deemed
- compatible with virtually all types of licenses, commercial or
- otherwise. In particular, the Free Software Foundation has declared
- it compatible with <a
- href="http://www.fsf.org/licensing/licenses/license-list.html#GPLCompatibleLicenses">
- GNU GPL</a>. It is also known to be approved by the Apache Software
- Foundation as compatible with <a
- href="http://www.apache.org/licenses/">Apache Software License</a>.
- </p>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/localization.html b/slf4j-site/src/site/pages/localization.html
deleted file mode 100755
index b321c63c..00000000
--- a/slf4j-site/src/site/pages/localization.html
+++ /dev/null
@@ -1,158 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>Localization</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
- </head>
- <body onload="prettyPrint()">
-
- <script type="text/javascript">prefix='';</script>
-
- <script type="text/javascript" src="js/prettify.js"></script>
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <noscript>Please turn on Javascript to view this menu</noscript>
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
-
- <div id="content">
-
-
- <h1>Localization support</h1>
-
- <p>A <a
- href="http://markmail.org/thread/drcabfc6z42sijdo">discussion</a>
- on the slf4j-dev mailing list spawned an open-source project
- called <a href="http://cal10n.qos.ch"><b>CAL10N or Compiler
- Assisted Localization</b></a>. As its name indicates, CAL10N
- focuses on the issue of localization/internationalization in Java
- applications.
- </p>
-
- <p>The <code>org.slf4j.cal10n</code> package which ships with
- <em>slf4j-ext-${project.version}.jar</em> adds an extremely thin
- layer on top of CALI0N to offer localized logging.</p>
-
-
- <p>Once you have a handle on an <a
- href="http://cal10n.qos.ch/apidocs/ch/qos/cal10n/IMessageConveyor.html">IMessageConveyor</a>
- instance, you can create a <a
- href="xref/org/slf4j/cal10n/LocLoggerFactory.html">LocLoggerFactory</a>,
- which in turn can create <a
- href="xref/org/slf4j/cal10n/LocLogger.html">LocLogger</a>
- instances capable of doing localized logging.
- </p>
-
-
- <p>Let us assume that you have defined localized message in your
- application. In accordance with the CAL10N's philosophy, you have
- the declared the keys for those messages in the enum type
- <code>Production</code>.</p>
-
-
- <pre class="prettyprint source">import ch.qos.cal10n.LocaleData;
-import ch.qos.cal10n.Locale;
-import ch.qos.cal10n.BaseName;
-
-@BaseName("production")
-@LocaleData( { @Locale("en_UK"), @Locale("ja_JP") })
-public enum Production {
- APPLICATION_STARTED,
- APPLICATION_STOPPED,
- ...
- DB_CONNECTION,
- DB_CONNECTION_FAILURE;
-}</pre>
-
- <p>It is assumed that you have created appropriate bundle file for
- the various locales "en_UK" and "ja_JP" as appropriate. Here is a
- sample bundle for the "en_UK" locale.
- </p>
-
-
- <pre class="source">APPLICATION_STARTED=Application <b>{0}</b> has started.
-APPLICATION_STOPPED=Application <b>{0}</b> has stopped.
-... </pre>
-
- <p>Then, you
- can instantiate a <code>IMessageConveyor</code>, inject it into a
- <code>LogLoggerFactory</code>, retrieve multiple
- <code>LogLogger</code> instances by name and log away, as the next
- sample code illustrates.
- </p>
-
-
- <pre class="prettyprint source">import java.util.Locale;
-
-import org.slf4j.cal10n.LocLogger;
-import org.slf4j.cal10n.LocLoggerFactory;
-
-import ch.qos.cal10n.IMessageConveyor;
-import ch.qos.cal10n.MessageConveyor;
-
-public class MyApplication {
-
- // create a message conveyor for a given locale
- IMessageConveyor messageConveyor = new MessageConveyor(Locale.UK);
-
- // create the LogLoggerFactory
- LocLoggerFactory llFactory_uk = new LocLoggerFactory(messageConveyor);
-
- // create a locLogger
- LocLogger locLogger = llFactory_uk.getLocLogger(this.getClass());
-
-
- public void applicationStart() {
- locLogger.info(Production.APPLICATION_STARTED, "fooApp");
- // ..
- }
-
- public void applicationStop() {
- locLogger.info(Production.APPLICATION_STOPPED, "fooApp");
- // ...
- }
-}</pre>
-
- <p>Assuming the resource bundle
- <em>production_en_UK.properties</em> exists, and the underlying
- logging framework is enabled for the info level, log messages will
- be output in UK English.
- </p>
-
- <p>Note that a <code>LogLogger</code> is a regular SLF4J logger
- with additional methods supporting localization. For those
- additional methods which take an enum as first parameter,
- <code>LogLogger</code> follows the standard Java convention for
- parameter substitution as defined by the <a
- href="http://java.sun.com/j2se/1.5.0/docs/api/java/text/MessageFormat.html">java.text.MessageFormat</a>
- class. For non-localized logs, which take a String as first
- parameter, <code>LogLogger</code> follows the {} convention, as
- customary for all <code>org.slf4j.Logger</code> implementations.
- </p>
-
- <p>Here is an example illustrating the difference.</p>
-
- <pre class="prettyprint source">import ...;
-public class MyApplication {
-
- IMessageConveyor messageConveyor = new MessageConveyor(Locale.UK);
- LocLoggerFactory llFactory_uk = new LocLoggerFactory(messageConveyor);
- LocLogger locLogger = llFactory_uk.getLocLogger(this.getClass());
-
- public void someMethod() {
- // follows the MessageFormat convention
- locLogger.info(Production.APPLICATION_STARTED, "fooApp");
-
- // follows the {} convention
- logLogger.info("Hello {}", name);
- ...
- }
-}</pre>
- <script src="templates/footer.js" type="text/javascript"></script>
- </div>
- </body>
-</html>
diff --git a/slf4j-site/src/site/pages/mailing-lists.html b/slf4j-site/src/site/pages/mailing-lists.html
deleted file mode 100755
index 09611469..00000000
--- a/slf4j-site/src/site/pages/mailing-lists.html
+++ /dev/null
@@ -1,128 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
- <script type="text/javascript">prefix='';</script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
- <h1>SLF4J Mailing Lists</h1>
-
- <p>A mailing list is an electronic discussion forum that anyone can
- subscribe to. When someone sends an email message to the mailing
- list, a copy of that message is broadcast to everyone who is
- subscribed to that mailing list. Mailing lists provide a simple and
- effective communication mechanism. With potentially thousands of
- subscribers, there is a common set of etiquette guidelines that you
- should observe. Please keep on reading.
- </p>
-
- <h3>Respect the mailing list type</h3>
-
- <p>The "User" lists where you can send questions and comments about
- configuration, setup, usage and other "user" types of questions.
- The "Developer" lists where you can send questions and comments
- about the actual software source code and general "development"
- types of questions.
- </p>
-
- <p>Some questions are appropriate for posting on both the "user" and
- the "developer" lists. In this case, pick one and only one. Do not
- cross post.
- </p>
-
- <p>Please do your best to ensure that you are not sending HTML or
- "Stylized" email to the list. If you are using Outlook or Outlook
- Express or Eudora, chances are that you are sending HTML email by
- default. There is usually a setting that will allow you to send
- "Plain Text" email.
- </p>
-
-<!--
- <p>These lists are archived at
-
- <ul>
- <li><a href="http://logging.apache.org/mail/">Full mbox archives of all lists</a></li>
- <li> <a href="http://nagoya.apache.org/eyebrowse/">Eyebrowse Archives</a></li>
- <li>The Aims Group <a href="http://marc.theaimsgroup.com/">Archives</a></li>
- </ul>
- </p>
--->
-
-
-
- <h3>slf4j-announcements list</h3>
-
- <p>
- <b>Low Traffic:</b>
- <a href="http://www.qos.ch/mailman/listinfo/announce">Subscribe</a> |
- <a href="http://www.qos.ch/mailman/options/announce">Unsubscribe</a>
- <br/>
- <b>Archives:</b>
- <a href="http://www.qos.ch/pipermail/announce/">Pipermail</a> |
- <a href="http://slf4j.42922.n3.nabble.com/Slf4J-announce-f46208.html">Nabble</a>
- </p>
- <p>The announcements list is reserved for important SLF4J API
- related announcements. As such, the traffic on this list is
- guaranteed to be very low.
- </p>
-
- <p>Given that implementations are expected to statically bind with
- the SLF4J API, we recommend that any implementor of the SLF4J API
- be subscribed at least to the announcements list.
- </p>
-
- <h3>slf4j-user list</h3>
-
- <p>
- <b>Medium Traffic:</b>
- <a href="http://www.qos.ch/mailman/listinfo/slf4j-user">Subscribe</a> |
- <a href="http://www.qos.ch/mailman/options/slf4j-user">Unsubscribe</a>
- <br/>
- <b>Archives:</b>
- <a href="http://www.qos.ch/pipermail/slf4j-user/">qos.ch</a> |
- <a href="http://markmail.org/search/?q=order%3Adate-backward+list%3Aorg.slf4j.user">MarkLogic</a> |
- <a href="http://news.gmane.org/gmane.comp.java.slf4j.user">Gmane</a> |
- <a href="http://slf4j.42922.n3.nabble.com/slf4j-user-f41810.html">Nabble</a> |
- <a href="http://www.mail-archive.com/user%40slf4j.org/">MailArchive</a>
- <a href=""> </a>
-
-
- </p>
-
- <p>This is the list for users of slf4j. It is also a good forum for
- asking questions about how slf4j works, and how it can be
- used. SLF4J developers are usually subscribed to to this list in
- order to offer support.</p>
-
-
- <h3>slf4j-dev list</h3>
-
- <p>
- <b>Medium Traffic:</b>
- <a href="http://www.qos.ch/mailman/listinfo/slf4j-dev">Subscribe</a> |
- <a href="http://www.qos.ch/mailman/options/slf4j-dev">Unsubscribe</a>
- <br/>
- <b>Archives:</b>
- <a href="http://www.qos.ch/pipermail/slf4j-dev/">qos.ch</a> |
- <a href="http://markmail.org/search/?q=order%3Adate-backward+list%3Aorg.slf4j.dev">MarkLogic</a> |
- <a href="http://news.gmane.org/gmane.comp.java.slf4j.devel">Gmane</a> |
- <a href="http://slf4j.42922.n3.nabble.com/slf4j-dev-f41812.html">Nabble</a> |
- <a href="http://www.mail-archive.com/dev%40slf4j.org/">MailArchive</a>
- </p>
- <p>&nbsp;</p>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/manual.html b/slf4j-site/src/site/pages/manual.html
deleted file mode 100755
index 2c4430f0..00000000
--- a/slf4j-site/src/site/pages/manual.html
+++ /dev/null
@@ -1,539 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Manual</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
- </head>
- <body onload="prettyPrint(); decorate();">
- <script type="text/javascript">prefix='';</script>
- <script type="text/javascript" src="js/prettify.js"></script>
- <script type="text/javascript" src="js/jquery-min.js"></script>
- <script type="text/javascript" src="js/decorator.js"></script>
- <script type="text/javascript" src="templates/header.js"></script>
- <div id="left">
- <script type="text/javascript" src="templates/left.js"></script>
- </div>
- <div id="content">
-
-
- <h2>SLF4J user manual</h2>
-
- <p>The Simple Logging Facade for Java (SLF4J) serves as a simple
- facade or abstraction for various logging frameworks, such as
- java.util.logging, logback and log4j. SLF4J allows the end-user to
- plug in the desired logging framework at <em>deployment</em> time.
- Note that SLF4J-enabling your library/application implies the
- addition of only a single mandatory dependency, namely
- <em>slf4j-api-${project.version}.jar</em>.</p>
-
- <p><span class="label">since 1.6.0</span> If no binding is found on the
- class path, then SLF4J will default to a no-operation
- implementation.
- </p>
-
- <p><span class="label">since 1.7.0</span> Printing methods in the
- <a href="apidocs/org/slf4j/Logger.html"><code>Logger</code></a>
- interface now offer variants accepting <a
- href="http://docs.oracle.com/javase/1.5.0/docs/guide/language/varargs.html">varargs</a>
- instead of <code>Object[]</code>. This change implies that SLF4J
- requires JDK 1.5 or later. Under the hood the Java compiler
- transforms the varargs part in methods into
- <code>Object[]</code>. Thus, the Logger interface generated by the
- compiler is indistinguishable in 1.7.x from its 1.6.x
- counterpart. It follows that SLF4J version 1.7.x is totally 100%
- no-ifs-or-buts compatible with SLF4J version 1.6.x.
- </p>
-
- <p><span class="label">since 1.7.5</span> Significant improvement
- in logger retrieval times. Given the extent of the improvement,
- users are highly encouraged to migrate to SLF4J 1.7.5 or later.
- </p>
-
- <p><span class="label">since 1.7.9</span> By setting the
- <code>slf4j.detectLoggerNameMismatch</code> system property to
- true, SLF4J can automatically <a
- href="codes.html#loggerNameMismatch">spot incorrectly named
- loggers</a>.
- </p>
-
-
- <h3 class="doAnchor" name="hello_world">Hello World</h3>
-
- <p>As customary in programming tradition, here is an example
- illustrating the simplest way to output "Hello world" using SLF4J.
- It begins by getting a logger with the name "HelloWorld". This
- logger is in turn used to log the message "Hello World".
- </p>
-
-<pre class="prettyprint source">import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class HelloWorld {
- public static void main(String[] args) {
- Logger logger = LoggerFactory.getLogger(HelloWorld.class);
- logger.info("Hello World");
- }
-}</pre>
-
- <p>To run this example, you first need to <a
- href="download.html">download the slf4j distribution</a>, and
- then to unpack it. Once that is done, add the file
- <em>slf4j-api-${project.version}.jar</em> to your class path.</p>
-
- <p>Compiling and running <em>HelloWorld</em> will result in the
- following output being printed on the console.</p>
-
-<pre>SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
-SLF4J: Defaulting to no-operation (NOP) logger implementation
-SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.</pre>
-
- <p>This warning is printed because no slf4j binding could be
- found on your class path.</p>
-
- <p>The warning will disappear as soon as you add a <a
- href="#swapping">binding</a> to your class path. Assuming you add
- <em>slf4j-simple-${project.version}.jar</em> so that your class
- path contains:</p>
-
- <ul>
- <li>slf4j-api-${project.version}.jar</li>
- <li>slf4j-simple-${project.version}.jar</li>
- </ul>
-
- <p>Compiling and running <em>HelloWorld</em> will now result in
- the following output on the console.</p>
-
- <pre class="output">0 [main] INFO HelloWorld - Hello World</pre>
-
- <h3 class="doAnchor" name="typical_usage">Typical usage
- pattern</h3>
-
- <p>The sample code below illustrates the typical usage pattern
- for SLF4J. Note the use of {}-placeholders on line 15. See the
- question <a href="faq.html#logging_performance">"What is the
- fastest way of logging?"</a> in the FAQ for more details.
- </p>
-
- <p></p>
-
- <pre class="prettyprint source"> 1: <b>import org.slf4j.Logger;</b>
- 2: <b>import org.slf4j.LoggerFactory;</b>
- 3:
- 4: public class Wombat {
- 5:
- 6: <b>final Logger logger = LoggerFactory.getLogger(Wombat.class);</b>
- 7: Integer t;
- 8: Integer oldT;
- 9:
-10: public void setTemperature(Integer temperature) {
-11:
-12: oldT = t;
-13: t = temperature;
-14:
-15: <b>logger.debug("Temperature set to {}. Old temperature was {}.", t, oldT);</b>
-16:
-17: if(temperature.intValue() > 50) {
-18: <b>logger.info("Temperature has risen above 50 degrees.");</b>
-19: }
-20: }
-21: } </pre>
-
-
-
- <h3 class="doAnchor" name="swapping">Binding with a logging
- framework at deployment time</h3>
-
- <p>As mentioned previously, SLF4J supports various logging
- frameworks. The SLF4J distribution ships with several jar files
- referred to as "SLF4J bindings", with each binding corresponding
- to a supported framework. </p>
-
- <dl>
-
- <dt><em>slf4j-log4j12-${project.version}.jar</em>
- </dt>
- <dd>Binding for <a
- href="http://logging.apache.org/log4j/1.2/index.html">log4j
- version 1.2</a>, a widely used logging framework. You also
- need to place <em>log4j.jar</em> on your class path.<p/></dd>
-
- <dt><em>slf4j-jdk14-${project.version}.jar</em> </dt>
- <dd>Binding for java.util.logging, also referred to as JDK 1.4
- logging <p/></dd>
-
- <dt><em>slf4j-nop-${project.version}.jar</em></dt>
- <dd>Binding for <a
- href="http://www.slf4j.org/api/org/slf4j/helpers/NOPLogger.html">NOP</a>,
- silently discarding all logging.<p/></dd>
-
- <dt><em>slf4j-simple-${project.version}.jar</em></dt>
- <dd>Binding for <a
- href="http://www.slf4j.org/apidocs/org/slf4j/impl/SimpleLogger.html">Simple
- </a> implementation, which outputs all events to
- System.err. Only messages of level INFO and higher are
- printed. This binding may be useful in the context of small
- applications.<p/></dd>
-
- <dt><em>slf4j-jcl-${project.version}.jar</em></dt>
-
- <dd>Binding for <a
- href="http://commons.apache.org/logging/">Jakarta Commons
- Logging</a>. This binding will delegate all SLF4J logging to
- JCL.<p/>
- </dd>
-
- <dt><em>logback-classic-${logback.version}.jar (requires logback-core-${logback.version}.jar)</em></dt>
-
- <dd><span class="label notice">Native implementation</span> There are also
- SLF4J bindings external to the SLF4J project, e.g. <a
- href="http://logback.qos.ch/">logback</a> which implements
- SLF4J natively. Logback's
- <a href="http://logback.qos.ch/apidocs/ch/qos/logback/classic/Logger.html">
- <code>ch.qos.logback.classic.Logger</code></a> class is a
- direct implementation of SLF4J's <a
- href="http://www.slf4j.org/apidocs/org/slf4j/Logger.html">
- <code>org.slf4j.Logger</code></a> interface. Thus, using SLF4J
- in conjunction with logback involves strictly zero memory and
- computational overhead.
-
- </dd>
- </dl>
-
- <p>
- </p>
-
-
- <p>To switch logging frameworks, just replace slf4j bindings on
- your class path. For example, to switch from java.util.logging
- to log4j, just replace slf4j-jdk14-${project.version}.jar with
- slf4j-log4j12-${project.version}.jar.
- </p>
-
- <p>SLF4J does not rely on any special class loader machinery. In
- fact, each SLF4J binding is hardwired <em>at compile time</em>
- to use one and only one specific logging framework. For
- example, the slf4j-log4j12-${project.version}.jar binding is
- bound at compile time to use log4j. In your code, in addition
- to <em>slf4j-api-${project.version}.jar</em>, you simply drop
- <b>one and only one</b> binding of your choice onto the
- appropriate class path location. Do not place more than one
- binding on your class path. Here is a graphical illustration of
- the general idea.
- </p>
-
- <p><a href="images/concrete-bindings.png">
- <img border="1" src="images/concrete-bindings.png" alt="click to enlarge" width="800"/>
- </a></p>
-
- <p>The SLF4J interfaces and their various adapters are extremely
- simple. Most developers familiar with the Java language should
- be able to read and fully understand the code in less than one
- hour. No knowledge of class loaders is necessary as SLF4J does
- not make use nor does it directly access any class loaders. As a
- consequence, SLF4J suffers from none of the class loader
- problems or memory leaks observed with Jakarta Commons Logging
- (JCL).
- </p>
-
- <p>Given the simplicity of the SLF4J interfaces and its
- deployment model, developers of new logging frameworks should
- find it very easy to write SLF4J bindings.
- </p>
-
- <h3 class="doAnchor" name="libraries">Libraries</h3>
-
- <p>Authors of widely-distributed components and libraries may
- code against the SLF4J interface in order to avoid imposing an
- logging framework on their end-user. Thus, the end-user may
- choose the desired logging framework at deployment time by
- inserting the corresponding slf4j binding on the classpath,
- which may be changed later by replacing an existing binding with
- another on the class path and restarting the application. This
- approach has proven to be simple and very robust.
- </p>
-
- <p><b>As of SLF4J version 1.6.0</b>, if no binding is found on
- the class path, then slf4j-api will default to a no-operation
- implementation discarding all log requests. Thus, instead of
- throwing a <code>NoClassDefFoundError</code> because the
- <code>org.slf4j.impl.StaticLoggerBinder</code> class is missing,
- SLF4J version 1.6.0 and later will emit a single warning message
- about the absence of a binding and proceed to discard all log
- requests without further protest. For example, let Wombat be
- some biology-related framework depending on SLF4J for
- logging. In order to avoid imposing a logging framework on the
- end-user, Wombat's distribution includes <em>slf4j-api.jar</em>
- but no binding. Even in the absence of any SLF4J binding on the
- class path, Wombat's distribution will still work
- out-of-the-box, and without requiring the end-user to download a
- binding from SLF4J's web-site. Only when the end-user decides to
- enable logging will she need to install the SLF4J binding
- corresponding to the logging framework chosen by her.
- </p>
-
- <p><span class="label">Basic rule</span> <b>Embedded components
- such as libraries or frameworks should not declare a dependency
- on any SLF4J binding but only depend on slf4j-api</b>. When a
- library declares a transitive dependency on a specific binding,
- that binding is imposed on the end-user negating the purpose of
- SLF4J. Note that declaring a non-transitive dependency on a
- binding, for example for testing, does not affect the
- end-user.</p>
-
- <p>SLF4J usage in embedded components is also discussed in the
- FAQ in relation with <a
- href="faq.html#configure_logging">logging configuration</a>, <a
- href="faq.html#optional_dependency">dependency reduction</a> and
- <a href="faq.html#optional_dependency">testing</a>.</p>
-
- <h3 class="doAnchor" name="projectDep">Declaring project
- dependencies for logging</h3>
-
- <p>Given Maven's transitive dependency rules, for "regular"
- projects (not libraries or frameworks) declaring logging
- dependencies can be accomplished with a single dependency
- declaration.
- </p>
-
- <p><span class="label notice">logback-classic</span> If you wish
- to use logback-classic as the underlying logging framework, all
- you need to do is to declare "ch.qos.logback:logback-classic" as
- a dependency in your <em>pom.xml</em> file as shown below. In
- addition to <em>logback-classic-${logback.version}.jar</em>,
- this will pull <em>slf4j-api-${project.version}.jar</em> as well
- as <em>logback-core-${logback.version}.jar</em> into your
- project. Note that explicitly declaring a dependency on
- <em>logback-core-${logback.version}</em> or
- <em>slf4j-api-${project.version}.jar</em> is not wrong and may
- be necessary to impose the correct version of said artifacts by
- virtue of Maven's "nearest definition" dependency mediation
- rule.
- </p>
-
-<pre class="prettyprint source">&lt;dependency>
- &lt;groupId>ch.qos.logback&lt;/groupId>
- &lt;artifactId>logback-classic&lt;/artifactId>
- &lt;version>${logback.version}&lt;/version>
-&lt;/dependency></pre>
-
- <p/>
-
- <p><span class="label notice">log4j</span> If you wish to use
- log4j as the underlying logging framework, all you need to do is
- to declare "org.slf4j:slf4j-log4j12" as a dependency in your
- <em>pom.xml</em> file as shown below. In addition to
- <em>slf4j-log4j12-${project.version}.jar</em>, this will pull
- <em>slf4j-api-${project.version}.jar</em> as well as
- <em>log4j-${log4j.version}.jar</em> into your project. Note
- that explicitly declaring a dependency on
- <em>log4j-${log4j.version}.jar</em> or
- <em>slf4j-api-${project.version}.jar</em> is not wrong and may
- be necessary to impose the correct version of said artifacts by
- virtue of Maven's "nearest definition" dependency mediation
- rule.</p>
-
-<pre class="prettyprint source">&lt;dependency>
- &lt;groupId>org.slf4j&lt;/groupId>
- &lt;artifactId>slf4j-log4j12&lt;/artifactId>
- &lt;version>${project.version}&lt;/version>
-&lt;/dependency></pre>
-
- <p/>
-
- <p><span class="label notice">java.util.logging</span> If you
- wish to use java.util.logging as the underlying logging
- framework, all you need to do is to declare
- "org.slf4j:slf4j-jdk14" as a dependency in your <em>pom.xml</em>
- file as shown below. In addition to
- <em>slf4j-jdk14-${project.version}.jar</em>, this will pull
- <em>slf4j-api-${project.version}.jar</em> into your project.
- Note that explicitly declaring a dependency on
- <em>slf4j-api-${project.version}.jar</em> is not wrong and may
- be necessary to impose the correct version of said artifact by
- virtue of Maven's "nearest definition" dependency mediation
- rule.</p>
-
-<pre class="prettyprint source">&lt;dependency>
- &lt;groupId>org.slf4j&lt;/groupId>
- &lt;artifactId>slf4j-jdk14&lt;/artifactId>
- &lt;version>${project.version}&lt;/version>
-&lt;/dependency></pre>
-
-
-
- <h3 class="doAnchor" name="compatibility">Binary
- compatibility</h3>
-
- <p>An SLF4J binding designates an artifact such as
- <em>slf4j-jdk14.jar</em> or <em>slf4j-log4j12.jar</em> used to
- <em>bind</em> slf4j to an underlying logging framework, say,
- java.util.logging and respectively log4j.
- </p>
-
- <p class="highlight">From the client's perspective all versions
- of slf4j-api are compatible. Client code compiled with
- slf4j-api-N.jar will run perfectly fine with slf4j-api-M.jar for
- any N and M. You only need to ensure that the version of your
- binding matches that of the slf4j-api.jar. You do not have to
- worry about the version of slf4j-api.jar used by a given
- dependency in your project. </p>
-
-
- <p>Mixing different versions of <em>slf4j-api.jar</em> and SLF4J
- binding can cause problems. For example, if you are using
- slf4j-api-${project.version}.jar, then you should also use
- slf4j-simple-${project.version}.jar, using
- slf4j-simple-1.5.5.jar will not work.</p>
-
-
- <p>However, from the client's perspective all versions of
- slf4j-api are compatible. Client code compiled with
- <em>slf4j-api-N.jar</em> will run perfectly fine with
- <em>slf4j-api-M.jar</em> for any N and M. You only need to
- ensure that the version of your binding matches that of the
- slf4j-api.jar. You do not have to worry about the version of
- slf4j-api.jar used by a given dependency in your project. You
- can always use any version of <em>slf4j-api.jar</em>, and as
- long as the version of <em>slf4j-api.jar</em> and its binding
- match, you should be fine.
- </p>
-
- <p>At initialization time, if SLF4J suspects that there may be
- an slf4j-api vs. binding version mismatch problem, it will emit
- a warning about the suspected mismatch.
- </p>
-
-
- <h3 class="doAnchor" name="consolidate">Consolidate logging via
- SLF4J</h3>
-
- <p>Often times, a given project will depend on various
- components which rely on logging APIs other than SLF4J. It is
- common to find projects depending on a combination of JCL,
- java.util.logging, log4j and SLF4J. It then becomes desirable to
- consolidate logging through a single channel. SLF4J caters for
- this common use-case by providing bridging modules for JCL,
- java.util.logging and log4j. For more details, please refer to
- the page on <a href="legacy.html"><b>Bridging legacy
- APIs</b></a>.
- </p>
-
- <h3 class="doAnchor" name="mdc">Mapped Diagnostic Context (MDC) support</h3>
-
- <p>"Mapped Diagnostic Context" is essentially a map maintained
- by the logging framework where the application code provides
- key-value pairs which can then be inserted by the logging
- framework in log messages. MDC data can also be highly helpful
- in filtering messages or triggering certain actions.</p>
-
- <p>SLF4J supports MDC, or mapped diagnostic context. If the
- underlying logging framework offers MDC functionality, then
- SLF4J will delegate to the underlying framework's MDC. Note that
- at this time, only log4j and logback offer MDC functionality. If
- the underlying framework does not offer MDC, for example
- java.util.logging, then SLF4J will still store MDC data but the
- information therein will need to be retrieved by custom user
- code.</p>
-
- <p>Thus, as a SLF4J user, you can take advantage of MDC
- information in the presence of log4j or logback, but without
- forcing these logging frameworks upon your users as
- dependencies.
- </p>
-
- <p>For more information on MDC please see the <a
- href="http://logback.qos.ch/manual/mdc.html">chapter on MDC</a>
- in the logback manual.
- </p>
-
-
-
- <h3 class="doAnchor" name="summary">Executive summary</h3>
-
- <table class="bodyTable striped" cellspacing="4" cellpadding="4">
- <tr>
- <th align="left">Advantage</th>
- <th align="left">Description</th>
- </tr>
-
- <tr>
-
- <td>Select your logging framework at deployment time</td>
-
- <td>The desired logging framework can be plugged in at
- deployment time by inserting the appropriate jar file
- (binding) on your class path.
- </td>
- </tr>
-
-
- <tr>
- <td>Fail-fast operation</td>
-
- <td>Due to the way that classes are loaded by the JVM, the
- framework binding will be verified automatically very early
- on. If SLF4J cannot find a binding on the class path it
- will emit a single warning message and default to
- no-operation implementation.
- </td>
- </tr>
-
-
- <tr>
- <td>Bindings for popular logging frameworks
- </td>
-
- <td>SLF4J supports popular logging frameworks, namely log4j,
- java.util.logging, Simple logging and NOP. The <a
- href="http://logback.qos.ch">logback</a> project supports
- SLF4J natively. </td>
-
- </tr>
-
- <tr>
- <td>Bridging legacy logging APIs</td>
-
- <td>
- <p>The implementation of JCL over SLF4J, i.e
- <em>jcl-over-slf4j.jar</em>, will allow your project to
- migrate to SLF4J piecemeal, without breaking compatibility
- with existing software using JCL. Similarly,
- log4j-over-slf4j.jar and jul-to-slf4j modules will allow
- you to redirect log4j and respectively java.util.logging
- calls to SLF4J. See the page on <a
- href="legacy.html">Bridging legacy APIs</a> for more
- details.
- </p>
- </td>
- </tr>
-
- <tr>
- <td>Migrate your source code</td>
- <td>The <a href="migrator.html">slf4j-migrator</a> utility
- can help you migrate your source to use SLF4J.
- </td>
- </tr>
-
-
-
- <tr>
- <td>Support for parameterized log messages</td>
-
- <td>All SLF4J bindings support parameterized log messages
- with significantly <a
- href="faq.html#logging_performance">improved performance</a>
- results.</td>
- </tr>
-
-
- </table>
-
- <script src="templates/footer.js" type="text/javascript"></script>
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/migrator.html b/slf4j-site/src/site/pages/migrator.html
deleted file mode 100755
index 76948f41..00000000
--- a/slf4j-site/src/site/pages/migrator.html
+++ /dev/null
@@ -1,226 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J Migrator</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- </head>
- <body>
- <script type="text/javascript">prefix='';</script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
-
- <h1>SLF4J Migrator</h1>
-
- <p>The SLF4J migrator is a small Java tool for migrating Java source
- files from the Jakarta Commons Logging (JCL) API to SLF4J. It can
- also migrate from the log4j API to SLF4J, or from
- <code>java.util.logging</code> API to SLF4J.
- </p>
-
- <p>The SLF4J migrator consists of a single jar file that can be
- launched as a stand-alone java application. Here is the command:
- </p>
-
- <p class="source">java -jar slf4j-migrator-${version}.jar </p>
-
- <br/>
-
- <p>Once the application is launched, a window similar to the
- following should appear.
- </p>
-
- <p><img src="images/slf4j-migrator.gif" alt="slf4j-migrator.gif"/></p>
-
- <p>Use of the application should be self-explanatory. Please note that
- this migration tool does in-place replacement of Java files, meaning
- that there will be no back-up copies of modified files. <b>It is
- your responsibility to backup your files before using SLF4J
- Migrator.</b>
- </p>
-
-
- <h2>Limitations</h2>
-
- <p>SLF4J migrator is intended as a simple tool to help you to
- migrate your project source using JCL, log4j or JUL to SLF4J. It can
- only perform elementary conversion steps. Essentially, it will
- replace appropriate import lines and logger declarations.
- </p>
-
- <p>MyClass is a sample class using JCL. Here it is before:</p>
-
- <p class="source">package some.package;
-
-<b>import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;</b>
-
-public MyClass {
-
- <b>Log logger = LogFactory.getLog(MyClass.class);</b>
-
- public void someMethod() {
- logger.info("Hello world");
- }
-}</p>
-
- <p>and after migration:</p>
-
- <p class="source">package some.package;
-
-<b>import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;</b>
-
-public MyClass {
-
- <b>Logger logger = LoggerFactory.getLogger(MyClass.class);</b>
-
- public void someMethod() {
- logger.info("Hello world");
- }
-}</p>
-
- <br/>
-
- <p>Although its conversion rules are elementary, the SLF4J migrator
- can still alleviate much of the grunt-work involved in migrating a
- Java project from JCL to SLF4J.
- </p>
-
- <p>Migration rules from log4j to SLF4J, or from JUL to SLF4J are
- similar.</p>
-
- <h3>General limitations</h3>
-
- <ul>
-
- <li>Build scripts are not modified
-
- <p>Your Ant/Maven/Ivy build scripts need to be modified manually to
- use SLF4J instead of JCL or log4j.</p>
-
- <p></p>
- </li>
-
- <li>only messages of type String are supported
-
- <p>If one of your log statements contains a non-string object as
- its sole parameter, you will have to manually add a toString()
- method call on the object.
- </p>
-
- <p>For example,</p>
- <p class="source">logger.debug(new Object()); </p>
- <p>has to be manually re-written as</p>
- <p class="source">logger.debug(new Object().toString()); </p>
-
- <p></p>
- </li>
-
- <li>the FATAL level is not supported.
-
- <p>You have to convert them manually. This limitation is not
- deemed very serious because there are usually very few log
- statements bearing the FATAL level.
- </p>
-
- <p>
- </p>
- </li>
-
- <li>if a method declares multiple loggers on the same line, the
- conversion will not be complete. Example:
-
- <p class="source"> public void someMethod(Log l1, Log l2) {
- ...
- }
-
-will be converted as
-
- public void someMethod(Log l1, Logger l2) {
- ...
- } </p>
- </li>
- </ul>
-
- <h3>Limitations when migrating from log4j</h3>
-
- <ul>
- <li>NDC statements are left as-is
-
- <p>Since NDC is not supported by SLF4J, the migrator cannot
- properly handle NDC statements. You have to migrate them to MDC
- manually. Again, this limitation is not deemed serious because
- there are usually very few NDC statements even in large projects.
- </p>
-
- <p>Please note that contrary to NDC, MDC statements are migrated
- correctly because SLF4J supports such statements.</p>
-
- <p></p>
- </li>
-
- <li>Calls to <code>PropertyConfigurator</code> or
- <code>DomConfigurator</code> cannot be migrated since they have no
- SLF4J equivalents.
-
- <p>
- </p>
-
- </li>
- </ul>
-
- <h3>Limitations when migrating from JUL</h3>
-
-
- <ul>
- <li>Calls to <code>finest()</code>, <code>finer()</code> or
- <code>finest()</code> methods of
- <code>java.util.logging.Logger</code> are left as is.
-
- <p>Given that <code>finest()</code>, <code>finer()</code> or
- <code>finest()</code> calls could map to both trace() or debug()
- calls in SLF4J, it is impossible to guess how the user wants to
- map these calls.
- </p>
-
- <p>
- </p>
-
- </li>
-
-
- <li>All strings matching ".severe(" are replaced by the string
- ".error(" without any contextual analysis. Similarly, all strings
- matching ".warning(" are replaced by ".warn(".
-
- <p>Since the match/replace operation is not contextual, if your
- code contains methods named "severe" or "warning", then the
- migration results will have compilation errors. Fortunately, such
- errors should be rare and easy to identify.
- </p>
-
- <p>
- </p>
-
- </li>
-
- <li>Invocations of the following methods defined in the
- <code>java.util.logging.Logger</code> class need to be migrated
- manually: <code>log</code>, <code>logp</code>, <code>logrb</code>,
- <code>entering</code>, <code>exiting</code>.
-
- </li>
- </ul>
-
- <script src="templates/footer.js" type="text/javascript"></script>
- </div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/news.html b/slf4j-site/src/site/pages/news.html
deleted file mode 100755
index 36d4b338..00000000
--- a/slf4j-site/src/site/pages/news.html
+++ /dev/null
@@ -1,1638 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
-
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
- <title>SLF4J News</title>
- <link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
- <link rel="stylesheet" type="text/css" href="css/prettify.css" />
- </head>
- <body onload="prettyPrint()">
- <script type="text/javascript">prefix='';</script>
- <script type="text/javascript" src="js/prettify.js"></script>
-
- <script src="templates/header.js" type="text/javascript"></script>
- <div id="left">
- <script src="templates/left.js" type="text/javascript"></script>
- </div>
- <div id="content">
-
-
- <h1>SLF4J News</h1>
-
- <p>Please note that you can receive SLF4J related announcements by
- subscribing to the <a
- href="http://www.qos.ch/mailman/listinfo/announce">QOS.ch
- announce</a> mailing list.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>March 26th, 2015 - Release of SLF4J 1.7.12</h3>
-
- <p>All java files have been reformatted to with the code formatter
- style defined in <i>codeStyle.xml</i>. This style uses 4 spaces for
- indentation and a maximum line width of 160.</p>
-
- <p>As SLF4J requires JDK 1.5 or later, the
- <code>Bundle-RequiredExecutionEnvironment</code> declaration in the
- various MANIFEST files have been updated to J2SE-1.5.
- </p>
-
- <p>Added missing Bundle-ManifestVersion attribute in the MANIFEST
- files in log4j-over-slf4j. The issue was raised in <a
- href="http://jira.qos.ch/browse/SLF4J-321">SLF4J-231</a> by Nikolas
- Falco who also provided the the appropriate pull request. </p>
-
- <p>Added <code>getAppender(String)</code> method in
- <code>Category</code> class in the log4j-over-slf4j module. This
- addition was requested by Ramon Gordillo in <a
- href="http://jira.qos.ch/browse/SLF4J-319">SLF4J-319</a>.
- </p>
-
- <p>Added <code>setThreshold</code> method in
- <code>AppenderSkeleton</code> class in the log4j-over-slf4j
- module. This addition was requested by Dimitrios Liapis who also
- provided the appropriate pull request.
- </p>
-
- <p>Added <code>getParent</code> method in <code>Category</code>
- class in the log4j-over-slf4j module. This addition was requested
- by Himanshu Bhardwaj in <a
- href="http://jira.qos.ch/browse/SLF4J-318">SLF4J-318</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>6th of January, 2015 - Release of SLF4J 1.7.10</h3>
-
- <p>The <code>MDC.putCloseable</code> method now explicitly returns
- <code>MDC.MDCloseable</code> instead of the more generic
- <code>java.io.Closeable</code>. This in turn allows one to write
- try-with-resources statement without a catch clause. Many thanks to
- William Delanoue for proposing this change.</p>
-
- <p>The various constructors in <code>FileAppender</code> in the
- log4j-over-slf4j module are now public.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>16th of December, 2014 - Release of SLF4J 1.7.9</h3>
-
- <p class="highlight"><a href="codes.html#loggerNameMismatch">Spot
- incorrectly named loggers</a> by setting the
- <code>slf4j.detectLoggerNameMismatch</code> system property to
- true.</p>
-
- <p><a href="codes.html#loggerNameMismatch">Spot incorrectly named
- loggers</a> by setting the
- <code>slf4j.detectLoggerNameMismatch</code> system property to
- true. This significant feature was contributed by Alexander
- Dorokhine.</p>
-
- <p>Added <code>MDC.putCloseable</code> method so that it can be
- used as a <a
- href="https://docs.oracle.com/javase/7/docs/technotes/guides/language/try-with-resources.html">closeable
- resource</a> under Java 7.</p>
-
- <p>Added <code>getContext</code> method returning a hashtable in
- org.apache.log4j.MDC in the log4j-over-slf4j module.
- </p>
-
- <p>The introduction of the @Nonnull JSR 305 annotation in SLF4J
- version 1.7.8 causes the Scala compiler to fail. This is issue has
- been documented in <a
- href="https://issues.scala-lang.org/browse/SI-5420">SI-5420</a>. Given
- that many Scala users will be affected by this issue for the
- foreseeable future, we have decided to renounce the user of JSR 305
- annotations in SLF4J for the time being.
- </p>
-
- <p>Numerous small code improvements too minor to be listed
- here.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>4th of April, 2014 - Release of SLF4J 1.7.7 </h3>
-
- <p>SFL4J API now uses generics. This enhancement was contributed by
- Otavio Garcia. Due to erasure of generics in Java, the changes are
- backward-compatible.</p>
-
- <p>The slf4j-migrator can now convert statements using the long deprecated
- <code>Category</code> class.</p>
-
- <p>Added the <code>SimpleLayout</code> and
- <code>FileAppender</code> classes to the log4j-over-slf4j
- module.</p>
-
-
- <h3>February 5th, 2014 - Release of SLF4J 1.7.6</h3>
-
- <p>Added slf4j-android module to the slf4j distribution. This
- module is contributed by Andrey Korzhevskiy.</p>
-
- <p>Loggers created during the initialization phase are no longer
- <code>NOPLoggers</code> which drop all logging calls. Instead,
- SLF4J now creates substitute loggers which delegate to the
- appropriate logger implementation after the initilization phase
- completes. Only calls made to these loggers during the
- initialization phase are dropped. This enhacement was proposed in
- <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=311">bug 311</a>
- by Chetan Mehrotra.
- </p>
-
- <p>Improvements to the <code>exit()</code> and
- <code>throwing()</code> methods in <code>XLogger</code>. This
- enhacement was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=197">bug 197</a>.
- </p>
-
- <p>Concunrrency improvement in <code>MessageFormatter</code>. This
- improvement was contributed by Vivek Pathak in a <a
- href="https://github.com/qos-ch/slf4j/pull/52">pull
- request</a>.</p>
-
- <p>Concunrrency improvement in
- <code>BasicMarkerFactory</code>. This improvement was contributed
- by Mikhail Mazursky in a <a
- href="https://github.com/qos-ch/slf4j/pull/40">pull
- request</a>.</p>
-
- <p><code>JCLLoggerAdapter</code> was incorrectly invoking
- <code>isDebugEnabled</code> calls in its <code>trace()</code>
- methods. This issue was reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=281">bug 281</a>.
-
- </p>
-
- <p>In the log4j-over-slf4j module, the <code>setLevel</code>
- method in the <code>Category</code> class. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=279">bug
- 279</a>. Alfredo Ramos provied the relevant patch.
- </p>
-
- <p>In the log4j-over-slf4j module, added empty implementations for
- <code>OptionHander</code>, <code>WriterAppender</code>,
- <code>ConsoleAppender</code> and <code>AppenderSkeleton</code>
- classes.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>25th of March, 2013 - Release of SLF4J 1.7.5</h3>
-
- <p class="highlight">Given the significance of these performance
- improvements, users are highly encouraged to migrate to SLF4J
- version 1.7.5 or later. </p>
-
- <p><span class="label notice">performance improvements</span> The
- logger factories in most SLF4J modules namely in jcl-over-slf4j,
- log4j-over-slf4j, slf4j-jcl, slf4j-jdk14, slf4j-log4j12, and
- slf4j-simple now use a <code>ConcurrentHashMap</code> instead of a
- regular <code>HashMap</code> to cache logger instances. This change
- significantly improves logger retrieval times at the cost of some
- memory overhead. This improvement was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=298">bug #298</a>
- by Taras Tielkes who also provided the relevant patch.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>18th of March, 2013 - Release of SLF4J 1.7.4</h3>
-
- <p>Added a package private <code>reset()</code> method to
- <code>SimpleLoggerFactory</code> for testing purposes.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>15th of March, 2013 - Release of SLF4J 1.7.3</h3>
-
- <p>The jul-to-slf4j bridge now correctly handles cases where the
- message string contains {}-placeholders but has no or zero
- parameters. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=212">bug
- #212</a>. The relevant patch was provided by Matthew Preston in a
- git pull request.</p>
-
- <p>Added missing methods and classes in log4j-over-slf4j module for
- Velocity compatibility. This issue was reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=280">bug 280</a> by
- Thomas Mortagne.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>11th of October, 2012 - Release of SLF4J 1.7.2</h3>
-
- <p>Added osgi-over-slf4j module which serves as an OSGi LogService
- implementation delegating to slf4j. This module is maintained by
- Matt Bishop and Libor Jelinek.</p>
-
- <p> Christian Trutz added missing PatternLayout class as well as
- several methods in the <code>Logger</code> and
- <code>Category</code> classes. See commit 442e90ba5785cba9 dated
- September 27th 2012 for details.
- </p>
-
- <p>Added org.slf4j.simpleLoggerwarnLevelString in slf4j-simple
- module.</p>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=272">bug
- 272</a>. All <code>Logger</code> implementations shipping with
- SLF4J use <code>Object...</code> instead of <code>Object[]</code>
- to avoid compiler warnings.</p>
-
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>14th of September, 2012 - Release of SLF4J 1.7.1</h3>
-
- <p><a
- href="apidocs/org/slf4j/impl/SimpleLogger.html"><code>SimpleLogger</code></a>
- now supports writing to a file. The property names for configuring
- <code>SimpleLogger</code> have been modified to be consistently in
- camel case. More configuration options have been added. In the
- absence of configuration directives, <code>SimpleLogger</code> will
- behave exactly the same as in the past. <b>If you are one of the
- few users configuring <code>SimpleLogger</code> with configuration
- properties, you will need to adapt to the new and more consistent
- property names.</b></p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>6th of September, 2012 - Release of SLF4J 1.7.0</h3>
-
- <p><span class="bold big green">SLF4J now requires JDK 1.5.</span></p>
-
- <p>Printing methods in the <a
- href="apidocs/org/slf4j/Logger.html">Logger</a> interface now offers
- variants accepting <a
- href="http://docs.oracle.com/javase/1.5.0/docs/guide/language/varargs.html">varargs</a>
- instead of Object[]. Given that under the hood, the Java compiler
- transforms varargs into an array, this change is totally 100%
- no-ifs-or-buts backward compatible with all existing client
- code. </p>
-
- <p>The logger field (of type <code>java.util.logging.Logger</code>)
- in <code>JDK14LoggerAdapter</code> is now marked as transient. This
- fixes <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=261">bug
- #261</a>, a serialization problem reported by Thorbj&oslash;rn Ravn
- Andersen.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>11th of June, 2012 - Release of SLF4J 1.6.6</h3>
-
- <p>Source repository has been moved to <a
- href="https://github.com/qos-ch/slf4j">https://github.com/qos-ch/slf4j</a>
- on github.</p>
-
- <p>In case multiple bindings are found on the class path, SLF4J
- will now output the name of the framework/implementation class it
- binds with.</p>
-
- <p><a
- href="apidocs/org/slf4j/impl/SimpleLogger.html">SimpleLogger</a>
- now supports configuration properties. </p>
-
- <p>LoggerWrapper in the slf4j-ext module now correctly deals with
- markers. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=265">bug #265</a>
- reported by Dario Campagna.</p>
-
- <p>The log4j-over-slf4j module now supports legacy projects
- providing their own log4j <code>LoggerFactory</code>. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=234">bug #234</a>
- reported by Laurent Pellegrino with Piotr Jagielski providing the
- appropriate patch.</p>
-
- <h3>4th of June, 2012 - Release of SLF4J 1.6.5</h3>
-
- <p>In the slf4j-log4j12 module, upgraded the log4j dependency to
- version 1.2.17.</p>
-
- <p>Added removeHandlersForRootLogger() method to <code><a
- href="apidocs/org/slf4j/bridge/SLF4JBridgeHandler.html">SLF4JBridgeHandler</a></code>
- class.</p>
-
- <p>The log4j-over-slf4j module now exports all its packages in its
- manifest. This issue was reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=262">262</a> by
- Mikhail Mazursky who also provided the relevant patch.
- </p>
-
- <h3>October 31st, 2011 - Release of SLF4J 1.6.4</h3>
-
- <p>Fixed in thread-safety issues in <code>BasicMDCAdapter</code>
- fixing <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=203">bug
- #203</a> and <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=224">bug
- #224</a>. Note that <code>BasicMDCAdapter</code> is only used with
- the slf4j-jdk14.jar binding.
- </p>
-
- <p><code>BasicMDCAdapter</code> invoked a method introduced in JDK
- 1.5 preventing it from running under JDK 1.4. Interestingly enough,
- this issue has never been reported by the user community.</p>
-
- <h3>October 17th, 2011 - Release of SLF4J 1.6.3</h3>
-
- <p><code>LogEvent</code> class in slf4j-ext module now correctly
- passes the event data as a parameter object. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=246">bug #246</a>
- reported by Ralph Goers.
- </p>
-
- <p>Added missing OSGi manifest to the jul-to-slf4j module. This
- fixes <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=166">bug
- #166</a> reported by Ekkehard Gentz. </p>
-
- <p>In the log4j-over-slf4j module, added missing
- <code>getAllAppenders</code>() method in <code>Category</code>
- class. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=235">bug #235</a>
- reported by Anthony Whitford.
- </p>
-
- <h3>August 19th, 2011 - Release of SLF4J 1.6.2</h3>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=138">bug
- #138</a>. SLF4J will no longer complain about multiple SLF4J
- bindings when running under a Weblogic server.
- </p>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=228">bug
- #228</a>. When running under IBM's JDK, and if no binding can be
- found, SLF4J will no longer throw a
- <code>NoClassDefFoundError</code>. Instead, it will default to an
- NOP implementation. Under the same circumstances but with Sun's
- JDK, SLF4J already defaulted to an NOP implementation since release
- 1.6.0.</p>
-
- <p>Added certain missing classes to the log4j-over-slf4j module as
- requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=225">bug 225</a> by
- Josh Stewart.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>July 5th, 2010 - Release of SLF4J 1.6.1</h3>
-
- <p>Updated log4j dependency to version 1.2.16 and <a
- href="http://cal10n.qos.ch/">CAL10N</a> dependency to version
- 0.7.4.
- </p>
-
- <p>Fixed missing versioning OSGi metadata in the log4j-over-slf4j
- module. This problem was reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=187">bug 187</a> by
- David Savage.
- </p>
-
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 8th, 2010 - Release of SLF4J 1.6.0</h3>
-
- <p>It is expected that <em>all</em> SLF4J releases in the 1.6.x
- series will be mutually compatible.
- </p>
-
- <p>As of SLF4J version 1.6.0, in the absence of an SLF4J binding,
- slf4j-api will default to a no-operation implementation discarding
- all log requests. Thus, instead of throwing an exception, SLF4J
- will emit a single warning message about the absence of a binding
- and proceed to discard all log requests without further
- protest. See also the <a href="manual.html#libraries">relevant
- section</a> in the user manual.
- </p>
-
- <p>In the presence of multiple parameters and if the last argument
- in a logging statement is an exception, then SLF4J will now presume
- that the user wants the last argument to be treated as an exception
- and not a simple parameter. See the relevant <a
- href="faq.html#paramException">FAQ entry</a> for further
- details. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=70">bug 70</a>
- submitted by Joern Huxhorn who also provided the relevant patch.
- </p>
-
- <p>The <code>log</code> method in <code>LocationAwareLogger</code>
- interface now admits an additional parameter of type
- <code>Object[]</code> representing additional arguments of the log
- request. Due to this modification, slf4j-api version 1.6.x will not
- work with bindings shipping with SLF4J 1.5.x -- bindings shipping
- with 1.6.x must be used.
- </p>
-
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=150">bug 150</a> by
- implementing missing <code>resetConfiguration()</code> and
- <code>shutdown()</code> methods in <code>LogManager</code> (in
- log4j-over-slf4j) as nop. In addition, the
- <code>getCurrentLoggers()</code> method has been implemented by
- returning an empty enumeration.
- </p>
-
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=170">bug 170</a> by
- a bare-bones implementation of the <code>NDC</code> class in
- log4j-over-slf4j.</p>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=175">bug 175</a> by
- synchronizing access to the loggerNameList field.</p>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=164">bug 164</a>
- observed when SLF4J artifacts were placed under
- java.endorsed.dirs.</p>
-
- <p>Fixed sub-optimal list type usage in
- <code>SLF4JLogFactory</code> as reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=179">bug 179</a> by
- Sebastian Davids.
- </p>
-
-
- <p>Fixed documentation inconsistency in <code>SLF4JLog</code> as
- reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=180">bug 180</a> by
- Sebastian Davids.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>February 25th, 2010 - Release of SLF4J 1.5.11</h3>
-
-
- <p>Users yet unfamiliar with SLF4J sometimes unknowingly place both
- <em>log4j-over-slf4j.jar</em> and <em>slf4j-log4j12.jar</em>
- simultaneously on the class path causing stack overflow
- errors. Simultaneously placing both <em>jcl-over-slf4j.jar</em> and
- <em>slf4j-jcl.jar</em> on the class path, is another occurrence of
- the same general problem. As of this version, SLF4J preempts the
- inevitable stack overflow error by throwing an exception with
- details about the actual cause of the problem. This is deemed to be
- better than leaving the user wondering about the reasons of the
- <code>StackOverflowError</code>.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=168">bug
- 168</a>. In case log4j-over-slf4j is used and a logback appender
- requires a third party library which depends on log4j, the
- <code>log(String FQCN, Priority p, Object msg, Throwable t)</code>
- method in log4j-over-slf4j's Category class would throw an
- <code>UnsupportedOperationException</code>. Problem reported by Seth
- Call.</p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>December 3rd, 2009 - Release of SLF4J 1.5.10</h3>
-
- <p>SLF4J version 1.5.10 consist of bug fixes and minor
- enhancements. It is totally backward compatible with SLF4J version
- 1.5.8. However, the slf4j-ext module ships with a new package called
- <code>org.slf4j.cal10n</code> which adds <a
- href="localization.html">localized/internationalized logging</a>
- support as a thin layer built upon the <a
- href="http://cal10n.qos.ch">CAL10N API</a>.</p>
-
- <p><a href="http://www.slf4j.org/android/">SLF4J-android</a>,
- maintained by <a
- href="http://dbis.cs.unibas.ch/team/thorsten-moller/dbis_staff_view">Thorsten
- M&ouml;ller</a>, was added as a daughter project of SLF4J.
- </p>
-
- <p>Added missing "Export-Package" declaration for cal10n in the OSGi
- manifest file for sfl4j-ext. This was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=156">bug 156</a> by
- Pete Muir.</p>
-
- <p>In log4j-over-slf4j, added missing log(...) methods as requested
- by Zoltan Szel in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=139">bug report
- 139</a>.</p>
-
- <p>In log4j-over-slf4j, added missing <code>LogManager</code> class
- as requested by Rick Beton in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=150">bug report
- 150</a>.</p>
-
- <p>In the slf4j-ext module, added
- <code>getCopyOfChildTimeInstruments</code> and
- <code>getCopyOfGlobalStopWatch</code> methods to the
- <code>Profiler</code> class. This enables developers to build their
- own output formatters for a given Profiler. This feature was
- requested by David Lindel&ouml;f in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=141">bug 141</a>.
- </p>
-
- <p>Fixed a <code>NullPointerException</code> occurring in unspecified
- conditions as described in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=146">bug report
- 146</a> by Dapeng Ni.</p>
-
- <p>Added missing OSGi manifest to the <em>log4j-over-slf4j</em>
- module as requested by Wade Poziombka in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=117">bug 117</a>.
- </p>
-
- <p>OSGi manifests produced by SLF4J now replace the '-' character by
- '.' in compliance with the OSGi specification. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=152">bug 152</a>
- according to the patch supplied by Hugues Malphettes.
- </p>
-
- <p>Fixed packaging issue in jcl104-over-slf4j which inadvertently
- produced a jar file as described in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=151">bug 151</a> by
- Jesse McConnell.</p>
-
-
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>June 11th, 2009 - Release of SLF4J 1.5.8</h3>
-
- <p>SLF4J version 1.5.8 consist of bug fixes. It is totally backward
- compatible with SLF4J version 1.5.7.</p>
-
- <p>The Maven pom file for the <code>log4j-over-slf4j</code> module
- contained a compile time dependency on the <code>slf4j-jdk14</code>
- module. The dependency should have been declared in the test
- scope. This problem was reported by Jean-Luc Geering on the slf4j
- user list.
- </p>
-
- <h3>June 10th, 2009 - Release of SLF4J 1.5.7</h3>
-
- <p>SLF4J version 1.5.7 consist of bug fixes and minor
- enhancements. It is totally backward compatible with SLF4J version
- 1.5.6.</p>
-
- <p>In SLF4J versions 1.5.5 and 1.5.6, the <code>LoggerFactory</code>
- class which is at the core of SLF4J, if a version compatibility
- issue was detected, accidentally invoked a method which was
- introduced in JDK 1.5. Thus, instead of issuing a clear warning
- message, SLF4J would throw a
- <code>NoClassDefFoundError</code>. Consequently, SLF4J would not run
- with JDK 1.4 and earlier but only if a version incompatibility issue
- was present. For example, if you were mixing
- <em>slf4j-api-1.5.6.jar</em> with <em>slf4j-simple-1.4.2.jar</em>,
- which are mutually incompatible. Please note that this bug affects
- only SLF4J versions 1.5.5 and 1.5.6 <em>and</em> only in the
- presence of incompatible versions of slf4j-api and its binding.
- </p>
-
- <p>SLF4J will now emit a warning if more than one binding is present
- on the class path. This enhancement was proposed in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=132">bug 132</a>
- contributed by by Robert Elliot.
- </p>
-
- <p>The Log interface implementations in the jcl-over-slf4j module
- will now correctly cope with serialization. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=79">bug 79</a>
- reported by Mathias Bogaert. Many thanks to Eric Vargo for precisely
- identifying the problem and supplying the corresponding patch.</p>
-
- <p>The log4j-over-slf4j module will now correctly
- interact with logging frameworks supporting location information
- such as java.util.logging and logback. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=131">bug 131</a>
- reported by Marc Zampetti.
- </p>
-
- <p><code>SLF4JBridgeHandler</code> will no longer ignore log records
- with an empty message. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=108">bug 108</a>
- reported by Pepijn Van Eeckhoudt and independently by Dan Lewis.
- </p>
-
- <p>In case the <code>toString()</code> method of a parameter throws
- an exception, <code>MessageFormatter</code> will now print an error
- message, instead of letting the exception bubble higher up as
- previously. This fixes <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=112">bug 112</a>
- submitted by Joern Huxhorn.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>November 21st, 2008 - Release of SLF4J 1.5.6</h3>
-
- <p>SLF4J version 1.5.6 consists of bug fixes. Users are encouraged
- to upgrade to SLF4J version 1.5.6. The upgrade should pose no
- problems. Nevertheless, you might still want to refer to the SLF4J
- <a href="compatibility.html">compatibility report</a>.
- </p>
-
- <p>Fixed long standing <a
- href="http://jira.qos.ch/browse/LBCLASSIC-87">LBCLASSIC-87</a> and
- its younger sibling <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=113">bug
- 113</a>. With each call to getLogger() method,
- <code>LoggerContext</code> will now retrieve the ILoggerFactory
- afresh from <code>StaticLoggerBinder</code>. This change enables
- context selectors of native implementations, e.g logback, to work
- correctly.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=114">bug
- 114</a> reported by Jason Arndt. Corrected the way
- <code>XLogger</code> (in slf4j-ext) passes its fully qualified class
- name so that the underlying logging system can correctly compute
- location information.
- </p>
-
-
- <p>The <code>install()</code> method of
- <code>SLF4JBridgeHandler</code> will no longer reset the entire
- j.u.l. environment but solely add a <code>SLF4JBridgeHandler</code>
- instance to jul's root logger. By the same token, the
- <code>uninstall()</code> method will remove previously added
- <code>SLF4JBridgeHandler</code> instances without making any other
- modifications to the j.u.l. configuration.
- </p>
-
- <p>Added <code>MDCStrLookup</code> to slf4j-ext. This class can be
- used with Apache Commons Lang's <code>StrSubstitutor</code> class to
- inject values in the SLF4J MDC into strings. Information on
- StrSubstitutor can be found at <a
- href="http://commons.apache.org/lang/api-release/org/apache/commons/lang/text/StrSubstitutor.html">StrSubstitutor
- javadoc</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>October 17th, 2008 - Release of SLF4J 1.5.5</h3>
-
- <p>The version check mechanism introduced in SLF4J 1.5.4 was
- inconsistent with the large size of SLF4J's installed user base. We
- cannot expect external SLF4J implementations to align their release
- schedule with that of SLF4J. Consequently, this SLF4J version,
- namely 1.5.5, retains versions checks but as an elective
- process. For further details see the <a
- href="faq.html#version_checks">relevant entry</a> in the FAQ.
- </p>
-
- <p>You are highly encouraged to upgrade to SLF4J version 1.5.5. The
- upgrade should pose no problems. Nevertheless, you might still want
- to refer to the SLF4J <a href="compatibility.html">compatibility
- report</a>.
- </p>
-
- <h3>October 16th, 2008 - Release of SLF4J 1.5.4</h3>
-
- <p>This version corrects critical bugs.
- </p>
-
- <p>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=106">critical bug
- 106</a>. In previous versions of SLF4J, if during the initial
- binding phase, the underlying logging system's default configuration
- created or invoked loggers, a <code>NullPointerException</code>
- would be thrown. Refer to the <a
- href="codes.html#substituteLogger">in error codes</a> document for a
- fuller explanation.</p>
-
- <p>At initialization time, LoggerFactory will now check that the
- version of the slf4j-binding matches that of slf4j-api. If there is
- a mismatch a warning will be issued on the console. This should help
- users identify SLF4J related problems more quickly.</p>
-
- <p>Improvements in documentation as well as fix for <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=102">packaging
- problems</a> related to <em>slf4j-ext</em> module.
- </p>
-
- <p>SLF4JBridgeHandler (part of jul-to-slf4j) now accounts for
- loggers with resourceBundle as well parameters. This feature
- requested by Darryl Smith in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=98">bug 98</a> and
- by Jarek Gawor in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=103">bug
- 103</a>.</p>
-
- <p>We now say that markers contain <em>references</em> to other
- markers. We no longer talk about child markers. The javadocs of the
- <code>Marker</code> interface have been updated to reflect this
- change. Moreover, the <code>hasChildren()</code> method in the
- Marker interface has been deprecated and a new method called
- <code>hasReferences()</code> was added.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>September 12th, 2008 - Release of SLF4J 1.5.3</h3>
-
- <p>See also the <a href="compatibility.html#1_5_3">compatibility
- report for this version</a>.
- </p>
-
- <p>Added a new module called slf4j-ext for slf4j-extensions. See <a
- href="extensions.html">its documentation</a> for further
- details.</p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=71">bug
- 71</a> which was re-opened by Manfred Geiler. SLF4J loggers now
- survive serialization. By survive serialization, we mean
- that the deserialized logger instance are fully functional. </p>
-
- <p>The fix for <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=68">bug 68</a> as
- implemented in version 1.5.1 was incomplete. Michael Furman supplied
- a more complete fix which was incorporated in this release.</p>
-
- <p>When slf4j bridges, e.g. jcl-over-slf4j or log4j-over-slf4j, were
- used in conjunction with JUL as the underlying logging system,
- JDK14LoggerAdapter created a LogRecord even for disabled log
- statements. This performance issue was reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=90">bug 90</a> by
- Matthew Mastracci.
- </p>
-
- <p>Added support for array values, including multi-dimensional
- arrays, as parameters. For example,</p>
- <p class="source">log.debug("{} {}", "A", new int[] {1, 2}});</p>
- <p>will print as "A [1, 2]" instead of "A [I@6ca1c" as
- previously. This enhancement was proposed by "lizongbo".
- </p>
-
- <p>Parameter substitution code has been simplified. SLF4J now only
- cares about the "{}" formatting anchor, that is the '{' character
- immediately followed by '}'. Previously, the '{' had meaning on its
- own. As a result of this change, users no longer need to escape the
- '{' unless it is immediately followed by '}'. Existing messages
- which escaped standalone '{' character will be printed with a
- preceding backslash. However, no data loss in the printed messages
- will occur.
- </p>
-
- <p>Added missing <code>getInstance</code> methods to the
- <code>Category</code> class in the log4j-over-slf4j module, fixing
- <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=95">bug 95</a>
- reported by Michael Rumpf.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>June 8th, 2008 - Release of SLF4J 1.5.2</h3>
-
- <p>Improvements to SLF4J documentation as well as fix of <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=88">packaging
- problems</a> related to <em>jul-to-slf4j.jar</em> and
- <em>jcl104-over-slf4j.jar</em>.
- </p>
-
- <h3>June 5th, 2008 - Release of SLF4J 1.5.1</h3>
-
- <p>See also the <a href="compatibility.html#1_5_1">compatibility
- report for this version</a>.</p>
-
- <p>In order to support JCL version 1.1.1, the
- <em>jcl<b>104</b>-over-slf4j</em> module was renamed as
- <em>jcl-over-slf4j</em>. SLF4J will no longer ship with
- <em>jcl104-over-slf4j.jar</em> but with <em>jcl-over-slf4j.jar</em>.
- The related work responds to enhancement request discussed in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=85">bug 85</a> as
- reported by Niklas Gustavsson.
- </p>
-
- <p>The <em>slf4j-jcl</em> binding now depends on commons-logging
- version 1.1.1 instead of the older 1.0.4</p>
-
-
- <p>Added a java.util.logging to SLF4J bridge as requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=38">bug 38</a> by
- Christian Stein, David Smiley, Johan Ferner, Joern Huxhorn and
- others.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=68">bug
- 68</a> reported by Su Chuan and David Rauschenbach. SLF4J requires
- log4j 1.2.12 or later. However, if an older version of log4j is
- present (lacking the TRACE level), in order to avoid
- NoSuchMethodError exceptions, the SLF4J's
- <code>Log4jLoggerAdapter</code> will map the TRACE level as DEBUG.
- </p>
-
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=78">bug
- 78</a> reported by Venu Thachappilly. If the argument array passed
- to a Logger printing method (debug, info, etc.) was null, a
- <code>NullPointerException</code> was thrown. With the correction,
- the messagePattern is returned as is, without parameter
- substitution.
- </p>
-
-
- <p>Added the <code>getCopyOfContextMap</code> and
- <code>setContextMap</code> methods to the <code>MDCAdapter</code>
- and <code>org.sf4j.MDC</code> classes. This was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=84">bug 84</a> by
- Anton Tagunov.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=74">bug
- 74</a>, an endless recursion problem in Marker.contains method,
- reported by Michael Newcomb. Also added he
- <code>getDetachedMarker</code> method to <code>IMarkerFactor</code>
- and <code>MarkerFactory</code> classes which was indirectly
- requested in bug 74.
- </p>
-
- <p>Added the methods <code>getLevel()</code> and
- <code>getEffectiveLevel()</code> to the <code>Category</code> class
- in log4j-over-slf4j. This addition was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=74">bug 74</a> by
- Michael Newcomb.
- </p>
-
- <p>The <a href="migrator.html">SLF4J Migrator</a>
- tool has been improved to support migration from JUL to SLF4J.
- </p>
-
- <p>In <code>MarkerIgnoringBase</code> class, corrected mapping of
- trace methods with markers to their equivalents without marker
- data. Previously, the mapping was trace to debug. The incorrect
- mapping affected only calls to the trace method with
- markers. Interestingly enough, this bug was picked up by new unit
- tests and has not been reported as a bug by our users.
- </p>
-
-
- <h3>February 26th, 2008 - Release of SLF4J 1.5.0</h3>
-
-
- <p>A tool called <a href="migrator.html">SLF4J Migrator</a> now
- ships with SLF4J. It can help you migrate your project using JCL or
- log4j to use SLF4J instead.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=61">bug
- 61</a> reported by Christopher Sahnwaldt. It is now possible to
- place a backslash in front of a formatting anchor, by escaping the
- backslash. For example, the call to
- <code>MessageFormatter.format("C:\\\\{}", "foo")</code> will now
- correctly return "C:\\foo". The backslash character needs to be
- escaped in Java, which leads to four backslashes.
- </p>
-
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=63">bug
- 63</a> reported by Maarten Bosteels. SLF4J now supports MDC for
- <code>java.util.logging</code> package.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=64">bug
- 64</a> reported by Michal Bernhard. The log4j binding will now alert
- the user if she uses SLF4J with a version of log4j earlier than 1.2.12.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=65">bug
- 65</a> reported by Ben Gidley. Superfluous
- &lt;version>$&#x7B;parent.version}&lt;/version> lines have been
- removed from pom.xml files. These lines reportedly confuse certain
- Maven repositories.
- </p>
-
- <p>In the <code>org.apache.log4j.Category</code> class, as
- implemented in the log4j-over-slf4j module, calls to the printing
- trace() are now correctly mapped to SLF4J's trace() printing method
- (instead of debug()). Superfluous printing methods with the
- signature <code>xxxx(Object, Object)</code> and <code>xxxx(String,
- Object, Object)</code> have been removed.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=67">bug
- 67</a> reported by Chris Custine. The manifest file for
- jcl104-over-slf4j now correctly declares version 1.0.4 for the
- exported JCL packages.
- </p>
-
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=69">bug
- 69</a> reported by Joern Huxhorn, who graciously supplied the fix as
- well as a test case. The <code>add</code> method in
- <code>BasicMarker</code> class now correctly prevents multiple
- addition of the same child. Moreover, the <code>remove</code> method
- now correctly removes the specified child marker.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=41">bug
- 41</a> reported by Sebastian Davids. The manifest files of various
- projects now mention J2SE-1.3 as the required execution
- environment.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=71">bug
- 71</a> reported by Manfred Geiler. The SLF4JLog and
- SLF4JLocationAwareLog classes are now serializable solving
- serialization problems encountered with certain libraries which
- attempt to serialize JCL log instances.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=73">bug
- 73</a> reported by Oleg Smirsky. A "Fragment-Host: slf4j.api" line
- has been added to every MANIFEST.MF file exporting
- <code>org.slf4j.impl</code>.
- </p>
-
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=72">bug
- 72</a> reported by Ian Carr. Performance issues with slf4j-jdk14 for
- disabled log statements have now been corrected.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>August 20th, 2007 - Release of SLF4J 1.4.3</h3>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=60">bug
- 60</a> as reported by Costin Leau. OSGI manifest entries now declare
- the correct SLF4J version.
- </p>
-
- <p>Clarified the behavior of the various methods methods in the MDC
- class with respect to "null" parameters. This was requested in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=58">bug 58</a> by
- Sebastian Davids.
- </p>
-
- <p>Removed the slf4j-archetype module because nobody seems to have a
- use for it.</p>
-
- <h3>July 12th, 2007 - Release of SLF4J 1.4.2</h3>
-
- <p>The <a href="log4j-over-slf4j.html">log4j-over-slf4j</a> module
- has been moved back into SLF4J. Originally, this module was part of
- SLF4J and was moved into logback due to the lack of MDC support in
- SLF4J. With version 1.4.2 and the addition of MDC support in SLF4J
- 1.4.1, log4j-over-slf4j returns to its original home. Note that the
- previous name of the module was <a
- href="http://logback.qos.ch/bridge.html">log4j-bridge</a>.
- </p>
-
- <p>Addition of the <code>getMDCAdapter</code> method to
- org.slf4j.MDC class. This allows access to the actual MDC
- implementation which can on occasion come in very handy.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
-
-
- <h3>July 4th, 2007 - Release of SLF4J 1.4.1</h3>
-
-
- <p>SLF4J now supports <a href="manual.html#mdc">Mapped Diagnostic
- Contexts</a> (MDC) as requested by Andy Gerweck and Steve Ebersole
- in <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=49">bug
- 49</a>.
- </p>
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=53">bug
- 53</a> as reported by Heinrich Nirschl. The public method
- <code>trace(String)</code> in the <code>Log4jLoggerAdapter</code>
- class incorrectly called the underlying log4j logger with level DEBUG
- instead of TRACE.
- </p>
-
- <p>Fixed various documentation related errors kindly reported by
- Mark Vedder.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
-
- <h3>May 16th, 2007 - Release of SLF4J 1.4.0</h3>
-
-
- <p>In response to many user requests over time, the TRACE level has
- been added to <a
- href="api/org/slf4j/Logger.html">org.slf4j.Logger</a>
- interface. Please also see the <a href="faq.html#trace">FAQ entry
- discussing</a> the TRACE level.
- </p>
-
-
- <p>Fixed <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=47">bug
- 47</a> as reported by Terry Todd. In previous a SLF4J release the
- <code>org.apache.commons.logging.impl.SLF4FLogFactory</code> class
- was renamed as <code>SLF4JLogFactory</code>. The
- <em>META-INF/services/org.apache.commons.logging.LogFactory</em>
- resource file had not reflected this change. It does now.
- </p>
-
-
- <p>Eric Yung <a
- href="http://www.slf4j.org/pipermail/user/2007-April/000327.html">reported</a>
- that Apache commons-configuration access certain commons-logging
- classes, namely <code>org.apache.commons.logging.impl.NoOpLog</code>
- and SimpleLog, directly. Following Eric's suggestion,
- jcl104-over-slf4j now includes the aforementioned classes.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>April 15th, 2007 - Release of SLF4J 1.3.1</h3>
-
-
- <p>In response to a <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=39">enhancement
- request</a> made by Michael Newcomb, a marker can now be detached
- from the internal list of the <code>MarkerFactory</code> that
- generated it.
- </p>
-
- <p>Fixed a silly but nonetheless annoying bug where log request of
- level ERROR made through jcl104-over-slf4j would log twice. This bug
- was <a
- href="http://www.slf4j.org/pipermail/user/2007-April/000323.html">reported</a>
- and precisely described by Andrew Cooke.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>February 25th, 2007 - Release of SLF4J 1.3.0</h3>
-
- <p>This release consists of rearrangement of classes among
- projects. More specifically, the
- <code>org.slf4j.LoggerFactory</code> class is now packaged within
- the <em>slf4j-api.jar</em> file instead of the various slf4j
- bindings. <b>It follows that client code needs to depend on only
- slf4j-api in order to compile, while the various slf4j bindings are
- only needed as runtime dependencies.</b> See also the <a
- href="faq.html#maven2">Maven2-related FAQ entry</a>. Given the
- practical significance of this change, we highly recommend that
- library-authors upgrade to version 1.3 at their earliest
- convenience.
- </p>
-
- <p><a href="http://bugzilla.slf4j.org/show_bug.cgi?id=23">Bug number
- 23</a> has been fixed, at the cost of minor and backward compatible
- changes. In other words, jcl104-over-slf4j now preserves caller
- location information.
- </p>
-
- <p>It is now possible to obtain the root logger of the underlying
- logging implementation by requesting a logger named
- &quot;ROOT&quot;. This feature was requested by Sebastien Davids
- in <a href="http://bugzilla.slf4j.org/show_bug.cgi?id=35">bug
- report 35</a>. </p>
-
- <p>For an exact list of changes please refer to the <a
- href="changes/changes-1.3.txt">1.3.0 compatibility report</a> file
- as generated by clirr.</p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>January 24th, 2007 - Release of SLF4J 1.2</h3>
- <p>This release includes several modifications to make SLF4J
- an <a href="http://www.osgi.org/">OSGi</a>-friendly framework.
- The modules' MANIFEST.MF files now include
- OSGi metadata. Regarding these improvements, and OSGi in general, the
- SLF4J project is happy to welcome John E. Conlon as a new committer.
- </p>
-
- <p>Marker objects are now Serializable.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>December 21st, 2006 - Release of SLF4J 1.1.0 (final)</h3>
-
- <p>This release consists of minor bug fixes and documentation
- changes. More importantly, the log4j-over-slf4j module has been
- moved to the logback project, under the name <a
- href="http://logback.qos.ch/bridge.html">log4j-bridge</a>.
- </p>
-
- <p>Added the file "org.apache.commons.logging.LogFactory" under
- META-INF/services directory which went missing in the 1.1.0 series
- of SLF4J. This fixes a compatibility problem with Apache Axis which
- uses its own discovery mechanism, namely, commons-discovery version
- 0.2. The problem was reported in bug <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=33">report 33</a>
- by David Varnes.
- </p>
-
- <p>The file jcl104-over-slf4j.jar had various entries missing in its
- MANIFEST.MF file, as reported by Boris Unkel in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=30">bug number
- 30</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>November 16th, 2006 - Release of SLF4J 1.1.0-RC1</h3>
-
- <p>This release consists of packaging related bug fix in addition to
- minor documentation changes.
- </p>
-
- <p>Contrary to RC0, RC1 no longer uses SNAPSHOT versions for the
- slf4j-parent pom. The solution to <a
- href="http://ceki.blogspot.com/2006/11/solution-to-maven2-version-number.html">Maven
- version problem</a> does not work for public projects such as SLF4J
- because SNAPSHOTs are not allowed on ibiblio.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>November 4th, 2006 - Release of SLF4J 1.1.0-RC0</h3>
-
- <p>This release consists of bug fixes. Moreover, since the major
- packaging related changes in 1.1.0-beta0 seem to work well, this
- release is marked as RC0.</p>
-
- <p>Fixed the JDK 1.5 dependency for the SLF4J build, as reported by
- Boris Unkel in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=28">bug number
- 28</a>. SLF4J now explicitly declares a dependency on JDK 1.4 in its
- pom.xml file.
- </p>
-
- <p>Fixed an incorrect reference to the logback project in slf4j-api
- pom file. This bug was reported by Boris Unkel in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=29">bug number
- 29</a>.
- </p>
-
- <p>Fixed a synchronization problem in factories of almost all SLF4J
- bindings. This bug was reported independently by Howard M. Lewis Ship
- and Boris Unkel in bug reports <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=26">26</a> and
- respectively <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=26">27</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>September 7th, 2006 - Release of SLF4J 1.1.0-beta0</h3>
-
- <p>Release 1.1.0-beta0 is a relatively important release with a
- refactoring of the way class files are organized in jar files. In
- previous releases, each binding was self-contained in a single jar
- file. In this release, each and every binding depends on
- <em>slf4j-api.jar</em> which contains the bulk of the classes
- required to use SLF4J, except for one or two adapter classes. Only
- the adapter classes are now shipped with each specific binding jar
- as appropriate for the underlying logging system..
- </p>
-
- <p>This release is built using Maven instead of Ant. As for the java
- code, it has not been changed.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>June 8th, 2006 - Release of SLF4J 1.0.2</h3>
-
- <p>Release 1.0.2 is a maintenance release containing bug fixes
- only.</p>
-
- <ul>
-
- <li>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=22">bug number
- 22</a> reported by Bjorn Danielsson. This version of the SLF4J API
- will no longer systematically throw an exception when the
- <code>o.a.c.l.impl.SLF4FLogFactory#release()</code> method is
- invoked. Instead, the <code>release()</code> method will issue a
- <a href="http://www.slf4j.org/codes.html">warning</a>.
-
- </li>
-
- </ul>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 1st, 2006 - Release of SLF4J 1.0.1</h3>
-
- <p>Release 1.0.1 is a maintenance release containing bug fixes
- only.</p>
-
- <ul>
-
- <li>Fixed <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=20">bug number
- 20</a> reported by Steve Bate. <code>JDK14LoggerAdapter</code>
- will now correctly relay the logger name to the underlying JDK 14
- logging system.
- </li>
-
- <li>Added the file "org.apache.commons.logging.LogFactory" under
- META-INF/services directory in the jcl104-over-slf4j jar
- file. This fixes a compatibility problem with Apache Axis which
- uses its own discovery mechanism, namely, commons-discovery
- version 0.2. The bug was reported by Dave Wallace.
- </li>
-
- </ul>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>March 8th, 2006 - Release of SLF4J 1.0</h3>
-
- <p>This is release labeled as 1.0 (final) contains few relatively
- minor changes:
- </p>
-
- <ul>
- <li>As <a
- href="http://marc.theaimsgroup.com/?t=114063163800004">discussed</a>
- on the slf4j user list, <code>SimpleLogger</code> now directs its
- output to stderr instead of stdout.
- </li>
-
- <li>Modified <code>JDK14LoggerAdapter</code> so that caller
- information is now correctly printed, as reported in <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=13">bug 13</a> by
- Peter Royal.
- </li>
-
- <li>Minor additions to the Marker interface.</li>
-
- </ul>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>February 4th, 2006 - Release of SLF4J 1.0-RC6 and NLOG4J
- 1.2.22</h3>
-
- <p>The <code>MarkingLogger</code> interface has been removed and its
- contents merged into <code>org.slf4j.Logger</code>. This change
- should not adversely affect end-users. However, SLF4J bindings need
- to be updated. This has been done for all the bindings shipped with
- SLF4J distribution as well as NLOG4J. As for x4juli, the update is
- planned for its next release.
- </p>
-
- <p>The merge between the <code>MarkingLogger</code> and
- <code>Logger</code> interfaces has been motivated by the need to
- allow end-users to easily switch between logging systems that
- support markers and those that do not.
- </p>
-
- <p>Added a default instance to SimpleLoggerFactory to serve as a
- last resort fallback mechanism. This instance is designed to be used
- by a very specific group of users, namely for those developing
- logging systems (e.g. log4j or LOGBack). It is not intended for
- end-users of the SLF4J API.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>January 9th, 2006 - Release of SLF4J 1.0-RC5 and NLOG4J
- 1.2.21</h3>
-
- <p>A maintenance release correcting bugs <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=11">#11</a> and <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=12">#12</a> and in
- general improved resilience to null input parameters across
- implementations. Many thanks to Boris Unckel and Kenneth for
- reporting the null input issue.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>December 27th, 2005 - Release of SLF4J 1.0-RC4 and NLOG4J
- 1.2.20</h3>
-
-
- <p>The printing methods in <code>org.slf4j.Logger</code> interface
- now support passing 3 or more parameters in an <code>Object</code>
- array. This was a frequently requested feature missing in previous
- versions of SLF4J.
- </p>
-
- <p>NLOG4J 1.2.20 reflects the addition of new methods in the
- <code>org.slf4j.Logger</code> interface.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>December 8th, 2005 - Release of SLF4J 1.0-RC3</h3>
-
- <p>Maintenance release fixing reported bugs <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=6">#6</a> and <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=7">#7</a>.
- </p>
-
-
- <h3>November 28th, 2005 - Release of SLF4J 1.0-RC2</h3>
-
- <p>In response to a request by Greg Wilkins, this release adds the
- jar file <em>slf4j-jcl.jar</em>, an SLF4J binding for JCL. Please
- read the <a href="manual.html#gradual">gradual migration section</a>
- in the manual for more details.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>November 21st, 2005 - Release of SLF4J 1.0-RC1</h3>
-
- <p>A maintenance release correcting bugs <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=4">#4</a> and <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=5">#5</a>. Many
- thanks to Christian Beil for accurately reporting bug #4.
- </p>
-
- <p>There has been also an effort to minimize the file sizes of the
- various jar files produced by SLF4J, resulting in jar files
- approximately 40% smaller than in version 1.0beta9.
- </p>
-
- <p>Given that the SLF4J API is now deemed stable, this release is
- marked as RC1, that is release candidate number 1.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>October 19th, 2005 - Release of SLF4J 1.0-beta9</h3>
-
- <p>The SLF4J distribution now includes two distinct bindings
- <em>slf4j-log4j12.jar</em> and <em>slf4j-log4j13.jar</em> in order
- to differentiate between log4j version 1.2 and version 1.3. This
- distinction is absolutely necessary because log4j 1.2 and 1.3 are
- not run-time compatible, although they are mostly compile-time
- compatible.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>October 19th, 2005 - Release of SLF4J 1.0-beta8 and NLOG4J 1.2.18</h3>
-
-
- <p>Added a new SLF4J binding, <em>slf4j-log4j.jar</em>, intended to
- be used in conjunction with vanilla <em>log4j.jar</em>, as
- distributed by the <a href="http://logging.apache.org">Apache
- Logging Services</a> project. The slf4j-log4j binding is quite
- similar in structure to the JDK 1.4 binding that existed
- previously.
- </p>
-
- <p>The slf4j-log4j binding addresses compatibility problems which
- arose when copies of both <em>log4j.jar</em> and <em>nlog4j.jar</em>
- lay on the class path, in particular when it was undesirable or
- impossible to remove the preexisting <em>log4j.jar</em> file.
- </p>
-
- <p>Methods in the <code>org.slf4j.Logger</code> interface related to
- markers were moved to a separate super interface called <a
- href="api/org/slf4j/MarkingLogger.html">
- <code>org.slf4j.MarkingLogger</code></a>. This refactoring reduces
- the weight of the <a href="api/org/slf4j/Logger.html">
- <code>Logger</code></a> interface.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>August 28th, 2005 - Release of SLF4J 1.0-beta7 and NLOG4J 1.2.17</h3>
-
- <p>Spurred by <a
- href="http://bugzilla.slf4j.org/show_bug.cgi?id=3">bug report
- #3</a>, SLF4J binding code has been refactored and
- simplified. Logging systems implementing SLF4J interfaces have to
- have less work in order to bind with SLF4J. Moreover, these changes
- have no incidence on the published interface of SLF4J.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>August 26th, 2005 - Release of SLF4J 1.0-beta6</h3>
-
- <p>To ease migration to SLF4J from JCL, this release includes a jar
- file called <em>jcl-over-slf4j-1.0.4.jar</em>. This jar file can be
- used as drop-in replacement for JCL version 1.0.4. It implements the
- public API of JCL using SLF4J underneath.
- </p>
-
- <p>Thus, you can immediately benefit from the advantages of SLF4J
- without waiting for all the libraries you depend on to migrate to
- SLF4J first.</p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>August 16th, 2005 - Release of NLOG4J 1.2.16</h3>
-
- <p>This release adds solves a compatibility problem between log4j
- and nlog4j. Previous to this release, code compiled with log4j
- would not run correctly with nlog4j.
- </p>
-
- <p>With the fixes introduced in NLOG4J 1.2.16, code compiled with
- log4j 1.2.x will run without problems when deployed using NLOG4j.
- </p>
-
- <p>However, the inverse is not true. Code compiled with nlog4j can
- only be deployed using nlog4j.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>August 12th, 2005 - Release of SLF4J 1.0-beta5 and NLOG4J
- 1.2.15</h3>
-
- <p>This release adds support for the <a
- href="api/org/slf4j/Marker.html">Marker</a> interface. Thus, log
- statements can be decorated with Marker data allowing more
- expressive power in the processing of log statements.
- </p>
-
- <p>For the sake of IoC frameworks, <code>Logger</code> instances can
- new be queried for their <a
- href="api/org/slf4j/Logger.html#getName()">name</a>.
- </p>
-
- <p>With the addition of markers, sub-domains are no longer
- needed.</p>
-
- <p>The <code>LoggerFactoryAdapter</code> has been simplified and
- renamed as <a
- href="api/org/slf4j/ILoggerFactory.html"><code>ILoggerFactory</code></a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>July 5th, 2005 - Release of NLOG4J 1.2.14</h3>
-
- <p>This release fixes compatibility problems between NLOG4J and
- Jakarta Commons Logging.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>June 28th, 2005 - Release of SLF4J 1.0-beta4 and NLOG4J
- 1.2.13</h3>
-
- <p>Following discussions on the SLF4J developers list, the
- signatures of the printing methods in <a
- href="api/org/slf4j/Logger.html"><code>org.slf4j.Logger</code></a>
- interface have been modified to admit messages of type
- <code>String</code> instead of type <code>Object</code> as
- previously. The current set of printing methods is listed below.
- </p>
-
- <pre class="source">
- void debug(String msg);
- void debug(String format, Object arg);
- void debug(String format, Object arg1, Object arg2);
- void debug(String msg, Throwable t);
-
- void error(String msg);
- void error(String format, Object arg;)
- void error(String format, Object arg1, Object arg2);
- void error(String msg, Throwable t);
-
- void info(String msg);
- void info(String format, Object arg);
- void info(String format, Object arg1, Object arg2);
- void info(String msg, Throwable t);
-
- void warn(String msg);
- void warn(String format, Object arg);
- void warn(String format, Object arg1, Object arg2);
- void warn(String msg, Throwable t); </pre>
-
-
- <p>NLOG4J release 1.2.13 reflects changes in the SLF4J API.
- </p>
-
- <p>You can download SLF4J and NLOG4J, including full source code,
- class files and documentation on our <a
- href="download.html">download page</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 17th, 2005 - SLF4J version 1.0-beta-3 released</h3>
-
- <p>In response to user comments, the <code>org.slf4j.ULogger</code>
- interface has been renamed as <code>org.slf4j.Logger</code>.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 17th, 2005 - NLOG4J version 1.2.12 released</h3>
-
- <p>SLF4J.ORG is proud to release NLOG4J 1.2.12, a log4j-replacement
- with native SLF4J API support. Except for users of LF5, chainsaw or
- <code>NTEvenAppender</code>, NLOG4J should be considered as a 100%
- compatible, drop-in replacement for log4j version 1.2.9.
- </p>
-
- <p>This release reflects changes in the SLF4J API, i.e renaming of
- <code>org.slf4j.ULogger</code> interface as
- <code>org.slf4j.Logger</code>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 17th, 2005 - SLF4J version 1.0-beta-3 released</h3>
-
- <p>SLF4J.ORG is proud to release SLF4J 1.0-beta-3. In response to
- user comments, the <code>org.slf4j.ULogger</code> interface has been
- renamed as <code>org.slf4j.Logger</code>.
- </p>
-
- <p>You can download SLF4J, including full source code, class files
- and documentation on our <a href="download.html">download page</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 14th, 2005 - NLOG4J version 1.2.11 released</h3>
-
- <p>SLF4J.ORG is proud to release NLOG4J 1.2.11, a log4j-replacement
- with native SLF4J API support. Except for users of LF5, chainsaw or
- <code>NTEvenAppender</code>, NLOG4J should be considered as a 100%
- compatible, drop-in replacement for log4j version 1.2.9.
- </p>
-
- <p>You can download NLOG4J version 1.2.11, including full source
- code, class files and documentation on our <a
- href="download.html">download page</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>May 4th, 2005 - SLF4J version 1.0-beta-2 released</h3>
-
- <p>SLF4J.ORG is proud to release SLF4J 1.0-beta-2. This release
- contains cosmetic or javadoc changes. For example, the project has a
- new logo.
- </p>
-
- <p>You can download SLF4J version 1.0-beta2, including full source
- code, class files and documentation on our <a
- href="download.html">download page</a>.
- </p>
-
-
- <hr noshade="noshade" size="1"/>
-
- <h3>1 May 2005 - not-log4j-1.2.10 released</h3>
-
- <p>Subsequent to the recall of log4j 1.2.10, SLF4J.ORG releases
- non-log4j-1.2.10 for those interested in SLF4J support in log4j.
- </p>
-
- <p>You can download not-log4j version 1.2.10, including full source
- code, class files and documentation on our <a
- href="download.html">download page</a>.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
-
- <h3>22 April 2005 - SLF4J project goes live</h3>
-
- <p>The SLF4J project site, including SVN repositories go
- live. Users can download SLF4J version 1.0-beta1.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>15 April 2005 - start of work on SLF4J source code</h3>
-
- <p>Start of work on the SLF4j source code.
- </p>
-
- <hr noshade="noshade" size="1"/>
-
- <h3>13 April 2005 - start of work on SLF4J project</h3>
-
- <p>Launch of the SLF4J project. Work has begun on the web-site, svn
- repositories as well as the source code.
- </p>
-
-
- <script src="templates/footer.js" type="text/javascript"></script>
-
-</div>
-</body>
-</html>
diff --git a/slf4j-site/src/site/pages/support.html b/slf4j-site/src/site/pages/support.html
deleted file mode 100644
index 010a56b0..00000000
--- a/slf4j-site/src/site/pages/support.html
+++ /dev/null
@@ -1,43 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/2000/REC-xhtml1-20000126/DTD/xhtml1-transitional.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
-<head>
-<meta http-equiv="content-type" content="text/html; charset=iso-8859-1" />
-<title>Log4j Bridge</title>
-<link rel="stylesheet" type="text/css" media="screen" href="css/site.css" />
-<link rel="stylesheet" type="text/css" media="print" href="css/print.css" />
-
-</head>
-<body>
- <script>
-prefix='';
-</script>
-
-<script src="templates/header.js"></script>
-<div id="left">
- <script src="templates/left.js"></script>
-</div>
-<div id="right">
- <script src="templates/right.js"></script>
-</div>
-<div id="content">
-
- <h2>Contractual Support</h2>
-
-
- <p>The following companies, listed in alphabetical order, offer
- contractual support for SLF4J.
- </p>
-
- <ul>
- <li>QOS.ch, in Lausanne, Swizerland. For more information visit
- QOS.ch's <a href="">support page</a>. </li>
- </ul>
-
-
-
-<script src="templates/footer.js"></script>
-</div>
-</body>
-</html>
-
-
diff --git a/slf4j-site/src/site/pages/templates/footer.js b/slf4j-site/src/site/pages/templates/footer.js
deleted file mode 100755
index b7d01cf9..00000000
--- a/slf4j-site/src/site/pages/templates/footer.js
+++ /dev/null
@@ -1,28 +0,0 @@
-
-document.write('<table class="footer" border="0">')
-
-document.write('<tr>')
-
-document.write(' <td valign="top" align="left">Copyright &copy; 2004-2015 <a href="http://www.qos.ch/">QOS.ch</a></td>')
-
-//document.write(' <td rowspan="2">');
-//document.write(' <a href="http://twitter.com/qos_ch">');
-//document.write(' <img alt="Follow @qos_ch" src="images/follow_us.png" />');
-//document.write(' </a>');
-//document.write(' </td>');
-
-
-document.write('</tr>')
-
-AAT = '@'
-DOOTT = '.'
-document.write('<tr>')
-document.write('<td align="left" colspan="1">')
-document.write('We are actively looking for volunteers to proofread the documentation. Please send your corrections or suggestions for improvement to "corrections' + AAT +'qos'+DOOTT+'ch". See also the <a href="http://articles.qos.ch/contributing.html">instructions for contributors</a>.');
-document.write('</td>')
-document.write('</tr>')
-
-
-document.write('</table>')
-
-
diff --git a/slf4j-site/src/site/pages/templates/header.js b/slf4j-site/src/site/pages/templates/header.js
deleted file mode 100644
index 35f75bc9..00000000
--- a/slf4j-site/src/site/pages/templates/header.js
+++ /dev/null
@@ -1,12 +0,0 @@
-
-document.write('<table width="100%" border="0"><tr>');
-document.write('<td><a href="http://www.slf4j.org/">');
-document.write('<img src="' + prefix + 'images/logos/slf4j-logo.jpg" alt="" border="0"/>');
-document.write('</a></td>')
-
-//document.write('<td align="right"><a id="job" href="http://logback.qos.ch/job.html">');
-//document.write('<img src="' + prefix + 'images/myjob.png" alt="" border="0"/>');
-//document.write('</a></td>')
-
-document.write('</tr></table>');
-document.write('<div id="breadcrumbs"></div>'); \ No newline at end of file
diff --git a/slf4j-site/src/site/pages/templates/left.js b/slf4j-site/src/site/pages/templates/left.js
deleted file mode 100755
index 3fc7824b..00000000
--- a/slf4j-site/src/site/pages/templates/left.js
+++ /dev/null
@@ -1,59 +0,0 @@
-document.write('<div class="menuGroup">');
-document.write(' <p class="menu_header">SLF4J Project</p>');
-document.write(' <a href="index.html">Introduction</a>');
-document.write(' <a href="download.html">Download</a>');
-document.write(' <a href="docs.html">Documentation</a>');
-document.write(' <a href="license.html">License</a>');
-document.write(' <a href="news.html">News</a>');
-
-document.write(' <p class="menu_header">Support</p>');
-
-document.write(' <a href="mailing-lists.html">Mailing Lists</a>');
-document.write(' <a href="bug-reporting.html">Bug Reporting</a>');
-document.write(' <a href="https://github.com/qos-ch/slf4j">Source Repository</a>');
-document.write(' <a href="http://www.qos.ch/shop/products/professionalSupport">Support offerings</a>');
-document.write(' <a href="http://www.qos.ch/shop/products/training">Training</a>');
-
-document.write(' <p class="menu_header">Native implementations</p>');
-document.write(' <a href="http://logback.qos.ch/">Logback</a>');
-
-document.write(' <p class="menu_header">Wrapped implementations</p>');
-document.write(' <a href="http://bmc.github.com/avsl/">AVSL</a>');
-document.write(' <a href="api/org/slf4j/impl/JDK14LoggerAdapter.html">JDK14</a>');
-document.write(' <a href="api/org/slf4j/impl/Log4jLoggerAdapter.html">Log4j</a>');
-document.write(' <a href="api/org/slf4j/impl/SimpleLogger.html">Simple</a>');
-document.write(' <a href="android/">Android</a>');
-document.write(' </p>');
-
-document.write(' <p class="menu_header">Sub-projects</p>');
-document.write(' <a href="http://www.slf4j.org/taglib/">slf4j-taglib</a>');
-document.write(' </p>');
-
-document.write('</div>');
-
-
-document.write('<p>&nbsp;</p>');
-
-document.write('<div class="pub">');
-document.write(' <a href="http://twitter.com/qos_ch" style="">');
-document.write(' <img alt="Follow @qos_ch" src="images/follow_us.png" />');
-document.write(' </a>');
-document.write('</div>');
-
-document.write('<p>&nbsp;</p>');
-document.write('<div class="pub"><img src="https://travis-ci.org/qos-ch/slf4j.svg?branch=master"/></div>');
-
-
-//document.write('<p>&nbsp;</p>');
-//document.write('<div class="jobadd"><p><a href="http://logback.qos.ch/job.html">Your career<br/>@QOS.ch</a></p></div>');
-
-
-//document.write('<p>&nbsp;</p>');
-//document.write('<p class="pub">');
-//document.write(' <a href="https://www.qos.ch/shop/products/log4jManual">');
-//document.write(' <img src="images/buyDirect.jpg" border="0" title="" alt="buy direct from the developer"/>');
-//document.write(' </a>');
-//document.write('</p>');
-
-
-
diff --git a/slf4j-site/src/site/pages/templates/right.js b/slf4j-site/src/site/pages/templates/right.js
deleted file mode 100644
index 8b137891..00000000
--- a/slf4j-site/src/site/pages/templates/right.js
+++ /dev/null
@@ -1 +0,0 @@
-
diff --git a/slf4j-site/src/site/resources/css/anchor12.png b/slf4j-site/src/site/resources/css/anchor12.png
deleted file mode 100644
index 2cd97acb..00000000
--- a/slf4j-site/src/site/resources/css/anchor12.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/css/anchor16.png b/slf4j-site/src/site/resources/css/anchor16.png
deleted file mode 100644
index c0676f49..00000000
--- a/slf4j-site/src/site/resources/css/anchor16.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/css/anchor20.png b/slf4j-site/src/site/resources/css/anchor20.png
deleted file mode 100644
index 76ca74bb..00000000
--- a/slf4j-site/src/site/resources/css/anchor20.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/css/anchor24.png b/slf4j-site/src/site/resources/css/anchor24.png
deleted file mode 100644
index 13c433fa..00000000
--- a/slf4j-site/src/site/resources/css/anchor24.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/PythonPowered.png b/slf4j-site/src/site/resources/images/PythonPowered.png
deleted file mode 100644
index 2e9d99c2..00000000
--- a/slf4j-site/src/site/resources/images/PythonPowered.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/beginnerSLF4J.png b/slf4j-site/src/site/resources/images/beginnerSLF4J.png
deleted file mode 100644
index c156a18f..00000000
--- a/slf4j-site/src/site/resources/images/beginnerSLF4J.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/bindings.png b/slf4j-site/src/site/resources/images/bindings.png
deleted file mode 100644
index 4021c095..00000000
--- a/slf4j-site/src/site/resources/images/bindings.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/bridging.png b/slf4j-site/src/site/resources/images/bridging.png
deleted file mode 100644
index b61c0a7b..00000000
--- a/slf4j-site/src/site/resources/images/bridging.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/buyDirect.jpg b/slf4j-site/src/site/resources/images/buyDirect.jpg
deleted file mode 100644
index dd2ff4c8..00000000
--- a/slf4j-site/src/site/resources/images/buyDirect.jpg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/concrete-bindings.png b/slf4j-site/src/site/resources/images/concrete-bindings.png
deleted file mode 100644
index 9c7d1b16..00000000
--- a/slf4j-site/src/site/resources/images/concrete-bindings.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/devoxx09.jpeg b/slf4j-site/src/site/resources/images/devoxx09.jpeg
deleted file mode 100644
index f6f38ebb..00000000
--- a/slf4j-site/src/site/resources/images/devoxx09.jpeg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/follow_us.png b/slf4j-site/src/site/resources/images/follow_us.png
deleted file mode 100644
index fe3a3888..00000000
--- a/slf4j-site/src/site/resources/images/follow_us.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/gnu-head-tiny.jpg b/slf4j-site/src/site/resources/images/gnu-head-tiny.jpg
deleted file mode 100644
index 441be50d..00000000
--- a/slf4j-site/src/site/resources/images/gnu-head-tiny.jpg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/jazoon09.gif b/slf4j-site/src/site/resources/images/jazoon09.gif
deleted file mode 100644
index f386387c..00000000
--- a/slf4j-site/src/site/resources/images/jazoon09.gif
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/legacy.png b/slf4j-site/src/site/resources/images/legacy.png
deleted file mode 100644
index 46d1f6da..00000000
--- a/slf4j-site/src/site/resources/images/legacy.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/logos/qosLogo.png b/slf4j-site/src/site/resources/images/logos/qosLogo.png
deleted file mode 100644
index 52b216e9..00000000
--- a/slf4j-site/src/site/resources/images/logos/qosLogo.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/logos/qoslogo.gif b/slf4j-site/src/site/resources/images/logos/qoslogo.gif
deleted file mode 100644
index d06ec29b..00000000
--- a/slf4j-site/src/site/resources/images/logos/qoslogo.gif
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/logos/slf4j-logo.jpg b/slf4j-site/src/site/resources/images/logos/slf4j-logo.jpg
deleted file mode 100644
index 62295c91..00000000
--- a/slf4j-site/src/site/resources/images/logos/slf4j-logo.jpg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/logos/slf4j-small.jpg b/slf4j-site/src/site/resources/images/logos/slf4j-small.jpg
deleted file mode 100644
index a26ab0c2..00000000
--- a/slf4j-site/src/site/resources/images/logos/slf4j-small.jpg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/logos/valid-html401.png b/slf4j-site/src/site/resources/images/logos/valid-html401.png
deleted file mode 100644
index 7cd17ee5..00000000
--- a/slf4j-site/src/site/resources/images/logos/valid-html401.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/mailman.jpg b/slf4j-site/src/site/resources/images/mailman.jpg
deleted file mode 100644
index 94a4c011..00000000
--- a/slf4j-site/src/site/resources/images/mailman.jpg
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/myjob.png b/slf4j-site/src/site/resources/images/myjob.png
deleted file mode 100644
index 40b50d4f..00000000
--- a/slf4j-site/src/site/resources/images/myjob.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/slf4j-migrator.gif b/slf4j-site/src/site/resources/images/slf4j-migrator.gif
deleted file mode 100644
index 27c126ef..00000000
--- a/slf4j-site/src/site/resources/images/slf4j-migrator.gif
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/twitter-bird-light-bgs.png b/slf4j-site/src/site/resources/images/twitter-bird-light-bgs.png
deleted file mode 100644
index 188597e9..00000000
--- a/slf4j-site/src/site/resources/images/twitter-bird-light-bgs.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/images/twitter.png b/slf4j-site/src/site/resources/images/twitter.png
deleted file mode 100644
index 0e75e4d7..00000000
--- a/slf4j-site/src/site/resources/images/twitter.png
+++ /dev/null
Binary files differ
diff --git a/slf4j-site/src/site/resources/slf4j-in-10-slides.ppt b/slf4j-site/src/site/resources/slf4j-in-10-slides.ppt
deleted file mode 100644
index 8976db2e..00000000
--- a/slf4j-site/src/site/resources/slf4j-in-10-slides.ppt
+++ /dev/null
Binary files differ
diff --git a/src/main/assembly/source.xml b/src/main/assembly/source.xml
deleted file mode 100755
index 0013471f..00000000
--- a/src/main/assembly/source.xml
+++ /dev/null
@@ -1,342 +0,0 @@
-<assembly>
- <id>dist</id>
- <formats>
- <format>zip</format>
- <format>tar.gz</format>
- </formats>
- <fileSets>
- <!-- Module POMs -->
- <fileSet>
- <directory>slf4j-api/</directory>
- <outputDirectory>slf4j-api/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jcl/</directory>
- <outputDirectory>slf4j-jcl/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jdk14/</directory>
- <outputDirectory>slf4j-jdk14/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-log4j12/</directory>
- <outputDirectory>slf4j-log4j12/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-nop/</directory>
- <outputDirectory>slf4j-nop/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-simple/</directory>
- <outputDirectory>slf4j-simple/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-android/</directory>
- <outputDirectory>slf4j-android/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-ext/</directory>
- <outputDirectory>slf4j-ext/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
-
- <fileSet>
- <directory>jcl104-over-slf4j/</directory>
- <outputDirectory>jcl104-over-slf4j/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>jcl-over-slf4j/</directory>
- <outputDirectory>jcl-over-slf4j/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>jul-to-slf4j/</directory>
- <outputDirectory>jul-to-slf4j/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>log4j-over-slf4j/</directory>
- <outputDirectory>log4j-over-slf4j/</outputDirectory>
- <includes><include>pom.xml</include></includes>
- </fileSet>
-
- <fileSet>
- <directory>osgi-over-slf4j/</directory>
- <outputDirectory>osgi-over-slf4j/</outputDirectory>
- <includes><include>pom.xml</include></includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-site/</directory>
- <outputDirectory>slf4j-site/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-migrator/</directory>
- <outputDirectory>slf4j-migrator/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>integration/</directory>
- <outputDirectory>integration/</outputDirectory>
- <includes>
- <include>pom.xml</include>
- <include>build.xml</include>
- <include>osgi-build.xml</include>
- <include>lib/*</include>
- </includes>
- </fileSet>
-
- <!-- Module Source directories (includes tests) -->
- <fileSet>
- <directory>slf4j-api/src/</directory>
- <outputDirectory>slf4j-api/src/</outputDirectory>
- <excludes>
- <exclude>test/output/</exclude>
- </excludes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jcl/src/</directory>
- <outputDirectory>slf4j-jcl/src/</outputDirectory>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jdk14/src/</directory>
- <outputDirectory>slf4j-jdk14/src/</outputDirectory>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-log4j12/src/</directory>
- <outputDirectory>slf4j-log4j12/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-nop/src/</directory>
- <outputDirectory>slf4j-nop/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-simple/src/</directory>
- <outputDirectory>slf4j-simple/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-android/src/</directory>
- <outputDirectory>slf4j-android/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-ext/src/</directory>
- <outputDirectory>slf4j-ext/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>jcl-over-slf4j/src/</directory>
- <outputDirectory>jcl-over-slf4j/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>jul-to-slf4j/src/</directory>
- <outputDirectory>jul-to-slf4j/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>log4j-over-slf4j/src/</directory>
- <outputDirectory>log4j-over-slf4j/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>osgi-over-slf4j/src/</directory>
- <outputDirectory>osgi-over-slf4j/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-site/src/</directory>
- <outputDirectory>slf4j-site/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>slf4j-migrator/src/</directory>
- <outputDirectory>slf4j-migrator/src/</outputDirectory>
- </fileSet>
- <fileSet>
- <directory>integration/src/</directory>
- <outputDirectory>integration/src/</outputDirectory>
- </fileSet>
-
-
- <!-- Module JARs -->
- <fileSet>
- <directory>slf4j-api/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-api-${project.version}-sources.jar</include>
- <include>slf4j-api-${project.version}.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jcl/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-jcl-${project.version}.jar</include>
- <include>slf4j-jcl-${project.version}-sources.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-jdk14/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-jdk14-${project.version}-sources.jar</include>
- <include>slf4j-jdk14-${project.version}.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-log4j12/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-log4j12-${project.version}.jar</include>
- <include>slf4j-log4j12-${project.version}-sources.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-nop/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-nop-${project.version}.jar</include>
- <include>slf4j-nop-${project.version}-sources.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-simple/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-simple-${project.version}-sources*.jar</include>
- <include>slf4j-simple-${project.version}.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-android/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-android-${project.version}-sources*.jar</include>
- <include>slf4j-android-${project.version}.jar</include>
- </includes>
- </fileSet>
-
-
- <fileSet>
- <directory>slf4j-ext/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-ext-${project.version}-sources*.jar</include>
- <include>slf4j-ext-${project.version}.jar</include>
- </includes>
- </fileSet>
-
-
- <fileSet>
- <directory>jcl-over-slf4j/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>jcl-over-slf4j-${project.version}-sources.jar</include>
- <include>jcl-over-slf4j-${project.version}.jar</include>
- </includes>
- </fileSet>
- <fileSet>
- <directory>jul-to-slf4j/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>jul-to-slf4j-${project.version}-sources.jar</include>
- <include>jul-to-slf4j-${project.version}.jar</include>
- </includes>
- </fileSet>
- <fileSet>
- <directory>log4j-over-slf4j/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>log4j-over-slf4j-${project.version}.jar</include>
- <include>log4j-over-slf4j-${project.version}-sources.jar</include>
- </includes>
- </fileSet>
- <fileSet>
- <directory>osgi-over-slf4j/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>osgi-over-slf4j-${project.version}.jar</include>
- <include>osgi-over-slf4j-${project.version}-sources.jar</include>
- </includes>
- </fileSet>
-
- <fileSet>
- <directory>slf4j-migrator/target/</directory>
- <outputDirectory>/</outputDirectory>
- <includes>
- <include>slf4j-migrator-${project.version}.jar</include>
- </includes>
- </fileSet>
-
- <!-- Website -->
- <fileSet>
- <directory>target/site</directory>
- <outputDirectory>/site</outputDirectory>
- <excludes>
- <exclude>dist/*</exclude>
- </excludes>
- </fileSet>
-
- <!-- Parent files -->
- <fileSet>
- <includes>
- <include>src/</include>
- <include>README*</include>
- <include>LICENSE*</include>
- <include>pom.xml</include>
- </includes>
- </fileSet>
- </fileSets>
-
-</assembly> \ No newline at end of file
diff --git a/test b/test
deleted file mode 100644
index e69de29b..00000000
--- a/test
+++ /dev/null
diff --git a/version.pl b/version.pl
deleted file mode 100644
index 5587b313..00000000
--- a/version.pl
+++ /dev/null
@@ -1,44 +0,0 @@
-
-if ($#ARGV < 1) {
- print "Usage: version.pl VER FILE {FILE, FILE}\n";
- exit;
-}
-
-$V=$ARGV[0];
-print "VER:'${V}'\r\n";
-shift(@ARGV);
-
-sub replace () {
- my $filename = $_[0];
-
- if(-s $filename) {
- print "Processing [" . $filename . "]\r\n";
-
- my $original = "$filename.original";
-
- rename($filename, $original);
- open(OUT, ">$filename");
- open(IN, "$original");
-
- my $hitCount=0;
- while(<IN>) {
- if($hitCount == 0 && /<version>.*<\/version>/) {
- s/<version>.*<\/version>/<version>${V}<\/version>/;
- $hitCount++;
- }
- print OUT;
- }
- close(IN);
- close(OUT);
- unlink($original);
- } else {
- print "File [" . $filename . "] does not exist\r\n"
- }
-}
-
-foreach $ARG (@ARGV) {
- do replace($ARG);
-}
-
-
-