Skip to content

Support Auto Decoration #5

@vipwan

Description

@vipwan

Usage

//注意 AutoDecor和AutoDecorFor是想反的标注,一个标注于需要装饰的类型上,一个标注于装饰器上

//标注于需要装饰的类型上

//netstandard2.0 +
[AutoDecor(Type implement)]

//C#11(NET7+) support generic attribute
[AutoDecor<T>]


//标注于装饰器上

//netstandard2.0 +
[AutoDecorFor(Type forType)]

//C#11(NET7+) support generic attribute
[AutoDecorFor<T>]

Define Base Service (IService or Class) & mark [AutoDecor]

  • 请注意,如需要避免代码侵入,可以使用partial拆分业务代码和特性
    [AutoDecor(typeof(HelloServiceDecor1))]
    [AutoDecor<HelloServiceDecor2>]
    public partial interface IHelloService
    {
        string SayHello(string name);
    }

    public class HelloService : IHelloService
    {
        public string SayHello(string name)
        {
            return $"Hello {name}";
        }
    }

    /// <summary>
    /// ClassService
    /// </summary>
    [AutoDecor<ClassServiceDecor>]
    public partial class ClassService
    {
        /// <summary>
        /// 请注意,如果TService是一个class,而不是interface,这里的virtual关键字是必须的
        /// </summary>
        /// <param name="name"></param>
        /// <returns></returns>
        public virtual string SayHello(string name)
        {
            return $"Hello {name}";
        }
    }

    public class ClassServiceDecor : ClassService
    {
        private readonly ClassService _helloService;
        private readonly ILogger<ClassServiceDecor> _logger;

        public ClassServiceDecor(ClassService helloService, ILogger<ClassServiceDecor> logger)
        {
            _helloService = helloService;
            _logger = logger;
        }

        public override string SayHello(string name)
        {
            Console.WriteLine($"Hello {name} from ClassServiceDecor");
            var result = _helloService.SayHello(name);
            _logger.LogInformation($"Hello {result} from ClassServiceDecor");
            return result;

        }
    }

    /// <summary>
    /// decor IHelloService
    /// </summary>
    public class HelloServiceDecor1 : HelloService
    {
        private readonly HelloService _helloService;

        public HelloServiceDecor1(HelloService helloService)
        {
            _helloService = helloService;
        }

        public new string SayHello(string name)
        {
            Console.WriteLine($"Hello {name} from HelloServiceDecor1");
            return _helloService.SayHello(name);
        }
    }

    /// <summary>
    /// decor IHelloService 2
    /// </summary>
    public class HelloServiceDecor2 : IHelloService
    {
        private readonly IHelloService _helloService;

        public HelloServiceDecor2(IHelloService helloService)
        {
            _helloService = helloService;
        }

        public string SayHello(string name)
        {
            Console.WriteLine($"Hello {name} from HelloServiceDecor2");
            return _helloService.SayHello(name);
        }
    }

auto generated

// <auto-generated />
// author:vipwan@outlook.com 万雅虎
// issue:https://github.com/vipwan/Biwen.AutoClassGen/issues
// 如果你在使用中遇到问题,请第一时间issue,谢谢!
// This file is generated by Biwen.AutoClassGen.SourceGenerator
#pragma warning disable
namespace Microsoft.Extensions.DependencyInjection
{
    public static class AutoDecorExtensions
    {
        /// <summary>
        /// AddAutoDecor
        /// </summary>
        public static IServiceCollection AddAutoDecor(this IServiceCollection services)
        {
            services.Decorate<TestConsole.Decors.IHelloService, TestConsole.Decors.HelloServiceDecor1>();
            services.Decorate<TestConsole.Decors.IHelloService, TestConsole.Decors.HelloServiceDecor2>();
            services.Decorate<TestConsole.Decors.ClassService, TestConsole.Decors.HelloServiceDecor1>();
            return services;
        }
    }
}
#pragma warning restore

enjoy

// add services
builder.Services.AddScoped<IHelloService, HelloService>();
builder.Services.AddScoped<ClassService>();

// add auto decor
builder.Services.AddAutoDecor();

// get service

var helloService = builder.Services.GetRequiredService<IHelloService>();
var classService = builder.Services.GetRequiredService<ClassService>();

Report Diagnostic Code

  • GEN043: 标记[AutoDecor]的类型,装饰器必须是它的实现类或者子类

Metadata

Metadata

Assignees

No one assigned

    Labels

    documentationImprovements or additions to documentationenhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions