#region Apache License // // Licensed to the Apache Software Foundation (ASF) under one or more // contributor license agreements. See the NOTICE file distributed with // this work for additional information regarding copyright ownership. // The ASF licenses this file to you under the Apache License, Version 2.0 // (the "License"); you may not use this file except in compliance with // the License. You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // #endregion using System; using System.Collections; #if NETCF_1_0 using Stack = log4net.Util.ThreadContextStack.Stack; #endif namespace log4net { /// /// Implementation of Nested Diagnostic Contexts. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// A Nested Diagnostic Context, or NDC in short, is an instrument /// to distinguish interleaved log output from different sources. Log /// output is typically interleaved when a server handles multiple /// clients near-simultaneously. /// /// /// Interleaved log output can still be meaningful if each log entry /// from different contexts had a distinctive stamp. This is where NDCs /// come into play. /// /// /// Note that NDCs are managed on a per thread basis. The NDC class /// is made up of static methods that operate on the context of the /// calling thread. /// /// /// How to push a message into the context /// /// using(NDC.Push("my context message")) /// { /// ... all log calls will have 'my context message' included ... /// /// } // at the end of the using block the message is automatically removed /// /// /// /// Nicko Cadell /// Gert Driesen /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public sealed class NDC { #region Private Instance Constructors /// /// Initializes a new instance of the class. /// /// /// Uses a private access modifier to prevent instantiation of this class. /// private NDC() { } #endregion Private Instance Constructors #region Public Static Properties /// /// Gets the current context depth. /// /// The current context depth. /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// The number of context values pushed onto the context stack. /// /// /// Used to record the current depth of the context. This can then /// be restored using the method. /// /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static int Depth { get { return ThreadContext.Stacks["NDC"].Count; } } #endregion Public Static Properties #region Public Static Methods /// /// Clears all the contextual information held on the current thread. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// Clears the stack of NDC data held on the current thread. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static void Clear() { ThreadContext.Stacks["NDC"].Clear(); } /// /// Creates a clone of the stack of context information. /// /// A clone of the context info for this thread. /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// The results of this method can be passed to the /// method to allow child threads to inherit the context of their /// parent thread. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static Stack CloneStack() { return ThreadContext.Stacks["NDC"].InternalStack; } /// /// Inherits the contextual information from another thread. /// /// The context stack to inherit. /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// This thread will use the context information from the stack /// supplied. This can be used to initialize child threads with /// the same contextual information as their parent threads. These /// contexts will NOT be shared. Any further contexts that /// are pushed onto the stack will not be visible to the other. /// Call to obtain a stack to pass to /// this method. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks", true)]*/ public static void Inherit(Stack stack) { ThreadContext.Stacks["NDC"].InternalStack = stack; } /// /// Removes the top context from the stack. /// /// /// The message in the context that was removed from the top /// of the stack. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// Remove the top context from the stack, and return /// it to the caller. If the stack is empty then an /// empty string (not null) is returned. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static string Pop() { return ThreadContext.Stacks["NDC"].Pop(); } /// /// Pushes a new context message. /// /// The new context message. /// /// An that can be used to clean up /// the context stack. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// Pushes a new context onto the context stack. An /// is returned that can be used to clean up the context stack. This /// can be easily combined with the using keyword to scope the /// context. /// /// /// Simple example of using the Push method with the using keyword. /// /// using(log4net.NDC.Push("NDC_Message")) /// { /// log.Warn("This should have an NDC message"); /// } /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static IDisposable Push(string message) { return ThreadContext.Stacks["NDC"].Push(message); } /// /// Pushes a new context message. /// /// The new context message string format. /// Arguments to be passed into messageFormat. /// /// An that can be used to clean up /// the context stack. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// Pushes a new context onto the context stack. An /// is returned that can be used to clean up the context stack. This /// can be easily combined with the using keyword to scope the /// context. /// /// /// Simple example of using the Push method with the using keyword. /// /// var someValue = "ExampleContext" /// using(log4net.NDC.PushFormat("NDC_Message {0}", someValue)) /// { /// log.Warn("This should have an NDC message"); /// } /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static IDisposable PushFormat(string messageFormat, params object[] args) { return Push(string.Format(messageFormat, args)); } /// /// Removes the context information for this thread. It is /// not required to call this method. /// /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// This method is not implemented. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static void Remove() { } /// /// Forces the stack depth to be at most . /// /// The maximum depth of the stack /// /// /// /// The NDC is deprecated and has been replaced by the . /// The current NDC implementation forwards to the ThreadContext.Stacks["NDC"]. /// /// /// /// Forces the stack depth to be at most . /// This may truncate the head of the stack. This only affects the /// stack in the current thread. Also it does not prevent it from /// growing, it only sets the maximum depth at the time of the /// call. This can be used to return to a known context depth. /// /// /*[Obsolete("NDC has been replaced by ThreadContext.Stacks")]*/ public static void SetMaxDepth(int maxDepth) { if (maxDepth >= 0) { log4net.Util.ThreadContextStack stack = ThreadContext.Stacks["NDC"]; if (maxDepth == 0) { stack.Clear(); } else { while(stack.Count > maxDepth) { stack.Pop(); } } } } #endregion Public Static Methods } }