Log4j DailyFileAppender in welcher Version?

Also hier habe ich schonmal einen ersten Wurf, der ganz prima funktioniert.
Fehlen tut da eigentlich nur noch die Möglichkeit (persistent) laufende Nummern mit einkonfigurieren zu können.
Java:
package de.cmk.log4j;

import java.util.HashMap;

import org.apache.log4j.FileAppender;

import de.cmk.util.generate.StringComposer;


public class NameComposingFileAppender extends FileAppender
{
	private String m_inputRegex       = null;
	private String m_str4Constr       = null;
	
	public void activateOptions() 
	{
		
		if (m_inputRegex==null)
		{
			StringComposer strComp = new StringComposer(new HashMap(), fileName);
			fileName = strComp.constructString();
		}
		else if (m_str4Constr==null)
		{
			errorHandler.error("String4ConstructionProperty has to be given when InputRegex are set!");
		}
		else
		{
			StringComposer strComp = new StringComposer(new HashMap(),
														m_inputRegex,
														m_str4Constr,
														fileName);
			fileName = strComp.constructString();
		}
		
		super.activateOptions();
	}
	
	public void setString4Construction(String str4ConstrProp)
	{
		m_str4Constr = str4ConstrProp;
	}
	
	public void setInputRegex(String inputRegex)
	{
		m_inputRegex = inputRegex;
	}	
}
Hier eine kleine Testkonfiguration
XML:
<?xml version="1.0" encoding="UTF-8" ?> 
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd"> 
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/"> 
<appender name="jdtaconv" class="de.cmk.log4j.NameComposingFileAppender"> 
        <param name="String4Construction" value="${inputfilename}"></param>
        <param name="inputRegex" value="([\\w[\\-]]*)\.([\\w[\\-]]*)\.([\\w[\\-]]*)\.([\\w[\\-]]*)\.(.*)"></param>
        <param name="file" value="logs/${user.name}/(1).{yyyy-MM-dd_HH-mm-ss-SSS}.(2).(3).(4).log" ></param> 
        <param name="Append" value="false" /> 
        <layout class="org.apache.log4j.PatternLayout"> 
                <param name="ConversionPattern" 
                        value="%d{ISO8601} %-5p %m%n" /> 
        </layout> 
</appender> 

<category name="de.tai.jdtatool2"> 
        <priority value="TRACE" ></priority> 
        <appender-ref ref="jdtaconv" /> 
</category> 

</log4j:configuration>
Hier sei angemerkt, dass inputfilename als zusätzliche Systemproperty im Aufruf der Anwendung der JVM mitgegeben wurde.

Schön finde ich, dass das Log4J Framework den Inhalt in Bezug auf ${Systempropertyname} von selbst auflöst. Das geht sogar soweit, dass man beim Aufrufscript der Anwendung eigene Systemproperties mit reinbringen kann, die auch berücksichtigt werden.
Beispiel:
Code:
...
<param name="file" value="logs/${user.name}/${inputfilename}.log" ></param> 
...

Eigene Appender-Properties zu erstellen geht recht einfach: Es ist lediglich die entsprechende Setter-Methode in seinen Appender einzubringen und ohne Umschweife können diese in der XML mit Werten belegt werden. (s. String4Construction, inputRegex)

BTW: Irgendwie hat es in meinem Appender den Anschein, dass hier die Property-Namen nicht "case sensitive" sind (bin selbst verblüfft)

Anbei die noch notwendigen java-Dateien damit sie auch hochgeladen werden als .txt "getarnt" :-D

Falls noch irgendwas fehlen sollte, um es benutzen zu können, wäre ich für feedback dankbar.

vielleicht gibt es irgendwann noch die Einbettung der Autocounter (laufenden Nummern).

Takidoso

Nachtrag zum besseren Nachvollziehen: ich habe die Anwendung die eine Datei einliest und in etwas anderes konvertiert folgenden Eingang als inputfilename:
090206.090107.sie.A001OAIL.dta128
und folgendes als Log-Dateiname:
090206.2009-03-06_18-47-34-980.090107.sie.A001OAIL.log
 

Anhänge

