6月 19

.net中的session需要添加引用nuget包

Microsoft.AspNetCore.Session

Session 是基于 IDistributedCache 构建的,所以必须引用一种 IDistributedCache 的实现,ASP.NET Core 提供了多种 IDistributedCache 的实现,如内存、数据库、redis等。所以也需要引用对应的nuget包,一种就可以

Microsoft.Extensions.Caching.Memory
Microsoft.Extensions.Caching.Redis
Microsoft.Extensions.Caching.SqlServer

这里先用最简单的Memory举例

 

添加startup->ConfigureServices

services.AddSession();

添加startup->Configure

app.UseSession();

特别注意:UseSession要在UseMvc之前,否则会有问题

然后在Controller中就可以使用session了

保存session

var b = System.Text.Encoding.UTF8.GetBytes("这个是测试.来自 http://blog.wx6.org");
HttpContext.Session.Set("key", b);

获取session

HttpContext.Session.TryGetValue("key", out byte[] xxx);
var s = System.Text.Encoding.UTF8.GetString(xxx);

这里获取和设置都使用的byte[]类型。这是因为.net core下的session可以远程服务器保存,因此就必须支持序列化。好在微软在Microsoft.AspNet.Http命名空间下,为我们添加了几个扩展方法,分别用于设置和保存byte[]类型、int类型、以及string类型

需要引用nuget包

Microsoft.AspNet.Http.Extensions.dll

  

另外,类库中不能直接使用,需要注入才可以调到,定义方法体如下

public static void Set1(ISession session)
{
    session.SetString("kkk", "dddd");
}

调用方式,是在Controller中调用

Class1.Set1(HttpContext.Session);

 

 

 

写了两个帮助类

    public static class SessionHelper
    { 
        public static void Set(this ISession session, string key, object obj)
        { 
            session.Set(key, ByteHelper.Object2Bytes(obj));
        }
        public static T Get<T>(this ISession session, string key)
        {
            var b = new byte[] { };
            session.TryGetValue(key, out b);
            return ByteHelper.Bytes2Object<T>(b); 
        }
    }

用到的ByteHelper

    public class ByteHelper
    {
        /// <summary>
        /// 将对象转换为byte数组
        /// </summary>
        /// <param name="obj">被转换对象</param>
        /// <returns>转换后byte数组</returns>
        public static byte[] Object2Bytes(object obj)
        {
            string json = JsonConvert.SerializeObject(obj);
            byte[] serializedResult = System.Text.Encoding.UTF8.GetBytes(json);
            return serializedResult;
        }

        /// <summary>
        /// 将byte数组转换成对象
        /// </summary>
        /// <param name="buff">被转换byte数组</param>
        /// <returns>转换完成后的对象</returns>
        public static object Bytes2Object(byte[] buff)
        {
            string json = System.Text.Encoding.UTF8.GetString(buff);
            return JsonConvert.DeserializeObject<object>(json);
        } 

        /// <summary>
        /// 将byte数组转换成对象
        /// </summary>
        /// <param name="buff">被转换byte数组</param>
        /// <returns>转换完成后的对象</returns>
        public static T Bytes2Object<T>(byte[] buff)
        {
            string json = System.Text.Encoding.UTF8.GetString(buff);
            return JsonConvert.DeserializeObject<T>(json);
        }
    }

written by ocean \\ tags:

6月 17

我做东西喜欢从最简单开始。这样方便梳理每个细节。今天弄个.net core的站点试试。

开发工具vs2017,新建项目 .net core 下的 asp.net core web application 

.net framework 选择最高的4.6.1 创建一个空的站点

 

空网站已经引用了两个包

Microsoft.ApplicationInsights.AspNetCore
Microsoft.AspNetCore

删除Startup自带的代码文件只保留两个方法体 ConfigureServices和Configure

 

增加mvc框架支持

添加nuget包引用

Microsoft.AspNetCore.Mvc

添加startup->ConfigureServices

services.AddMvc();

添加startup->Configure

app.UseMvc(routes =>
{
    routes.MapRoute(name: "default", template: "{controller=Home}/{action=Index}");
});

 按照mvc规则给项目添加Controllers和Home文件夹,并且添加简单的action和view。运行即可看到结果。

 

使用Session

比较多,特地重写了一篇

asp.net core中使用session

written by ocean \\ tags: ,

6月 15

appsettings.json

{
  "option1": "value1_from_json",
  "option2": 2,

  "subsection": {
    "suboption1": "subvalue1_from_json"
  },
  "wizards": [
    {
      "Name": "Gandalf",
      "Age": "1000"
    },
    {
      "Name": "Harry",
      "Age": "17"
    }
  ]
}

