依赖注入已经成为了.net 程序的标配了。 AspectInjector也是支持它的。
public class ConsoleLogger
{
public void Error(string message)
{
Console.WriteLine(message);
}
}
[Injection(typeof(LogAspect))]
public class LogAttribute : Attribute
{
public string Name { get; set; }
}
[Aspect(Scope.PerInstance, Factory = typeof(ApplicationServices))]
public class LogAspect
{
private readonly ConsoleLogger _logger;
public LogAspect(ConsoleLogger logger)
{
_logger = logger;
}
[Advice(Kind.Before)]
public void LogEnter([Argument(Source.Name)] string name, [Argument(Source.Triggers)] Attribute[] attributes)
{
// attribute的值就可以在这边获取到了。
var logAttribute = attributes.FirstOrDefault(it => it is LogAttribute) as LogAttribute;
_logger.Error($"Calling '{name}' method... attributeName:{logAttribute.Name}");
}
}
上面我们有一个 LogAspect用来拦截方法。这个类依赖于ConsoleLogger 这边当然可以换成ILogger之类的。 然后还有一个 LogAttribute,其它方法想记录相关日志的话就可以打上这个Attribute ConsoleLogger 输出log直接输出到控制台。 会看到还有一个类 ApplicationServices 这个就是用来处理依赖注入的。生成LogAspect
public static class ApplicationServices
{
public static readonly ServiceProvider ServiceProvider;
static ApplicationServices()
{
ServiceProvider = new ServiceCollection()
.AddTransient<LogAspect>()
.AddSingleton<ConsoleLogger>()
.BuildServiceProvider();
//在asp.net的项目中我们需要把这个注入的代码抽取出来。 这样两边的依赖注入配置才好共享。
}
public static object GetInstance(Type type)
{
return ServiceProvider.GetRequiredService(type);
}
}
public class DITestClass
{
[Log(Name = "attribute name")]
public void Do()
{
}
}
using Aspects.Cache;
using System;
using System.Threading.Tasks;
namespace ConsoleApp1
{
class Program
{
static async Task Main(string[] args)
{
var di = new DITestClass();
di.Do();
}
}
}
输出
Calling 'Do' method... attributeName:attribute name