如何在structuremap中进行装饰?

Med*_*tor 6 c# structuremap dependency-injection

我尝试装饰IProjectService但我找不到struturemap的文档

For<IProjectService>().Use<ProjectServiceLogDecorator>();
For<IProjectService>().Use<ProjectService>()
                      .DecorateWith((context, decorator) =>   
                                  context.GetInstance<ProjectServiceLogDecorator>());
Run Code Online (Sandbox Code Playgroud)

我做错了什么?

exeption:

检测到双向依赖关系!检查以下StructureMap堆栈跟踪:1.)新ProjectServiceLogDecorator(IRepository的默认,IUnitOfWork的默认,IProjectService的默认,的IPrincipal的默认,AuditEventLogger的默认)2.)3. Project.Services.Projects.ProjectServiceLogDecorator)实例Project.Services的.Projects.ProjectServiceLogDecorator 4.)Project.Services.Projects.IProjectService的FuncInterceptor:IContext.GetInstance()5.)Project.Services.Projects.ProjectService 6.)Project.Services.Projects.IProjectService的实例(Project.Services.Projects) .ProjectService)7.)新的UsersController(IUserService的默认值,IService的默认,IUserNotificationService的默认, IService的默认,IProjectService的默认,ILicenseGroupService的默认)8.)Project.Web.Api.Controllers.UsersController 9.)Project.Web.Api.Controllers.UsersController 10的实例)的容器.GetInstance(Project.Web.Api.Controllers.UsersController)

我找到了解决办法,但令人作呕的是:

For<IProjectService>().Use<ProjectService>().DecorateWith((ctx, service) => 
    new ProjectServiceLogDecorator(
        ctx.GetInstance<IRepository<Project>>(),
        ctx.GetInstance<IUnitOfWork>(),
        service,
        ctx.GetInstance<ILicenseService>(),
        ctx.GetInstance<IPrincipal>(),
        ctx.GetInstance<AuditEventLogger>()
    )
);
Run Code Online (Sandbox Code Playgroud)

Nig*_*888 6

虽然还没有文档,但是有一套完整的单元测试,显示了配置装饰器模式的所有不同方法.我相信你想要的是:

For<IProjectService>().DecorateAllWith<ProjectServiceLogDecorator>();
For<IProjectService>().Use<ProjectService>();
Run Code Online (Sandbox Code Playgroud)

您只需执行以下操作即可添加其他装饰器.但是,请注意最外面的装饰器是最后.DecorateAllWith指定的,因此首先指定最内层的类可能更直观.

For<IProjectService>().Use<ProjectService>();
For<IProjectService>().DecorateAllWith<ProjectServiceLogDecorator>();
For<IProjectService>().DecorateAllWith<SomeOtherDecorator>();
Run Code Online (Sandbox Code Playgroud)

结果如下:

SomeOtherDecorator
    ProjectServiceLogDecorator
        ProjectService
Run Code Online (Sandbox Code Playgroud)

如果需要更多控制,则可以始终使用智能实例将构造函数参数显式应用于装饰器(无需显式提供所有参数).

var projectService = For<IProjectService>().Use<ProjectService>();
For<IProjectService>().Use<ProjectServiceLogDecorator>()
    .Ctor<IProjectService>().Is(projectService);
Run Code Online (Sandbox Code Playgroud)