读取方式

            var builder = new ConfigurationBuilder()
                 .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("appsettings.json");

            Configuration = builder.Build();

            Console.WriteLine($"option1 = {Configuration["option1"]}");
            Console.WriteLine($"option2 = {Configuration["option2"]}");
            Console.WriteLine(
                $"suboption1 = {Configuration["subsection:suboption1"]}");
            Console.WriteLine();

            Console.WriteLine("Wizards:");
            Console.Write($"{Configuration["wizards:0:Name"]}, ");
            Console.WriteLine($"age {Configuration["wizards:0:Age"]}");
            Console.Write($"{Configuration["wizards:1:Name"]}, ");
            Console.WriteLine($"age {Configuration["wizards:1:Age"]}");

需要Nuget引用

Microsoft.Extensions.Configuration
Microsoft.Extensions.Configuration.Binder
Microsoft.Extensions.Configuration.Json

written by ocean \\ tags:

5月 27

log4net不用介绍了,很久以前就在使用了 零配置使用Log4Net

 

确实非常方便,一般小项目都是直接调用就好了,免除了配置的麻烦,直到最近遇到点小麻烦.

在一个站点我需要两个logger实例,记录两种类型的日志,并且把文件也分开到两个地方,但是实际用下来发现无法分离log内容,会有很多重复.

 

查了之后才明白,每个logger都会继承父类的东西,需要设置logger的additivity属性即可,

就像这样.

   <logger name='loggerRoot'  additivity='false'>

 可惜,我翻遍了也没找到可以用code设置additivity的方法.

 

找到配置的初始化方法.

//默认配置,就是把配置写到config文件的那种
public static ICollection Configure();
//配置从一个文件读取
public static ICollection Configure(FileInfo configFile);
//配置从一个流中获取
public static ICollection Configure(Stream configStream);

灵机一动.把配置字符串以流方式传进去实例化,规避配置文件

        static LogHelper()
        { 
            string xml = @"
  <log4net>
   <logger name='loggerRoot'  additivity='false'>
      <level value='ALL' />
      <appender-ref ref='LogAppender' />
    </logger>
   <logger name='loggerExe'  additivity='false'>
      <level value='ALL' />
      <appender-ref ref='LogExeAppender' />
    </logger>
  <appender name='LogAppender' type='log4net.Appender.RollingFileAppender'>
      <param name='File' value='logs/' />
      <param name='AppendToFile' value='true' /> 
      <param name='RollingStyle' value='Date' />
      <param name='DatePattern' value='yyyy.MM.dd"".log""' />
      <param name='StaticLogFileName' value='false' />
      <lockingModel type='log4net.Appender.FileAppender+MinimalLock' />
      <layout type='log4net.Layout.PatternLayout'>
        <param name='ConversionPattern' value='[%d][%p] - %m%n' />
      </layout>
    </appender>
  <appender name='LogExeAppender' type='log4net.Appender.RollingFileAppender'>
      <param name='File' value='logs/visit/' />
      <param name='AppendToFile' value='true' /> 
      <param name='RollingStyle' value='Date' />
      <param name='DatePattern' value='yyyy.MM.dd.HH"".log""' />
      <param name='StaticLogFileName' value='false' />
      <lockingModel type='log4net.Appender.FileAppender+MinimalLock' />
      <layout type='log4net.Layout.PatternLayout'>
        <param name='ConversionPattern' value='[%d][%p] - %m%n' />
      </layout>
    </appender>
  </log4net>
";
            using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(xml)))
            {
                XmlConfigurator.Configure(stream);
            }
            logger = LogManager.GetLogger("loggerRoot");
           
        }
        static log4net.ILog logger = null;

试了一下果然可以了,从此可以以通用的方式定制自己的零配置log组件,太棒了,给自己点个赞

2017.6.21更新

加入asp.net core下的初始化方法

    static LogHelper()
        {
            string xml = @"
  <log4net>
   <logger name='loggerRoot'  additivity='false'>
      <level value='ALL' />
      <appender-ref ref='LogAppender' />
    </logger>
  <appender name='LogAppender' type='log4net.Appender.RollingFileAppender'>
      <param name='File' value='logs/' />
      <param name='AppendToFile' value='true' /> 
      <param name='RollingStyle' value='Date' />
      <param name='DatePattern' value='yyyy.MM.dd"".log""' />
      <param name='StaticLogFileName' value='false' />
      <lockingModel type='log4net.Appender.FileAppender+MinimalLock' />
      <layout type='log4net.Layout.PatternLayout'>
        <param name='ConversionPattern' value='[%d][%p] - %m%n' />
      </layout>
    </appender>
  </log4net>
";

            ILoggerRepository repository = LogManager.CreateRepository("NETCoreRepository");
            using (MemoryStream stream = new MemoryStream(Encoding.UTF8.GetBytes(xml)))
            {               
                XmlConfigurator.Configure(repository, stream);
            }
            logger = LogManager.GetLogger(repository.Name, "loggerRoot");

        }

written by ocean \\ tags: ,