private void parseErrorHandler( final ErrorHandler eh, final String errorHandlerPrefix, final Properties props, final LoggerRepository hierarchy) { boolean rootRef = OptionConverter.toBoolean( OptionConverter.findAndSubst(errorHandlerPrefix + ROOT_REF, props), false); if (rootRef) { eh.setLogger(hierarchy.getRootLogger()); } String loggerName = OptionConverter.findAndSubst(errorHandlerPrefix + LOGGER_REF, props); if (loggerName != null) { Logger logger = (loggerFactory == null) ? hierarchy.getLogger(loggerName) : hierarchy.getLogger(loggerName, loggerFactory); eh.setLogger(logger); } String appenderName = OptionConverter.findAndSubst(errorHandlerPrefix + APPENDER_REF_TAG, props); if (appenderName != null) { Appender backup = parseAppender(props, appenderName); if (backup != null) { eh.setBackupAppender(backup); } } }
/** Parse the additivity option for a non-root category. */ void parseAdditivityForLogger(Properties props, Logger cat, String loggerName) { String value = OptionConverter.findAndSubst(ADDITIVITY_PREFIX + loggerName, props); LogLog.debug("Handling " + ADDITIVITY_PREFIX + loggerName + "=[" + value + "]"); // touch additivity only if necessary if ((value != null) && (!value.equals(""))) { boolean additivity = OptionConverter.toBoolean(value, true); LogLog.debug("Setting additivity for \"" + loggerName + "\" to " + additivity); cat.setAdditivity(additivity); } }
/** * Check the provided <code>Properties</code> object for a {@link * org.apache.log4j.spi.LoggerFactory LoggerFactory} entry specified by {@link * #LOGGER_FACTORY_KEY}. If such an entry exists, an attempt is made to create an instance using * the default constructor. This instance is used for subsequent Category creations within this * configurator. * * @see #parseCatsAndRenderers */ protected void configureLoggerFactory(Properties props) { String factoryClassName = OptionConverter.findAndSubst(LOGGER_FACTORY_KEY, props); if (factoryClassName != null) { LogLog.debug("Setting category factory to [" + factoryClassName + "]."); loggerFactory = (LoggerFactory) OptionConverter.instantiateByClassName( factoryClassName, LoggerFactory.class, loggerFactory); PropertySetter.setProperties(loggerFactory, props, FACTORY_PREFIX + "."); } }
static { String prop = OptionConverter.getSystemProperty("java.version", null); if (prop != null) { int i = prop.indexOf('.'); if (i != -1) { if (prop.charAt(i + 1) != '1') java1 = false; } } String ignoreTCLProp = OptionConverter.getSystemProperty("log4j.ignoreTCL", null); if (ignoreTCLProp != null) { ignoreTCL = OptionConverter.toBoolean(ignoreTCLProp, true); } }
void configureRootCategory(Properties props, LoggerRepository hierarchy) { String effectiveFrefix = ROOT_LOGGER_PREFIX; String value = OptionConverter.findAndSubst(ROOT_LOGGER_PREFIX, props); if (value == null) { value = OptionConverter.findAndSubst(ROOT_CATEGORY_PREFIX, props); effectiveFrefix = ROOT_CATEGORY_PREFIX; } if (value == null) LogLog.debug("Could not find root logger information. Is this OK?"); else { Logger root = hierarchy.getRootLogger(); synchronized (root) { parseCategory(props, root, effectiveFrefix, INTERNAL_ROOT_NAME, value); } } }
/** Parse non-root elements, such non-root categories and renderers. */ protected void parseCatsAndRenderers(Properties props, LoggerRepository hierarchy) { Enumeration enumeration = props.propertyNames(); while (enumeration.hasMoreElements()) { String key = (String) enumeration.nextElement(); if (key.startsWith(CATEGORY_PREFIX) || key.startsWith(LOGGER_PREFIX)) { String loggerName = null; if (key.startsWith(CATEGORY_PREFIX)) { loggerName = key.substring(CATEGORY_PREFIX.length()); } else if (key.startsWith(LOGGER_PREFIX)) { loggerName = key.substring(LOGGER_PREFIX.length()); } String value = OptionConverter.findAndSubst(key, props); Logger logger = hierarchy.getLogger(loggerName, loggerFactory); synchronized (logger) { parseCategory(props, logger, key, loggerName, value); parseAdditivityForLogger(props, logger, loggerName); } } else if (key.startsWith(RENDERER_PREFIX)) { String renderedClass = key.substring(RENDERER_PREFIX.length()); String renderingClass = OptionConverter.findAndSubst(key, props); if (hierarchy instanceof RendererSupport) { RendererMap.addRenderer((RendererSupport) hierarchy, renderedClass, renderingClass); } } else if (key.equals(THROWABLE_RENDERER_PREFIX)) { if (hierarchy instanceof ThrowableRendererSupport) { ThrowableRenderer tr = (ThrowableRenderer) OptionConverter.instantiateByKey( props, THROWABLE_RENDERER_PREFIX, org.apache.log4j.spi.ThrowableRenderer.class, null); if (tr == null) { LogLog.error("Could not instantiate throwableRenderer."); } else { PropertySetter setter = new PropertySetter(tr); setter.setProperties(props, THROWABLE_RENDERER_PREFIX + "."); ((ThrowableRendererSupport) hierarchy).setThrowableRenderer(tr); } } } } }
public static Object instantiateByKey( Properties props, String key, Class superClass, Object defaultValue) { // Get the value of the property in string form String className = findAndSubst(key, props); if (className == null) { LogLog.error("Could not find value for key " + key); return defaultValue; } // Trim className to avoid trailing spaces that cause problems. return OptionConverter.instantiateByClassName(className.trim(), superClass, defaultValue); }
/** * Read configuration options from <code>properties</code>. * * <p>See {@link #doConfigure(String, LoggerRepository)} for the expected format. */ public void doConfigure(Properties properties, LoggerRepository hierarchy) { repository = hierarchy; String value = properties.getProperty(LogLog.DEBUG_KEY); if (value == null) { value = properties.getProperty("log4j.configDebug"); if (value != null) LogLog.warn("[log4j.configDebug] is deprecated. Use [log4j.debug] instead."); } if (value != null) { LogLog.setInternalDebugging(OptionConverter.toBoolean(value, true)); } // // if log4j.reset=true then // reset hierarchy String reset = properties.getProperty(RESET_KEY); if (reset != null && OptionConverter.toBoolean(reset, false)) { hierarchy.resetConfiguration(); } String thresholdStr = OptionConverter.findAndSubst(THRESHOLD_PREFIX, properties); if (thresholdStr != null) { hierarchy.setThreshold(OptionConverter.toLevel(thresholdStr, (Level) Level.ALL)); LogLog.debug("Hierarchy threshold set to [" + hierarchy.getThreshold() + "]."); } configureRootCategory(properties, hierarchy); configureLoggerFactory(properties); parseCatsAndRenderers(properties, hierarchy); LogLog.debug("Finished configuring."); // We don't want to hold references to appenders preventing their // garbage collection. registry.clear(); }
/** This method must work for the root category as well. */ void parseCategory( Properties props, Logger logger, String optionKey, String loggerName, String value) { LogLog.debug("Parsing for [" + loggerName + "] with value=[" + value + "]."); // We must skip over ',' but not white space StringTokenizer st = new StringTokenizer(value, ","); // If value is not in the form ", appender.." or "", then we should set // the level of the loggeregory. if (!(value.startsWith(",") || value.equals(""))) { // just to be on the safe side... if (!st.hasMoreTokens()) return; String levelStr = st.nextToken(); LogLog.debug("Level token is [" + levelStr + "]."); // If the level value is inherited, set category level value to // null. We also check that the user has not specified inherited for the // root category. if (INHERITED.equalsIgnoreCase(levelStr) || NULL.equalsIgnoreCase(levelStr)) { if (loggerName.equals(INTERNAL_ROOT_NAME)) { LogLog.warn("The root logger cannot be set to null."); } else { logger.setLevel(null); } } else { logger.setLevel(OptionConverter.toLevel(levelStr, (Level) Level.DEBUG)); } LogLog.debug("Category " + loggerName + " set to " + logger.getLevel()); } // Begin by removing all existing appenders. logger.removeAllAppenders(); Appender appender; String appenderName; while (st.hasMoreTokens()) { appenderName = st.nextToken().trim(); if (appenderName == null || appenderName.equals(",")) continue; LogLog.debug("Parsing appender named \"" + appenderName + "\"."); appender = parseAppender(props, appenderName); if (appender != null) { logger.addAppender(appender); } } }
/** * Load the DSpace configuration properties. Only does anything if properties are not already * loaded. Properties are loaded in from the specified file, or default locations. * * @param configFile The <code>dspace.cfg</code> configuration file to use, or <code>null</code> * to try default locations */ public static synchronized void loadConfig(String configFile) { if (properties != null) { return; } URL url = null; InputStream is = null; try { String configProperty = null; try { configProperty = System.getProperty("dspace.configuration"); } catch (SecurityException se) { // A security manager may stop us from accessing the system properties. // This isn't really a fatal error though, so catch and ignore log.warn("Unable to access system properties, ignoring.", se); } if (configFile != null) { info("Loading provided config file: " + configFile); loadedFile = new File(configFile); url = loadedFile.toURL(); } // Has the default configuration location been overridden? else if (configProperty != null) { info("Loading system provided config property (-Ddspace.configuration): " + configProperty); // Load the overriding configuration loadedFile = new File(configProperty); url = loadedFile.toURL(); } // Load configuration from default location else { url = ConfigurationManager.class.getResource("/dspace.cfg"); if (url != null) { info("Loading from classloader: " + url); loadedFile = new File(url.getPath()); } } if (url == null) { fatal("Cannot find dspace.cfg"); throw new RuntimeException("Cannot find dspace.cfg"); } else { properties = new Properties(); is = url.openStream(); properties.load(is); // walk values, interpolating any embedded references. for (Enumeration pe = properties.propertyNames(); pe.hasMoreElements(); ) { String key = (String) pe.nextElement(); String value = interpolate(key, 1); if (value != null) properties.setProperty(key, value); } } } catch (IOException e) { fatal("Can't load configuration: " + url, e); // FIXME: Maybe something more graceful here, but with the // configuration we can't do anything throw new RuntimeException("Cannot load configuration: " + url, e); } finally { if (is != null) try { is.close(); } catch (IOException ioe) { } } // Load in default license File licenseFile = new File( getProperty("dspace.dir") + File.separator + "config" + File.separator + "default.license"); FileInputStream fir = null; InputStreamReader ir = null; BufferedReader br = null; try { fir = new FileInputStream(licenseFile); ir = new InputStreamReader(fir, "UTF-8"); br = new BufferedReader(ir); String lineIn; license = ""; while ((lineIn = br.readLine()) != null) { license = license + lineIn + '\n'; } br.close(); } catch (IOException e) { fatal("Can't load license: " + licenseFile.toString(), e); // FIXME: Maybe something more graceful here, but with the // configuration we can't do anything throw new RuntimeException("Cannot load license: " + licenseFile.toString(), e); } finally { if (br != null) try { br.close(); } catch (IOException ioe) { } if (ir != null) try { ir.close(); } catch (IOException ioe) { } if (fir != null) try { fir.close(); } catch (IOException ioe) { } } try { /* * Initialize Logging once ConfigurationManager is initialized. * * This is selection from a property in dspace.cfg, if the property * is absent then nothing will be configured and the application * will use the defaults provided by log4j. * * Property format is: * * log.init.config = ${dspace.dir}/config/log4j.properties * or * log.init.config = ${dspace.dir}/config/log4j.xml * * See default log4j initialization documentation here: * http://logging.apache.org/log4j/docs/manual.html * * If there is a problem with the file referred to in * "log.configuration" it needs to be sent to System.err * so do not instantiate another Logging configuration. * */ String dsLogConfiguration = ConfigurationManager.getProperty("log.init.config"); if (dsLogConfiguration == null || System.getProperty("dspace.log.init.disable") != null) { /* * Do nothing if log config not set in dspace.cfg or "dspace.log.init.disable" * system property set. Leave it upto log4j to properly init its logging * via classpath or system properties. */ info( "Using default log4j provided log configuration," + "if uninitended, check your dspace.cfg for (log.init.config)"); } else { info("Using dspace provided log configuration (log.init.config)"); File logConfigFile = new File(dsLogConfiguration); if (logConfigFile.exists()) { info("Loading: " + dsLogConfiguration); OptionConverter.selectAndConfigure( logConfigFile.toURL(), null, org.apache.log4j.LogManager.getLoggerRepository()); } else { info("File does not exist: " + dsLogConfiguration); } } } catch (MalformedURLException e) { fatal("Can't load dspace provided log4j configuration", e); throw new RuntimeException("Cannot load dspace provided log4j configuration", e); } }
void parseAppenderFilters(Properties props, String appenderName, Appender appender) { // extract filters and filter options from props into a hashtable mapping // the property name defining the filter class to a list of pre-parsed // name-value pairs associated to that filter final String filterPrefix = APPENDER_PREFIX + appenderName + ".filter."; int fIdx = filterPrefix.length(); Hashtable filters = new Hashtable(); Enumeration e = props.keys(); String name = ""; while (e.hasMoreElements()) { String key = (String) e.nextElement(); if (key.startsWith(filterPrefix)) { int dotIdx = key.indexOf('.', fIdx); String filterKey = key; if (dotIdx != -1) { filterKey = key.substring(0, dotIdx); name = key.substring(dotIdx + 1); } Vector filterOpts = (Vector) filters.get(filterKey); if (filterOpts == null) { filterOpts = new Vector(); filters.put(filterKey, filterOpts); } if (dotIdx != -1) { String value = OptionConverter.findAndSubst(key, props); filterOpts.add(new NameValue(name, value)); } } } // sort filters by IDs, insantiate filters, set filter options, // add filters to the appender Enumeration g = new SortedKeyEnumeration(filters); while (g.hasMoreElements()) { String key = (String) g.nextElement(); String clazz = props.getProperty(key); if (clazz != null) { LogLog.debug( "Filter key: [" + key + "] class: [" + props.getProperty(key) + "] props: " + filters.get(key)); Filter filter = (Filter) OptionConverter.instantiateByClassName(clazz, Filter.class, null); if (filter != null) { PropertySetter propSetter = new PropertySetter(filter); Vector v = (Vector) filters.get(key); Enumeration filterProps = v.elements(); while (filterProps.hasMoreElements()) { NameValue kv = (NameValue) filterProps.nextElement(); propSetter.setProperty(kv.key, kv.value); } propSetter.activate(); LogLog.debug( "Adding filter of type [" + filter.getClass() + "] to appender named [" + appender.getName() + "]."); appender.addFilter(filter); } } else { LogLog.warn("Missing class definition for filter: [" + key + "]"); } } }
Appender parseAppender(Properties props, String appenderName) { Appender appender = registryGet(appenderName); if ((appender != null)) { LogLog.debug("Appender \"" + appenderName + "\" was already parsed."); return appender; } // Appender was not previously initialized. String prefix = APPENDER_PREFIX + appenderName; String layoutPrefix = prefix + ".layout"; appender = (Appender) OptionConverter.instantiateByKey(props, prefix, org.apache.log4j.Appender.class, null); if (appender == null) { LogLog.error("Could not instantiate appender named \"" + appenderName + "\"."); return null; } appender.setName(appenderName); if (appender instanceof OptionHandler) { if (appender.requiresLayout()) { Layout layout = (Layout) OptionConverter.instantiateByKey(props, layoutPrefix, Layout.class, null); if (layout != null) { appender.setLayout(layout); LogLog.debug("Parsing layout options for \"" + appenderName + "\"."); // configureOptionHandler(layout, layoutPrefix + ".", props); PropertySetter.setProperties(layout, props, layoutPrefix + "."); LogLog.debug("End of parsing for \"" + appenderName + "\"."); } } final String errorHandlerPrefix = prefix + ".errorhandler"; String errorHandlerClass = OptionConverter.findAndSubst(errorHandlerPrefix, props); if (errorHandlerClass != null) { ErrorHandler eh = (ErrorHandler) OptionConverter.instantiateByKey( props, errorHandlerPrefix, ErrorHandler.class, null); if (eh != null) { appender.setErrorHandler(eh); LogLog.debug("Parsing errorhandler options for \"" + appenderName + "\"."); parseErrorHandler(eh, errorHandlerPrefix, props, repository); final Properties edited = new Properties(); final String[] keys = new String[] { errorHandlerPrefix + "." + ROOT_REF, errorHandlerPrefix + "." + LOGGER_REF, errorHandlerPrefix + "." + APPENDER_REF_TAG }; for (Iterator iter = props.entrySet().iterator(); iter.hasNext(); ) { Map.Entry entry = (Map.Entry) iter.next(); int i = 0; for (; i < keys.length; i++) { if (keys[i].equals(entry.getKey())) break; } if (i == keys.length) { edited.put(entry.getKey(), entry.getValue()); } } PropertySetter.setProperties(eh, edited, errorHandlerPrefix + "."); LogLog.debug("End of errorhandler parsing for \"" + appenderName + "\"."); } } // configureOptionHandler((OptionHandler) appender, prefix + ".", props); PropertySetter.setProperties(appender, props, prefix + "."); LogLog.debug("Parsed \"" + appenderName + "\" options."); } parseAppenderFilters(props, appenderName, appender); registryPut(appender); return appender; }
/** * Set the maximum size that the output file is allowed to reach before being rolled over to * backup files. * * <p>In configuration files, the <b>MaxFileSize</b> option takes an long integer in the range 0 - * 2^63. You can specify the value with the suffixes "KB", "MB" or "GB" so that the integer is * interpreted being expressed respectively in kilobytes, megabytes or gigabytes. For example, the * value "10KB" will be interpreted as 10240. */ public void setMaxFileSize(String value) { maxFileSize = OptionConverter.toFileSize(value, maxFileSize + 1); }
/* */ protected void finalizeConverter(char c) /* */ { /* 232 */ PatternConverter pc = null; /* 233 */ switch (c) { /* */ case 'c': /* 235 */ pc = new CategoryPatternConverter(this.formattingInfo, extractPrecisionOption()); /* */ /* 239 */ this.currentLiteral.setLength(0); /* 240 */ break; /* */ case 'C': /* 242 */ pc = new ClassNamePatternConverter(this.formattingInfo, extractPrecisionOption()); /* */ /* 246 */ this.currentLiteral.setLength(0); /* 247 */ break; /* */ case 'd': /* 249 */ String dateFormatStr = "ISO8601"; /* */ /* 251 */ String dOpt = extractOption(); /* 252 */ if (dOpt != null) /* 253 */ dateFormatStr = dOpt; /* */ DateFormat df; /* 255 */ if (dateFormatStr.equalsIgnoreCase("ISO8601")) /* */ { /* 257 */ df = new ISO8601DateFormat(); /* 258 */ } else if (dateFormatStr.equalsIgnoreCase("ABSOLUTE")) /* */ { /* 260 */ df = new AbsoluteTimeDateFormat(); /* 261 */ } else if (dateFormatStr.equalsIgnoreCase("DATE")) /* */ { /* 263 */ df = new DateTimeDateFormat(); /* */ } /* */ else try { /* 266 */ df = new SimpleDateFormat(dateFormatStr); /* */ } /* */ catch (IllegalArgumentException e) { /* 269 */ LogLog.error( "Could not instantiate SimpleDateFormat with " + dateFormatStr, e); /* */ /* 271 */ df = (DateFormat) OptionConverter.instantiateByClassName( "org.apache.log4j.helpers.ISO8601DateFormat", DateFormat.class, null); /* */ } /* */ /* */ /* 276 */ pc = new DatePatternConverter(this.formattingInfo, df); /* */ /* 279 */ this.currentLiteral.setLength(0); /* 280 */ break; /* */ case 'F': /* 282 */ pc = new LocationPatternConverter(this.formattingInfo, 1004); /* */ /* 286 */ this.currentLiteral.setLength(0); /* 287 */ break; /* */ case 'l': /* 289 */ pc = new LocationPatternConverter(this.formattingInfo, 1000); /* */ /* 293 */ this.currentLiteral.setLength(0); /* 294 */ break; /* */ case 'L': /* 296 */ pc = new LocationPatternConverter(this.formattingInfo, 1003); /* */ /* 300 */ this.currentLiteral.setLength(0); /* 301 */ break; /* */ case 'm': /* 303 */ pc = new BasicPatternConverter(this.formattingInfo, 2004); /* */ /* 306 */ this.currentLiteral.setLength(0); /* 307 */ break; /* */ case 'M': /* 309 */ pc = new LocationPatternConverter(this.formattingInfo, 1001); /* */ /* 313 */ this.currentLiteral.setLength(0); /* 314 */ break; /* */ case 'p': /* 316 */ pc = new BasicPatternConverter(this.formattingInfo, 2002); /* */ /* 319 */ this.currentLiteral.setLength(0); /* 320 */ break; /* */ case 'r': /* 322 */ pc = new BasicPatternConverter(this.formattingInfo, 2000); /* */ /* 326 */ this.currentLiteral.setLength(0); /* 327 */ break; /* */ case 't': /* 329 */ pc = new BasicPatternConverter(this.formattingInfo, 2001); /* */ /* 332 */ this.currentLiteral.setLength(0); /* 333 */ break; /* */ case 'x': /* 349 */ pc = new BasicPatternConverter(this.formattingInfo, 2003); /* */ /* 351 */ this.currentLiteral.setLength(0); /* 352 */ break; /* */ case 'X': /* 354 */ String xOpt = extractOption(); /* 355 */ pc = new MDCPatternConverter(this.formattingInfo, xOpt); /* 356 */ this.currentLiteral.setLength(0); /* 357 */ break; /* */ case 'D': /* */ case 'E': /* */ case 'G': /* */ case 'H': /* */ case 'I': /* */ case 'J': /* */ case 'K': /* */ case 'N': /* */ case 'O': /* */ case 'P': /* */ case 'Q': /* */ case 'R': /* */ case 'S': /* */ case 'T': /* */ case 'U': /* */ case 'V': /* */ case 'W': /* */ case 'Y': /* */ case 'Z': /* */ case '[': /* */ case '\\': /* */ case ']': /* */ case '^': /* */ case '_': /* */ case '`': /* */ case 'a': /* */ case 'b': /* */ case 'e': /* */ case 'f': /* */ case 'g': /* */ case 'h': /* */ case 'i': /* */ case 'j': /* */ case 'k': /* */ case 'n': /* */ case 'o': /* */ case 'q': /* */ case 's': /* */ case 'u': /* */ case 'v': /* */ case 'w': /* */ default: /* 359 */ LogLog.error( "Unexpected char [" + c + "] at position " + this.i + " in conversion patterrn."); /* */ /* 361 */ pc = new LiteralPatternConverter(this.currentLiteral.toString()); /* 362 */ this.currentLiteral.setLength(0); /* */ } /* */ /* 365 */ addConverter(pc); /* */ }