.netcore 自定义特性类注入(仿TypeFilterAttribute)

代码如下:

 /// <summary>
    /// 声明委托
    /// </summary>
    /// <param name="serviceProvider"></param>
    /// <returns></returns>
    public delegate object 
        ServiceObjFactory(IServiceProvider serviceProvider);
        
    /// <summary>
    /// 自定义类型注入特性类
    /// </summary>
    public class CustomServiceFilterAttribute : Attribute, IFilterFactory
    {
        /// <summary>
        /// 声明私有委托变量,用于首次赋值,后续直接从委托中获取无需重复实例
        /// </summary>
        private ServiceObjFactory _objFactory;

        /// <summary>
        /// 传递的实现类特性
        /// </summary>
        private readonly Type _implementationType;

        public CustomServiceFilterAttribute(Type implementationType)
        {
            _implementationType = implementationType;
        }

        public bool IsReusable { get; set; }

        public IFilterMetadata CreateInstance(IServiceProvider serviceProvider)
        {
            if (serviceProvider == null)
            {
                throw new ArgumentNullException("serviceProvider");
            }
            if (_implementationType == null)
            {
                throw new ArgumentNullException("_implementationType");
            }

            #region 使用表达式目录树实现

            if (_objFactory == null)
            {
                var providerExp = Expression.Parameter(typeof(IServiceProvider), "proveider");

                var ctors = _implementationType.GetTypeInfo().DeclaredConstructors;
                var lastCtor = ctors.OrderByDescending(m => m.GetParameters().Length).First();
                var parameters = lastCtor.GetParameters();

                List<Expression> exps = new List<Expression>();
                if (parameters.Length > 0)
                {
                    foreach (var parameter in parameters)
                    {
                        var parameterType = parameter.ParameterType;
                        var constantExp = Expression.Constant(parameterType, typeof(Type));
                        var methodInfo = typeof(IServiceProvider).GetMethod("GetService");
                        var methodCallExp = Expression.Call(providerExp, methodInfo, constantExp);
                        var convertExp = Expression.Convert(methodCallExp, parameterType);
                        exps.Add(convertExp);
                    }
                }
                var newExp = Expression.New(lastCtor, exps.ToArray());

                var lambdaExp = Expression.Lambda<Func<IServiceProvider, object>>(newExp, providerExp);

                _objFactory = lambdaExp.Compile().Invoke;
            }

            return (IFilterMetadata)_objFactory(serviceProvider);

            #endregion

            #region 使用反射的方式

            //var objArray = new List<object>();
            //var constructors = _implementationType.GetTypeInfo().DeclaredConstructors;
            //ConstructorInfo lastConstructor = null;
            //if (constructors?.Count() > 0)
            //{
            //    lastConstructor = constructors
            //        .OrderByDescending(m => m.GetParameters().Length).First();

            //}
            //var typeParameters = lastConstructor.GetParameters();
            //if (typeParameters != null)
            //{
            //    foreach (var parameterInfo in typeParameters)
            //    {
            //        var serviceType = serviceProvider.GetService(parameterInfo.ParameterType);
            //        objArray.Add(serviceType);
            //    }
            //}
            //return (IFilterMetadata)Activator.CreateInstance(_implementationType, objArray.ToArray());

            #endregion
        }
    }

    
  //调用方式
        [CustomServiceFilter(typeof(CustomExceptionAttribute))]
        public IActionResult Index()
        {
            return View();
        }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

双叶红于二月花

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值