代码之家  ›  专栏  ›  技术社区  ›  Aaron Weiker

Silverlight日志框架和/或最佳实践

  •  25
  • Aaron Weiker  · 技术社区  · 17 年前

    现在Silverlight 2终于发布了。我想知道是否有人为它准备了日志框架,也许是这样的 enterprise library logging log4net ? 我感兴趣的是可以执行客户端跟踪并将消息记录到服务器的东西。

    到目前为止,我找到的唯一项目是 Clog 在…上 CodeProject

    6 回复  |  直到 15 年前
        1
  •  14
  •   Chris S    16 年前

    如果您愿意摘下宇航员的头盔一分钟,下面是我为Silverlight编写的一个轻型记录器,用于客户端日志记录(主要用于WCF操作,但可能用于任何错误)。

    它最初用于iPhone应用程序的Monotouch,并已被改编为 IsolateStorage Read 方法在需要时显示在文本框中。在SL4中测试。

    /// <summary>
    /// A lightweight logging class for Silverlight.
    /// </summary>
    public class Log
    {
        /// <summary>
        /// The log file to write to. Defaults to "dd-mm-yyyy.log" e.g. "13-01-2010.log"
        /// </summary>
        public static string LogFilename { get; set; }
    
        /// <summary>
        /// Whether to appendthe calling method to the start of the log line.
        /// </summary>
        public static bool UseStackFrame { get; set; }
    
        static Log()
        {
            LogFilename = string.Format("{0}.log", DateTime.Today.ToString("dd-MM-yyyy"));
            UseStackFrame = false;
        }
    
        /// <summary>
        /// Reads the entire log file, or returns an empty string if it doesn't exist yet.
        /// </summary>
        /// <returns></returns>
        public static string ReadLog()
        {
            string result = "";
            IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForSite();
    
            if (storage.FileExists(LogFilename))
            {
                try
                {
                    using (IsolatedStorageFileStream stream = new IsolatedStorageFileStream(LogFilename,FileMode.OpenOrCreate,storage))
                    {
                        using (StreamReader reader = new StreamReader(stream))
                        {
                            result = reader.ReadToEnd();
                        }
                    }
                }
                catch (IOException)
                {
                    // Ignore
                }
            }
    
            return result;
        }
    
        /// <summary>
        /// Writes information (not errors) to the log file.
        /// </summary>
        /// <param name="format">A format string</param>
        /// <param name="args">Any arguments for the format string.</param>
        public static void Info(string format, params object[] args)
        {
            WriteLine(LoggingLevel.Info, format, args);
        }
    
        /// <summary>
        /// Writes a warning (non critical error) to the log file
        /// </summary>
        /// <param name="format">A format string</param>
        /// <param name="args">Any arguments for the format string.</param>
        public static void Warn(string format, params object[] args)
        {
            WriteLine(LoggingLevel.Warn, format, args);
        }
    
        /// <summary>
        /// Writes a critical or fatal error to the log file.
        /// </summary>
        /// <param name="format">A format string</param>
        /// <param name="args">Any arguments for the format string.</param>
        public static void Fatal(string format, params object[] args)
        {
            WriteLine(LoggingLevel.Fatal, format, args);
        }
    
        /// <summary>
        /// Writes the args to the default logging output using the format provided.
        /// </summary>
        public static void WriteLine(LoggingLevel level, string format, params object[] args)
        {
            string message = string.Format(format, args);
    
            // Optionally show the calling method
            if (UseStackFrame)
            {
                var name = new StackFrame(2, false).GetMethod().Name;
    
                string prefix = string.Format("[{0} - {1}] ", level, name);
                message = string.Format(prefix + format, args);
            }
    
            Debug.WriteLine(message);
            WriteToFile(message);
        }
    
        /// <summary>
        /// Writes a line to the current log file.
        /// </summary>
        /// <param name="message"></param>
        private static void WriteToFile(string message)
        {
            try
            {
                IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForSite();
                bool b = storage.FileExists(LogFilename);
    
                using (IsolatedStorageFileStream stream = new IsolatedStorageFileStream(LogFilename,FileMode.Append,storage))
                {
                    using (StreamWriter writer = new StreamWriter(stream))
                    {
                        writer.WriteLine("[{0}] {1}", DateTime.UtcNow.ToString(), message);
                    }
                }
            }
            catch (IOException)
            {
                // throw new Catch22Exception();
            }
        }
    }
    
    /// <summary>
    /// The type of error to log.
    /// </summary>
    public enum LoggingLevel
    {
        /// <summary>
        /// A message containing information only.
        /// </summary>
        Info,
        /// <summary>
        /// A non-critical warning error message.
        /// </summary>
        Warn,
        /// <summary>
        /// A fatal error message.
        /// </summary>
        Fatal
    }
    
        2
  •  6
  •   Kiquenet user385990    10 年前

    my blog .

        // http://kodierer.blogspot.com.es/2009/05/silverlight-logging-extension-method.html
        public static string Log(string message)
        {
            var msgLog = "";
            try
            {
    
                HtmlWindow window = HtmlPage.Window;
    
                //only log if a console is available
                var isConsoleAvailable = (bool)window.Eval("typeof(console) != 'undefined' && typeof(console.log) != 'undefined'");
    
                if (!isConsoleAvailable) return "isConsoleAvailable " + isConsoleAvailable;
    
                var createLogFunction = (bool)window.Eval("typeof(ssplog) == 'undefined'");
                if (createLogFunction)
                {
                    // Load the logging function into global scope:
                    string logFunction = @"function ssplog(msg) { console.log(msg); }";
                    string code = string.Format(@"if(window.execScript) {{ window.execScript('{0}'); }} else {{ eval.call(null, '{0}'); }}", logFunction);
                    window.Eval(code);
                }
    
                // Prepare the message
                DateTime dateTime = DateTime.Now;
                string output = string.Format("{0} - {1} - {2}", dateTime.ToString("u"), "DEBUG", message);
    
                // Invoke the logging function:
                var logger = window.Eval("ssplog") as ScriptObject;
                logger.InvokeSelf(output);
            }
            catch (Exception ex)
            {
                msgLog = "Error Log " + ex.Message;
            }
            return msgLog;
    
        }
    
        3
  •  4
  •   Craig Nicholson    17 年前

    我以前在完整的.NET框架和Compact框架下使用过非常成功的NLog项目,因此我很可能会使用现有的框架代码并添加一些日志目标:

    • 一个标准系统。诊断目标可以使用DebugView等进行捕获。
    • 具有延迟传输到服务器语义的隔离存储目标。

        4
  •  2
  •   LDuys    15 年前
        5
  •  0
  •   Aaron Weiker    17 年前

    我最终从头开始编写了一个新的日志框架来解决这个缺陷。我创建了一个本地队列,该队列将获取日志/跟踪消息,然后进行筛选并将它们发送到服务器。然后,队列将由独立存储进行备份,因此即使客户端在该会话中永久脱机,消息也将在其重新联机时发送。

        6
  •  0
  •   Robert Fraser    16 年前

    我正在使用JavaScript窗口,并使其可以在Silverlight中编写脚本。对于“生产”,我可以关闭此窗口,但仍将日志行保存到内存中,然后如果出现问题,将其发送到服务器。通过这种方式,我充分利用了这两个方面的优势——简单、实时地记录客户机上的调试日志,以及记录用户可能遇到的远程事后情况。

    推荐文章