Zuletzt bearbeitet von einem Moderator:
Wie versprochen dann doch noch eine Version, die laufende Nummern im Log-Dateinamen einbeziehen kann.

XML-Konfigurationsbeispiel:
XML:
<?xml version="1.0" encoding="UTF-8" ?> 
<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd"> 
<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/"> 
<appender name="jdtaconv" class="de.cmk.log4j.NameComposingFileAppender"> 
        <param name="string4Construction" value="${inputfilename}"></param>        
        <param name="inputRegex" value="([\\w[\\-]]*)\.([\\w[\\-]]*)\.([\\w[\\-]]*)\.([\\w[\\-]]*)\.(.*)"></param>
        <param name="autoCounters" 
               value="Name=sqn01;FileName=sqn01.ac;FirstValue=2;LastValue=10;Increment=4;ResetEachDay=FALSE;Cycle=TRUE;FileAutoCreation=TRUE
                    ##Name=sqn02;FileName=sqn02.ac;FirstValue=1;LastValue=10;Increment=3;ResetEachDay=FALSE;Cycle=TRUE;FileAutoCreation=TRUE"></param>
        <param name="file" value="logs/${user.name}/(1).{yyyy-MM-dd_HH-mm-ss-SSS}.(2).(3).(4).&lt;sqn01:000&gt;.&lt;sqn02:0000&gt;.log" ></param> 
        <param name="Append" value="false" /> 
        <layout class="org.apache.log4j.PatternLayout"> 
                <param name="ConversionPattern" 
                        value="%d{ISO8601} %-5p %m%n" /> 
        </layout> 
</appender> 

<category name="de.tai.jdtatool2"> 
        <priority value="TRACE" ></priority> 
        <appender-ref ref="jdtaconv" /> 
</category> 

</log4j:configuration>

Hier noch den Sourcecode des FileAppenders
Java:
package de.cmk.log4j;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;

import org.apache.log4j.FileAppender;

import de.cmk.util.AutoCounter;
import de.cmk.util.generate.StringComposer;


public class NameComposingFileAppender extends FileAppender
{
	private String m_inputRegex       = null;
	private String m_str4Constr       = null;
	private Map    m_autoCounterMap   = new HashMap();
	
	public void activateOptions() 
	{
		
		if (m_inputRegex==null)
		{
			StringComposer strComp = new StringComposer(new HashMap(), fileName);
			fileName = strComp.constructString();
		}
		else if (m_str4Constr==null)
		{
			errorHandler.error("String4Construction-Property has to be given when InputRegex are set!");
		}
		else
		{
			StringComposer strComp = new StringComposer(m_autoCounterMap,
														m_inputRegex,
														m_str4Constr,
														fileName);
			fileName = strComp.constructString();
		}
		
		super.activateOptions();
	}
	
	public void setString4Construction(String str4Constr)
	{
		m_str4Constr = str4Constr;
	}
	
	public void setInputRegex(String inputRegex)
	{
		m_inputRegex = inputRegex;
	}
	
	public void setAutoCounters(String autoCountersDefs)
	{
		//Trennung der Autocounterdefinitionen von einander Delimeter sei  "##"
		String[] acPropStrs = autoCountersDefs.split("#{2}");
		for (int i=0; i< acPropStrs.length; i++)
		{
			//Trennung der Properties eines Autocounters Delimeter sei ";"
			String propDefsStr = acPropStrs[i].trim().replaceAll(";", "\n");
			Properties props = new Properties();
			try
			{
				// Erstellen der Properties und instanziieren des Autocounters
				props.load(new ByteArrayInputStream(propDefsStr.getBytes()));
				AutoCounter ac = new AutoCounter(props);
				m_autoCounterMap.put(ac.getName(), ac);
			}
			catch (IOException ioEx)
			{
				throw new RuntimeException(ioEx);
			}
		}
	}
}
Außerdem hate ich auf diese Weise noch einen Fehler in der AutoCounter-Klasse entdeckt anbei als TXT "getarnt" die korrigierte AutoCounter-Klasse
 

Anhänge

Zuletzt bearbeitet von einem Moderator:

Neue Beiträge

Zurück