Good morning
Yesterday it became quite late and I had not the mental force to write down my vision of the RFA reimplementation: The log filename should be determined dynamically to allow users including information like %date, %time in the filename. It has often been requested and up to now it is supported only marginally. Another issue that I just remembered now is that currently there's no way to roll empty files on date/time boundaries. Rolling only happens when a log event is generated. If there's no log event, files won't be rolled. Thus we should investigate if we should implement the appender as a buffering async appender that does the rolling in his async work cycles and whose work cycles do not depend on the availability of log events. Futher, the rolling file appender should probably receive a persistent storage where he can keep a set of rolled files he has rolled in the past. This way we eliminate the dark magic behind detecting rolled files. It allows the user also to modify or mix the rolling strategies and/or rolling filename configuration from one instance to the next. The persistence will have to include a set of filenames. It would probably be nice to allow people configuring a relative filepath that will be stripped from the filenames. Otherwise we would break the usecase where a user moves an application from, let's say, drive C: to drive D: along with all logfiles because the rolled filenames would no longer be found and some files would become zombies that pollute the drive. Thus a persistable rolling history class could look alike: Public class RollingHistory { Public List<string> Files { get; } } To exchange information between the rolling strategies, rolling conditions and the rolling file appender itself we should probably use a data class. The name of it could be "RollingContext" and basically could be implemented like: public class RollingContext { public RollingHistory RollingHistory { get; } public string Logfile { get; } public long CurrentLogfileSize { get; } } That means that a rolling strategy could be an interface like: public interface RollingStrategy { public void DoRolling(RollingContext context); } which either throws exceptions on failure or returns true|false to notify the caller that something went wrong and log the errors into the log4net internal debug log. The next topic is the rolling condition. The rolling condition decides if rolling should be done right now. Thus its interface should be something like: public interface IRollingCondition { public bool IsRollingConditionMet(RollingContext context); } Concrete rolling conditions could be: * Roll if filesize exceeds a specific limit * Roll if a specific date/time condition is met ==> this is already kind of supported with an implementation of a "cron"-like syntax Making the rolling condition pluggable would greatly benefit others to invent their own rolling conditions. For example an implementation of IRollingCondition like: public class ManualRollingCondition implements IRollingCondition { public static bool RollOnNextCycle = false; public bool IsRollingConditionMet(RollingContext context) { if(RollOnNextCycle) { // reset roll on next cycle RollOnNextCycle = false; return true; } return false; } } could let the application that uses log4net decide when a file should be rolled by a simple invoke to: ManualRollingCondition.RollOnNextCycle=true; And now we come to the disposal of old files. Since we have a persistent set of old files we should pass it into the disposing logic and the interface to it could look like: Public interface IDisposeStrategy { Public bool DoDisposal(RollingContext context); } And a concrete implementation of it could be: Public class LimitNumberOfFilesDisposeStrategy implements IDisposeStrategy { Public int MaxNumberOfFiles { get; set; } Public bool DoDisposal(RollingContext context) { // delete all files in history While(MaxNumberOfFiles < Context.RollingHistory.Count) { If(Context.RollingHistory.Count == 0) Return true; // delete oldest file and persist the history // let it crash if someone has a logfile open and locked // and let the invoker decide if he wants to retry later Try { Delete(Context.RollingHistory.Oldest()); Context.RollingHistory.Remove(Context.RollingHistory.Oldest()); Context.RollingHistory.Persist(); } Catch // internal logging Return false; } Return true; } } Some of the ideas above are already implemented in the patch, but there are several things that are not yet finished. Von: Dominik Psenner [mailto:dpsen...@gmail.com] Gesendet: Sonntag, 11. August 2013 22:59 An: Log4NET Dev Betreff: Re: Creating a development environment for resolving LOG4NET-367 This is something that wouldn't work right now: <appender> <rollingfileappender> <filename>C:/fancydirectory/%processid/%username/%year/%month/mylogfile.log< /filename> <locking>inter-process</locking> <rollOn><date where="hour%3==0" /></rollOn> <rollTo>C:/fancydirectory/%processid/%username/%year/%month/%filenumber/mylo gfile.log</rollTo> <dispose><files where="filenumber > 50" /></dispose> </rollingfileappender> </appender> but we want it to work in the future. Of couse the syntax may be different, but it should be easy enough to write down how the RFA has to behave. Right now there are too many fancy flicks and switches that do things magically. Cheers 2013/8/11 Dominik Psenner <dpsen...@gmail.com <mailto:dpsen...@gmail.com> > See the inlines.. 2013/8/10 d_k <mail...@gmail.com <mailto:mail...@gmail.com> > Paperizing ideas sounds good. How does the log4net project handle requirements? JIRA? Yes Are there any requirements other than the ones under the 'supercedes' list? Yes and no. It should be a rolling file appender that handles things smarter than the current one. If there are ideas they are welcome. It should roll files (obvious) on "rolling conditions" with a "rolling strategy" and dispose old files with a "dispose strategy". The rolling condition, rolling strategy and dispose strategy should be pluggable and configurable (i.e. they are interfaces that can be implemented in different ways). It should support dynamic filenames that may change over time It should support changes to the rolling strategy in respect of disposal of old files (i.e. between process instances). It should support all currently supported locking strategies. For now I can't think of more. I'm afraid I don't have a 'vision' for the RFA-NG but I think we can take the patch under log4net-patches, make sure to fix the 'supercedes' list and off we go. I wouldn't want to spend time on a grand design because we can't tell how long will it take, and I think it is better to ship a less than perfect RFA-NG and fix it later on when we'll know what we want than to postpone the next release indefinitely. We have a RFA that does not what we want. We don't need another one. If we reimplement it now and release it, we have another RFA with a public api we do not want to change - sounds familiar. BTW, no offense, but is there a chance it will be easier to fix the current RFA than to rewrite it? There are things that are unfixable with the current implementation without breaking the public API and that's something we dont want. Is there a way to measure a given implementation of any RFA to determine if its good enough? It's good enough when it boils eggs and toast my bread .. just joking. ;-) It's good enough when it does what we want from it. On Fri, Aug 9, 2013 at 8:00 PM, Dominik Psenner <dpsen...@gmail.com <mailto:dpsen...@gmail.com> > wrote: Howdie, the patch there is mainly a first implementation showing the road we would like to go. There are many things to be discussed and I would start with paperizing the ideas before starting the implementation. The reimplementation should solve all known current issues of the rolling file appender. The patches repository is nothing else than a repository that holds patches that can be applied to the log4net source, which is located at apache.org <http://apache.org> 's svn. It's there to materialize the ideas without requiring write permissions to the actual svn and can be used as a sandbox to play with ideas. I started off with an implementation as a patch and wanted to improve that patch until it is stable enough to join the log4net appenders in svn. Cheers 2013/8/9 d_k <mail...@gmail.com <mailto:mail...@gmail.com> > Hi, So I think I got a working development environment for log4net. I installed mercurial and forked the log4net-crew repository (https://bitbucket.org/NachbarsLumpi/log4net-crew) and the log4net-patches repository (https://bitbucket.org/NachbarsLumpi/log4net-patches) and applied the RFA-NG patch with 'hg import'. Should I prefer to use http://svn.apache.org/viewvc/logging/log4net/trunk over https://bitbucket.org/NachbarsLumpi/log4net-crew? Will svn and mercurial coexist peacefully? Do I need anything else to start developing? Should I create my own RFA-NG2 patch? Or perhaps RFA-NG-NNN for each bug in the supercedes list of LOG4NET-367 (https://issues.apache.org/jira/browse/LOG4NET-367)? Are there any common pitfalls I should avoid? -- Dominik Psenner ## OpenPGP Key Signature ################################# # Key ID: B469318C # # Fingerprint: 558641995F7EC2D251354C3A49C7E3D1B469318C # ########################################################## -- Dominik Psenner ## OpenPGP Key Signature ################################# # Key ID: B469318C # # Fingerprint: 558641995F7EC2D251354C3A49C7E3D1B469318C # ########################################################## -- Dominik Psenner ## OpenPGP Key Signature ################################# # Key ID: B469318C # # Fingerprint: 558641995F7EC2D251354C3A49C7E3D1B469318C # ##########################################################