2010-01-16 12 views
24

Sto provando a creare una soluzione di registrazione che coinvolge più processi su più macchine. Ho pianificato di utilizzare UDPAppender per inviare tutti i messaggi di registro a una singola macchina che li gestisse. Ho alcune domande su patternstrings vs patternlayouts.informazioni identificativo processo log4

Perché ho bisogno di sapere sia da quale macchina e da quale processo proviene il messaggio di registro, voglio includerlo anche nel registro. Ho trovato% property {log4net: HostName} per hostname, e questo funziona benissimo. Tuttavia, non vedo nulla per ID processo in PatternLayouts. Ovviamente, vedo qualcosa del genere in PatternString. Dalla FAQ:

<appender name="LogFileAppender" type="log4net.Appender.FileAppender"> 
    <file type="log4net.Util.PatternString" value="log-file-[%processid].txt" /> 

    <layout type="log4net.Layout.PatternLayout" value="%date [%thread] %-5level %logger - %message%newline" /> 
</appender> 

Ma io non sono sicuro se o il modo di combinare i due (o anche se questo è il modo canonico di farlo).

Quindi, le mie domande sono:

  1. Qual è la differenza tra stringamodello e PatternLayout? Perché entrambi?

  2. Vedo il% processid in PatternString, come ottengo lo stesso in PatternLayout? Qui è il mio layout di prova:

    <layout type="log4net.Layout.PatternLayout"> 
        <conversionPattern value="%date [%thread] [%property{log4net:HostName}] %-5level %logger - %message%newline" /> 
    </layout> 
    
  3. Infine, ha senso utilizzare il layout XML per l'appender UDP. Sembra che XmlLayoutSchemaLog4j aggiunga già la proprietà HostNameProperty al messaggio XML. Se non dovessi aggiungere questo nuovo Process ID (e forse Process Name) al messaggio XML, qual è il modo migliore per farlo? Dovrei semplicemente copiare src \ Layouts \ XmlLayoutSchemaLog4j.cs, modificarlo e lasciare che log4net sappia che ho creato questo nuovo layout (come SampleLayoutsApp)?

Grazie per il vostro aiuto

risposta

39

È possibile aggiungere qualsiasi proprietà desiderata a GlobalContext.Io uso questo contesto, per memorizzare l'ID di processo, in questo modo:

log4net.GlobalContext.Properties["pid"] = Process.GetCurrentProcess().Id; 

Poi si fa riferimento a questo immobile dal tuo appender utilizzando uno schema regolare, come questo:

<layout type="log4net.Layout.PatternLayout"> 
    <conversionPattern value="%date %property{pid} %level %logger - %message%newline" /> 
</layout> 

È possibile aggiungere tutte le proprietà come vuoi, ma a causa della sua natura globale, funziona meglio per le proprietà che non cambiano durante l'esecuzione dell'applicazione.

+0

Provato di tutto pid%,% processid e molti altri, niente ha funzionato. La tua soluzione funziona. Grazie. – Nemo

3

Apparentemente stringamodello può essere utilizzato solo per creare i nomi di registro (vale a dire i nomi dei file, ecc), mentre il layout consente di formattare il messaggio reale che entra nel registro. Se non esiste un modello predefinito per l'ID del processo nel layout del processo, è possibile aggiungerlo facilmente. È molto più semplice della creazione dell'intero layout.

Ecco come fare:

Crea il tuo convertitore modello personalizzato (ad esempio qui sotto per ottenere il nome dell'applicazione, non importa vincere o web cerca):

internal sealed class ApplicationNamePatternConverter : PatternLayoutConverter 
{ 
    /// <summary> 
    /// Write the event application name to the output 
    override protected void Convert(TextWriter writer, LoggingEvent loggingEvent) 
    { 
     string name = string.Empty; 
     if(System.Web.HttpContext.Current != null) 
     { 
      string[] applicationPath = System.Web.HttpContext.Current.Request.ApplicationPath.Split('/'); 
      name = applicationPath[applicationPath.Length - 1]; 
     } 
     else 
     { 
      if(System.Reflection.Assembly.GetEntryAssembly() != null) 
      { 
       name = System.Reflection.Assembly.GetEntryAssembly().GetName().Name; 
      } 
     } 
     writer.Write(name); 
    } 
} 

aggiungere la voce per il convertitore al registro di classe PatternLayout

static PatternLayout() 
{ 
... 
    s_globalRulesRegistry.Add("ApplicationName", typeof(ApplicationNamePatternConverter)); 
} 

ora che è possibile utilizzare %ApplicationName nel valore PatternLayout per ottenere quello che ti serve.

Consiglio di non utilizzare il layout XmlLayoutSchemaLog4j in quanto è molto pesante e può ridurre le prestazioni della tua app se usato frequentemente.

15

È possibile alimentare uno stringamodello in un PatternLayout:

<layout type="log4net.Layout.PatternLayout"> 
     <conversionPattern type="log4net.Util.PatternString" value="%processid" /> 
    </layout> 
+0

Che ha funzionato davvero. Grazie. –

+3

Ricordarsi di evitare il carattere percentuale delle proprietà che si desidera estrarre dall'evento, ad es. per includere l'ID di processo come uno dei file di registro colonne – Pelle

Problemi correlati