因为工作需要需要在XP上运行一个C#编写的Winform插件,我就用Framework2.0,因为存在接口交互所以想保留交易过程的入参出参。

考虑到插件本身实施的因素,就没有使用Log4、NLog等成熟的日志插件。在网上搜索了一个是通过TextWriterTraceListener实现的,但是实际使用

过程中发现并没实现我想要的功能,于是乎自己重新造了个轮子,如果大家有需要可以参考下。

   /// <summary>
/// 日志类型
/// </summary>
public enum LogType
{
Error,
Trace,
Info
} /// <summary>
/// 日志类
/// 支持同步和异步
/// </summary>
public sealed class Logger
{ #region 变量|常量 /// <summary>
/// 用于Trace的组织输出的类别名称
/// </summary>
private const string error = "\r\n***********************EXCEPTION {0}***********************"; /// <summary>
/// 跟踪
/// </summary>
private const string trace = "\r\n*************************TRACE {0}*******************************"; /// <summary>
/// 信息
/// </summary>
private const string info = "\r\n****************************INFO {0}********************************"; /// <summary>
/// 1 仅控制台输出
/// 2 仅日志输出
/// 3 控制台+日志输出
/// </summary>
private static readonly int flag = ; //可以修改成从配置文件读取 #endregion #region 委托 private delegate void AsyncLogException(Exception ex);
private delegate void AyyncLog(string msg, LogType type);
private delegate void AsyncLogSqlCommand(SqlCommand cmd);
private delegate void AsyncLogSql(string sql, params SqlParameter[] parameter); private static void BeginError(Exception ex)
{
if (null != ex)
{
string path = GetLogPath(LogType.Error);
//输出日志头
WriteLog(path, string.Format(error, DateTime.Now));
while (null != ex)
{
WriteLog(path, string.Format("{0} {1}\r\n{2}\r\nSource:{3}", ex.GetType().Name, ex.Message, ex.StackTrace, ex.Source));
ex = ex.InnerException;
}
}
} private static void BeginTrace(string msg, LogType type)
{
if (string.IsNullOrEmpty(msg)) return;
string path = GetLogPath(type);
//输出日志头
WriteLog(path, string.Format(trace, DateTime.Now));
//输出日志内容
WriteLog(path, msg);
}
#endregion #region IO操作
/// <summary>
/// 获取日志类型对应的日志存储环境
/// </summary>
/// <param name="type">日志类型</param>
/// <returns></returns>
private static string GetLogPath(LogType type)
{
DateTime time = DateTime.Now;
string subdir = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "logs");
subdir = Path.Combine(subdir, type.ToString());
subdir = Path.Combine(subdir, time.ToString("yyyyMM"));
if (!Directory.Exists(subdir))
{
Directory.CreateDirectory(subdir);
}
string result = Path.Combine(subdir, time.ToString("yyyyMMdd") + ".log");
return result;
} /// <summary>
/// 写入日志
/// </summary>
/// <param name="path">日志环境</param>
/// <param name="text">写入的文本值</param>
private static void WriteLog(string path, string text)
{
string filePath = Path.GetDirectoryName(path);
if (Directory.Exists(filePath) == false)
{
Directory.CreateDirectory(filePath);
}
if (File.Exists(path))
{
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine(text + "\n");
sw.Flush();
sw.Close();
}
}
else
{
StreamWriter sr = File.CreateText(path);
sr.WriteLine(text + "\n");
sr.Flush();
sr.Close();
}
}
#endregion #region 发布的方法
/// <summary>
/// 写入异常日志
/// </summary>
/// <param name="ex">异常对象</param>
/// <param name="isAsync">是否异步,默认异步</param>
public static void Error(Exception ex, bool isAsync = true)
{
if (isAsync)
new AsyncLogException(BeginError).BeginInvoke(ex, null, null);
else
BeginError(ex);
} /// <summary>
/// 写入错误日志
/// </summary>
/// <param name="msg">错误信息</param>
/// <param name="isAsync">是否异步,默认异步</param>
public static void Error(string msg, bool isAsync = false)
{
if (isAsync)
new AyyncLog(BeginTrace).BeginInvoke(msg, LogType.Error, null, null);
else
BeginTrace(msg, LogType.Error);
} /// <summary>
/// 异步跟踪日志
/// </summary>
/// <param name="msg"></param>
public static void Trace(string msg, bool isAsync = true)
{
if (isAsync)
new AyyncLog(BeginTrace).BeginInvoke(msg, LogType.Trace, null, null);
else
BeginTrace(msg, LogType.Trace);
} /// <summary>
/// 写入日志信息,日志类型为info
/// </summary>
/// <param name="msg">日志信息</param>
/// <param name="isAsync">是否异步,默认异步</param>
public static void Info(string msg, bool isAsync = true)
{
if (isAsync)
new AyyncLog(BeginTrace).BeginInvoke(msg, LogType.Info, null, null);
else
BeginTrace(msg, LogType.Info);
}
#endregion }
}

