· 9 years ago · Jan 22, 2017, 05:12 PM
1package org.jbjf.core;
2
3import java.io.File;
4import java.net.URL;
5import java.util.Enumeration;
6
7import org.apache.log4j.ConsoleAppender;
8import org.apache.log4j.FileAppender;
9import org.apache.log4j.Level;
10import org.apache.log4j.LogManager;
11import org.apache.log4j.Logger;
12import org.apache.log4j.PatternLayout;
13import org.apache.log4j.xml.DOMConfigurator;
14
15/**
16 * <p>
17 * The <code>RootLogger</code> is a simple log4j singleton class
18 * that provides an easy management interface to configure, get, set,
19 * re-configure the log4j framework for your application.
20 * </p>
21 * <p>
22 * <h3>Dependencies:</h3>
23 * <ul>
24 * <li>JRE/JDK 6(+)</li>
25 * </ul>
26 * </p>
27 * <p>
28 * <h3>Details</h3>
29 * <hr>
30 * <h4>Input Resources</h4>
31 * <table border='1' width='100%'>
32 * <thead>
33 * <tr>
34 * <td width='15%'>Method</td>
35 * <td width='1%'> </td>
36 * <td width='15%'>Usage</td>
37 * <td width='1%'> </td>
38 * <td>Description/Comments</td>
39 * </tr>
40 * </thead>
41 * <tr valign='top'>
42 * <td>getEndTime/setEndTime</td>
43 * <td> </td>
44 * <td>Runtime</td>
45 * <td> </td>
46 * <td>
47 * Provides a JBJF ...
48 * </td>
49 * </tr>
50 * </table>
51 * </p>
52 * <p>
53 * <h3>Example(s)</h3>
54 * <hr>
55 * <pre>
56 * </pre>
57 * </p>
58 * <p>
59 * @author Adym S. Lincoln<br>
60 * Copyright (C) 2006-2017. JBJF, All rights reserved.
61 * @version 1.0.0
62 * @since 1.0.0
63 * </p>
64 * <p>
65 * @see org.jbjf
66 * </p>
67 */
68
69public final class RootLogger {
70
71 /**
72 * Stores a fully qualified class name. Used for debugging and
73 * auditing.
74 * @since 1.0.0
75 */
76 public static final String ID = RootLogger.class.getName ();
77
78 /**
79 * Stores the class name, primarily used for debugging and so
80 * forth. Used for debugging and auditing.
81 * @since 1.0.0
82 */
83 @SuppressWarnings("unused")
84 private static String SHORT_NAME = "RootLogger()";
85
86 /**
87 * Stores a <code>SYSTEM IDENTITY HASHCODE</code>. Used for
88 * debugging and auditing.
89 * @since 1.0.0
90 */
91 @SuppressWarnings("unused")
92 private String SYSTEM_IDENTITY = String.valueOf ( System.identityHashCode ( this ) );
93
94 /**
95 * Class property that contains the log4j XML file. Defaults
96 * to DEFAULT_LOG4J_XML... ./etc/app-log4j.xml.
97 */
98 private static String log4jXML = null;
99
100 /**
101 * Class property that stores the log4j object/instance.
102 */
103 private static Logger log = null;
104
105 /**
106 * Class property that stores the singleton object/instance.
107 */
108 private static RootLogger instance = null;
109
110 /**
111 * Singleton constructor.
112 */
113 private RootLogger() {
114 }
115
116 /**
117 * <p>
118 * Global access point for the Log4j object/instance...
119 * Logger myLog = RootLogger.getInstance().getLog();
120 * </p>
121 * @return The <code>RootLogger</code> object/instance.
122 */
123 public static RootLogger getInstance() {
124 if( instance == null) {
125 instance = new RootLogger();
126 initInstance ();
127 }
128 return instance;
129 }
130
131 /**
132 * <p>
133 * Returns the current <code>Logger</code>.
134 * </p>
135 * @return Returns the current <code>Logger</code>.
136 */
137 public static Logger getLog() {
138 return log;
139 }
140
141 /**
142 * <p>
143 * Traditional getter that returns the Logger with the given
144 * name...if no Logger is found, then null is returned.
145 * </p>
146 * @param theLoggerName The name of the Logger.
147 * @return A <code>Logger</code> if it exists or null.
148 */
149 public static Logger getLog ( String theLoggerName ) {
150 Logger ltheResults = null;
151 if ( theLoggerName != null ) {
152 for (Enumeration loggers=LogManager.getCurrentLoggers(); loggers.hasMoreElements(); ) {
153 Logger logger = (Logger) loggers.nextElement();
154 if ( logger.getName ().equals ( theLoggerName ) ) {
155 ltheResults = logger;
156 }
157 getLog().debug ( SHORT_NAME + ".setLog () - FOUND Logger......[" + logger.getName () + "]" );
158
159 }
160
161 }
162 return ltheResults;
163 }
164
165 public static void setLog(Logger theLog) {
166 log = theLog;
167 }
168
169 /**
170 * <p>
171 * A traditional setter method that allows you to set a specific
172 * logger as the new logger object/instance. By default, the
173 * rootLogger is set when the instance is initialized.
174 * </p>
175 * @param theLoggerName The name of the logger you wish to
176 * promote as the new logger...if the name is NOT FOUND, then
177 * the existing logger is left untouched.
178 */
179 public static void setLog ( String theLoggerName ) {
180 if ( theLoggerName != null ) {
181 for (Enumeration<Logger> loggers=LogManager.getCurrentLoggers(); loggers.hasMoreElements(); ) {
182 Logger logger = loggers.nextElement();
183 if ( logger.getName ().equals ( theLoggerName ) ) {
184 getLog().debug ( SHORT_NAME + ".setLog () - NEW Logger......[" + logger.getName () + "]" );
185 log = logger;
186 getLog().debug ( SHORT_NAME + ".setLog () - NEW Logger......[" + logger.getName () + "]" );
187 }
188
189 }
190
191 }
192
193 }
194
195 /**
196 * <p>
197 * A secondary initialization that allows you to re-configure
198 * the log4j framework using a different XML file. The log4j
199 * object/instance is reset to the new rootLogger defined in
200 * the given XML file. Unlike the startup initialization, this
201 * initialization will only do the following search and resolve
202 * steps :
203 * </p>
204 * <ul>
205 * <li>Use the file path and filename.xml in getLog4jXML().</li>
206 * <li>Use getLog4jXML() as a resource on the CLASSPATH...
207 * ClassLoader.getResource ( getLog4jXML() );</li>
208 * <li>Use getLog4jXML() as a resource next to this class...
209 * this.class.getResource ( "/"+getLog4jXML() );</li>
210 * </ul>
211 * <p>
212 * If all of the configuration attempts fail, then the log4j
213 * object/instance is left untouched.
214 * </p>
215 */
216 public static void initInstance ( String theLog4jPath ) {
217 setLog4jXML ( theLog4jPath );
218
219 File theLog4jFile = null;
220
221 try {
222 // FILE : First try and resolve and configure log4j
223 // using a direct file path/name.
224 //
225 if ( getLog4jXML() != null ) {
226 theLog4jFile = new File ( getLog4jXML() );
227 if ( theLog4jFile != null ) {
228 if ( theLog4jFile.exists () ) {
229 if ( theLog4jFile.canRead () ) {
230 System.out.println ( SHORT_NAME + ".setLog () Log4j XML Path [" + getLog4jXML() + "]" );
231 System.out.println ( SHORT_NAME + ".setLog () Log4j File Path [" + theLog4jFile.getAbsolutePath () + "]" );
232 DOMConfigurator.configureAndWatch ( getLog4jXML() );
233 log = Logger.getRootLogger ();
234
235 theLog4jFile = null;
236
237 }
238 else {
239 System.out.println ( SHORT_NAME + ".setLog () Log4j XML Path [" + getLog4jXML() + "] - CAN NOT BE READ!" );
240 }
241 }
242 else {
243 System.out.println ( SHORT_NAME + ".setLog () Log4j XML Path [" + getLog4jXML() + "] - DOES NOT EXIST!" );
244 }
245 }
246 }
247
248 // URL : Second, try and resolve and configure log4j
249 // using a URL on the CLASSPATH.
250 //
251 URL lclsLoaderResource = RootLogger.class.getClassLoader().getResource ( getLog4jXML() );
252 if ( ( lclsLoaderResource != null ) ) {
253 System.out.println ( SHORT_NAME + ".setLog () classLoaderResource URL [" + lclsLoaderResource.getFile () + "]" );
254 DOMConfigurator.configure ( lclsLoaderResource );
255 log = Logger.getRootLogger ();
256 }
257
258 // URL : Third, try and resolve and configure log4j
259 // using a URL on the class resource.
260 //
261 URL lclassResource = RootLogger.class.getResource ( "/"+getLog4jXML() );
262 if ( ( lclassResource != null ) ) {
263 System.out.println ( SHORT_NAME + ".setLog () classResource URL [" + lclassResource.getFile () + "]" );
264 DOMConfigurator.configure ( lclassResource );
265 log = Logger.getRootLogger ();
266 }
267
268 }
269 catch ( Exception lioXcp ) {
270 lioXcp.printStackTrace();
271 }
272
273 getLog ().debug ( SHORT_NAME + ".setLog() - COMPLETE! [" + getLog ().getName () + "]" );
274
275 }
276
277 /**
278 * <p>
279 * The primary method that will do an exhaustive search and resolve
280 * to identify and establish the log4j object/instance. If all
281 * search and resolves fails, then a default console and file
282 * appender are created and assigned.
283 * </p>
284 * <ul>
285 * <li>Use the file path and name.ext in getLog4jXML().</li>
286 * <li>Use getLog4jXML() as a resource on the CLASSPATH.</li>
287 * <li>Use getLog4jXML() as a resource next to this class.</li>
288 * <li>Use /log4j.xml as a resource next to this class.</li>
289 * <li>If all else, hard-code a console and single file appender (./jbjf-default.log) to teh rootLogger.</li>
290 * </ul>
291 */
292 public static void initInstance() {
293 File theLog4jFile = null;
294
295 if ( System.getProperty ( JBJFBaseGlobals.JVM_LOG4J_ARGUMENT ) != null ) {
296 setLog4jXML ( System.getProperty ( JBJFBaseGlobals.JVM_LOG4J_ARGUMENT ) );
297 System.out.println ( SHORT_NAME + ".initInstance () - JVM Argument......[" + JBJFBaseGlobals.JVM_LOG4J_ARGUMENT + "] Value [" + getLog4jXML () + "]" );
298 }
299
300 if ( getLog4jXML () == null ) {
301 setLog4jXML ( JBJFBaseGlobals.DEFAULT_LOG4J_XML );
302 System.out.println ( SHORT_NAME + ".initInstance () - Default Log4j.....[" + JBJFBaseGlobals.DEFAULT_LOG4J_XML + "] Value [" + getLog4jXML () + "]" );
303 }
304
305 try {
306
307 // FILE : First try and resolve and configure log4j
308 // using a direct file path/name.
309 //
310 if ( getLog4jXML() != null ) {
311 theLog4jFile = new File ( getLog4jXML() );
312 if ( theLog4jFile != null ) {
313 if ( theLog4jFile.exists () ) {
314 if ( theLog4jFile.canRead () ) {
315 System.out.println ( SHORT_NAME + ".initInstance () Log4j XML Path [" + getLog4jXML() + "]" );
316 System.out.println ( SHORT_NAME + ".initInstance () Log4j File Path [" + theLog4jFile.getAbsolutePath () + "]" );
317 DOMConfigurator.configureAndWatch ( getLog4jXML() );
318 log = Logger.getRootLogger ();
319
320 }
321 else {
322 System.out.println ( SHORT_NAME + ".initInstance () Log4j XML Path [" + getLog4jXML() + "] - CAN NOT BE READ!" );
323 }
324 }
325 else {
326 System.out.println ( SHORT_NAME + ".initInstance () Log4j XML Path [" + getLog4jXML() + "] - DOES NOT EXIST!" );
327 }
328 }
329 }
330
331 // URL : Second, try and resolve and configure log4j
332 // using a URL on the CLASSPATH.
333 //
334 URL lclsLoaderResource = RootLogger.class.getClassLoader().getResource ( getLog4jXML() );
335 if ( ( lclsLoaderResource != null ) && ( log == null ) ) {
336 System.out.println ( SHORT_NAME + ".initInstance () classLoaderResource URL [" + lclsLoaderResource.getFile () + "]" );
337 DOMConfigurator.configure ( lclsLoaderResource );
338 log = Logger.getRootLogger ();
339 }
340
341 // URL : Third, try and resolve and configure log4j
342 // using a URL on the class resource.
343 //
344 URL lclassResource = RootLogger.class.getResource ( "/"+getLog4jXML() );
345 if ( ( lclassResource != null ) && ( log == null ) ) {
346 System.out.println ( SHORT_NAME + ".initInstance () classResource URL [" + lclassResource.getFile () + "]" );
347 DOMConfigurator.configure ( lclassResource );
348 log = Logger.getRootLogger ();
349 }
350
351 // URL : Next, try and see if a default log4j XML file
352 // is on the CLASSPATH
353 //
354 URL ldefaultLog4j = RootLogger.class.getResource ( "/log4j.xml" );
355 if ( ( ldefaultLog4j != null ) && ( log == null ) ) {
356 System.out.println ( SHORT_NAME + ".initInstance () default log4j XML [" + lclassResource.getFile () + "]" );
357 DOMConfigurator.configure ( ldefaultLog4j );
358 log = Logger.getRootLogger ();
359 }
360
361 }
362 catch ( Exception lioXcp ) {
363 // TODO Auto-generated catch block
364 lioXcp.printStackTrace();
365 }
366
367 if ( log == null ) {
368 ConsoleAppender console = new ConsoleAppender(); //create appender
369 //configure the appender
370 String PATTERN = "%d [%p|%c|%C{1}] %m%n";
371 console.setLayout(new PatternLayout(PATTERN));
372 console.setThreshold(Level.DEBUG);
373 console.activateOptions();
374 //add appender to any Logger (here is root)
375 Logger.getRootLogger().addAppender(console);
376
377 FileAppender fa = new FileAppender();
378 fa.setName("DefaultLogger");
379 fa.setFile("jbjf-default.log");
380 fa.setLayout(new PatternLayout("%d %-5p [%c{1}] %m%n"));
381 fa.setThreshold(Level.DEBUG);
382 fa.setAppend(true);
383 fa.activateOptions();
384
385 //add appender to any Logger (here is root)
386 Logger.getRootLogger().addAppender(fa);
387 log = Logger.getRootLogger ();
388
389 }
390
391 getLog ().debug ( SHORT_NAME + ".setLog() - COMPLETE! [" + getLog ().getName () + "]" );
392
393 }
394
395 /**
396 * <p>
397 * Traditional getter method that returns the current log4j XML
398 * directory path and filename.ext.
399 * </p>
400 * @return The current log4j XML directory path and filename.ext
401 */
402 public static String getLog4jXML() {
403 return log4jXML;
404 }
405
406 /**
407 * <p>
408 * Traditional setter method that accepts a new log4j XML file
409 * and will re-configure the log4j framework using the new file.
410 * </p>
411 * @param theLog4jXML A new log4j XML file.
412 */
413 public static void setLog4jXML(String theLog4jXML) {
414 log4jXML = theLog4jXML;
415 initInstance ( theLog4jXML );
416 }
417
418}