我最近遇到了ASP.net vnext的AssemblyNeutral
属性。
如果我必须具体,那么您将在Logging资源库中找到该属性用法。 https://github.com/aspnet/logging
还有许多其他存储库,但这很简单。
现在根据许多博客,如果我们使用AssemblyNeutral
属性,那么该接口或类型不与程序集绑定,因此我们可以在其他需要相同合同的框架中使用AssemblyNeutral
属性定义相同的接口。
所以创建示例我在ASP.net vnext类库项目中创建了自己的小型记录器库但它给了我类型转换错误。
namespace MyLogger
{
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILogger
{
void Write(LogLevel logLevel, int eventId, object state, Exception exception, Func<object, Exception, string> formatter);
bool IsEnabled(LogLevel logLevel);
IDisposable BeginScope(object state);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILoggerFactory
{
ILogger Create(string name);
void AddProvider(ILoggerProvider provider);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILoggerProvider
{
ILogger Create(string name);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public enum LogLevel
{
Verbose = 1,
Information = 2,
Warning = 3,
Error = 4,
Critical = 5,
}
public class MyLogger : ILogger
{
public IDisposable BeginScope(object state)
{
return null;
}
public bool IsEnabled(LogLevel logLevel)
{
return true;
}
public void Write(LogLevel logLevel, int eventId, object state, Exception exception, Func<object, Exception, string> formatter)
{
System.IO.File.AppendAllText("C:\\Testlog.txt", "This is test log" + System.Environment.NewLine);
}
}
public class MyLoggerProvider : ILoggerProvider
{
private readonly Func<string, LogLevel, bool> _filter;
public MyLoggerProvider(Func<string, LogLevel, bool> filter)
{
_filter = filter;
}
public ILogger Create(string name)
{
return new MyLogger();
}
}
public static class MyLoggerExtentions
{
public static ILoggerFactory AddMyLogger(this ILoggerFactory factory, Func<string, LogLevel, bool> filter)
{
factory.AddProvider(new MyLoggerProvider(filter));
return factory;
}
}
}
现在我尝试在SampleApp(Logging Repository SampleApp)中使用。你可以看到它给了我Cast Error。为什么这样 ?
答案 0 :(得分:0)
IDE尚未正确处理源中定义的程序集中性接口。这就是你看到错误的原因。
答案 1 :(得分:0)
我部分同意Visual Studio 2015 Preview IDE不支持AssemlbyNeutral属性,但问题出在其他地方。
实际上,当我们在自定义程序集中再次定义Interface或Type时,如果我们希望它支持AssemblyNeutral,那么它必须具有与原始接口相同的名称空间。
在我的示例中,我通过将接口放入New Namespace来做错了。
我已更新代码,然后我在Visual Studio 2015中构建预览它编译甚至正确执行。
所以要记住的主要事情是&#34;将程序集中性接口和类型放在原始程序集所在的相同名称空间中,并且#34;。
以下是更新的代码。
namespace Microsoft.Framework.Logging
{
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILogger
{
void Write(LogLevel logLevel, int eventId, object state, Exception exception, Func<object, Exception, string> formatter);
bool IsEnabled(LogLevel logLevel);
IDisposable BeginScope(object state);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILoggerFactory
{
ILogger Create(string name);
void AddProvider(ILoggerProvider provider);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public interface ILoggerProvider
{
ILogger Create(string name);
}
#if ASPNET50 || ASPNETCORE50
[Microsoft.Framework.Runtime.AssemblyNeutral]
#endif
public enum LogLevel
{
Verbose = 1,
Information = 2,
Warning = 3,
Error = 4,
Critical = 5,
}
}
namespace MyLogger
{
public class MyLogger : ILogger
{
public IDisposable BeginScope(object state)
{
return null;
}
public bool IsEnabled(LogLevel logLevel)
{
return true;
}
public void Write(LogLevel logLevel, int eventId, object state, Exception exception, Func<object, Exception, string> formatter)
{
System.IO.File.AppendAllText("C:\\Testlog.txt", "This is test log" + System.Environment.NewLine);
}
}
public class MyLoggerProvider : ILoggerProvider
{
private readonly Func<string, LogLevel, bool> _filter;
public MyLoggerProvider(Func<string, LogLevel, bool> filter)
{
_filter = filter;
}
public ILogger Create(string name)
{
return new MyLogger();
}
}
public static class MyLoggerExtentions
{
public static ILoggerFactory AddMyLogger(this ILoggerFactory factory, Func<string, LogLevel, bool> filter)
{
factory.AddProvider(new MyLoggerProvider(filter));
return factory;
}
}
}