调用代码:

private void button1_Click_1(object sender, EventArgs e)
{
Logger.Info("测试");
}

运行效果如下:

支持异步写入的日志类,支持Framework2.0的更多相关文章

  1. C#写文本日志帮助类(支持多线程)

    代码: using System; using System.Configuration; using System.IO; using System.Threading.Tasks; namespa ...

  2. python日志,支持彩色打印和文件大小切片写入和写入mongodb

    1.项目中使用了自定义的ColorHandler和MongoHandler,使用了内置的RotatingFileHandler和三方库的ConcurrentRotatingFileHandler. 支 ...

  3. Android开发调试日志工具类[支持保存到SD卡]

    直接上代码: package com.example.callstatus; import java.io.File; import java.io.FileWriter; import java.i ...

  4. C#写文本日志帮助类(支持多线程)改进版(不适用于ASP.NET程序)

    由于iis的自动回收机制,不适用于ASP.NET程序 代码: using System; using System.Collections.Concurrent; using System.Confi ...

  5. BAE3.0还不支持本地写入文件

    BAE3.0对比2.0做了很大的改动,对于安装应用方面也方便了很多,普通的应用表面上(下文就是讲为什么说表面上)不需要做什么适配.比如wp博客,直接修改wp-config.php,把数据库信息填一下就 ...

  6. TNetHttpClient支持异步访问(Delphi 10.1 Berlin,红鱼儿的博客)

    Delphi 10.1进一步改进自Delphi 10带来的Http访问控件TNetHttpClient,支持异步访问,同时增加ConnectionTimeout及ResponseTimeout两个超时 ...

  7. 支持异步同步的分布式CommandBus MSMQ实现

    支持异步同步的分布式CommandBus MSMQ实现 先上一张本文所描述的适用场景图 分布式场景,共3台server: 前端Server Order App Server Warehouse App ...

  8. LogStation 支持浏览器实时查看日志

    我们在logback 分布式日志汇总中已经将日志输出到了all.logs,LogStation支持浏览器实时查看日志,适合研发和运维彼此独立的场景:研发没有服务器权限,却想看日志实时输出.再配合ngi ...

  9. Java - IO System类支持和缓冲流

    System类的支持和缓冲流 System类对IO的支持 在System类中,为了支持IO操作提供了三个常量: 错误输出: public static final PrintStream err; 输 ...

随机推荐

  1. BZOJ 4710

    枚举几个同学分到了 对于每种特产求一个方案数(经典做法)乘起来 然后容斥 #include<bits/stdc++.h> using namespace std; #define rep( ...

  2. 数据分析——pandas

    简介 import pandas as pd # 在数据挖掘前一个数据分析.筛选.清理的多功能工具 ''' pandas 可以读入excel.csv等文件:可以创建Series序列,DataFrame ...

  3. QT—QTextEdit控件显示日志

    功能:利用QTextEdit开发一个日志显示窗口.没有太多操作,需要实现的是日志自动向上滚动,总体的日志量可以控制在x行(比如300行)以内:其他的应用功能我后面继续添加 #include <Q ...

  4. 二维数组的最大子数组和 时间复杂度:O(n的四次方)

    先上代码 小组成员:高达,李奔 package 三月二十一号; import java.io.BufferedReader; import java.io.FileReader; import jav ...

  5. [LeetCode] Buddy Strings 伙计字符串

    Given two strings A and B of lowercase letters, return true if and only if we can swap two letters i ...

  6. 11、js 数组详细操作方法及解析合集

    js 数组详细操作方法及解析合集 前言 在开发中,数组的使用场景非常多,平日中也涉及到很多数组的api/相关操作,一直也没有对这块内容进行一块整理总结,很多时候就算用过几次这个api,在开发中也很容易 ...

  7. [微信小程序]编译.wxss出错,2 not found

    小程序新建项目就出错:2 not found  编译.wxss文件出错(不是一般的郁闷,新建项目就报错...) 大概的情况是开发工具没有更新.或更新不到, 第一,可以删掉开发工具重新下载最新安装: 第 ...

  8. 梯度提升决策树(GBDT)

    1.提升树 以决策树为基函数的提升方法称为提升树.决策树可以分为分类树和回归树.提升树模型可以表示为决策树的加法模型. 针对不同的问题的提升术算法的主要区别就是损失函数的不同,对于回归问题我们选用平方 ...

  9. 权限系统设计-day02

    练习中的问题: 1,<s:url action="employee_input" />这个标签用来让struts自动生成请求的路径,struts生成的路径是一个全路径, ...

  10. HTML标题 段落 样式

    HTML 标题 标题(Heading)是通过 <h1> - <h6> 等标签进行定义的. <h1> 定义最大的标题.<h6> 定义最小的标题. 注释:默 ...