You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

自动实现装饰器方法:数据访问类授权装饰模式的自动化实现问询

自动实现装饰器中的授权逻辑

你用装饰器模式给数据访问类加授权校验的思路没问题,但手动给每个接口方法重复写AuthorizationHelper.Instance.Authorize()确实太繁琐了。下面几个方案能帮你自动完成这个重复工作,不用再挨个方法编写授权逻辑:

1. 使用动态代理库(比如Castle DynamicProxy)

动态代理可以在运行时自动生成实现接口的代理类,给所有方法统一注入前置的授权逻辑。

实现步骤:

  • 先安装Castle.Core NuGet包:
Install-Package Castle.Core
  • 创建一个拦截器类,实现IInterceptor接口来封装授权逻辑:
public class AuthorizationInterceptor : IInterceptor
{
    public void Intercept(IInvocation invocation)
    {
        // 先执行授权校验
        AuthorizationHelper.Instance.Authorize();
        // 再调用原接口方法
        invocation.Proceed();
    }
}
  • 用代理生成器创建带授权逻辑的实例:
var proxyGenerator = new ProxyGenerator();
var authInterceptor = new AuthorizationInterceptor();
IUserData authorizedUserData = proxyGenerator.CreateInterfaceProxyWithTarget(
    new UserData(), 
    authInterceptor);

这样调用authorizedUserData的任何方法时,都会自动先执行授权校验,完全不用手动写每个方法的装饰代码。

2. 利用.NET AOP框架(比如AspectCore)

如果你的项目是.NET Core/.NET 5+,AspectCore这类轻量级AOP框架能更优雅地实现需求。

实现步骤:

  • 安装AspectCore.Core NuGet包:
Install-Package AspectCore.Core
  • 定义一个授权切面特性:
public class AuthorizationAttribute : AbstractInterceptorAttribute
{
    public override async Task Invoke(AspectContext context, AspectDelegate next)
    {
        AuthorizationHelper.Instance.Authorize();
        await next(context);
    }
}
  • 给目标接口或方法标记这个特性:
[Authorization]
interface IUserData 
{ 
    User GetUser(uint id); 
    User ByName(string username); 
}
  • 通过代理生成器获取带授权的实例:
var proxyGenerator = new ProxyGenerator();
IUserData authorizedUserData = proxyGenerator.CreateProxy<IUserData>(new UserData());

所有标记了[Authorization]的方法都会自动触发授权逻辑。

3. 手写通用装饰器(无第三方依赖)

如果不想引入外部库,也可以用.NET自带的DispatchProxy实现一个通用装饰器:

实现代码:

public class GenericAuthorizedDecorator<T> : DispatchProxy
{
    private T _targetInstance;

    protected override object Invoke(MethodInfo targetMethod, object[] args)
    {
        // 执行授权校验
        AuthorizationHelper.Instance.Authorize();
        // 调用目标对象的原方法
        return targetMethod.Invoke(_targetInstance, args);
    }

    public static T Create(T target)
    {
        object proxy = Create<T, GenericAuthorizedDecorator<T>>();
        ((GenericAuthorizedDecorator<T>)proxy)._targetInstance = target;
        return (T)proxy;
    }
}

使用方式:

IUserData authorizedUserData = GenericAuthorizedDecorator<IUserData>.Create(new UserData());

这个方案完全依赖.NET原生API,不需要额外安装包,适合轻量场景。

你可以根据自己的项目环境和复杂度,选一个最合适的方案就行。

内容的提问来源于stack exchange,提问作者Mike Cluck

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 08:16:10