dependency-injection - Orchard CMS : Creating module for OpenRasta, 依赖注入(inject)问题

标签 dependency-injection orchardcms openrasta

我正在尝试创建一个 Orchard CMS 模块,该模块可以使用 OpenRasta 为给定路由(例如/openrasta/*)启用 RESTful Web 服务。

我需要访问 Orchard ContentManager 来获取服务返回的内容,因此我的 OpenRasta 处理程序 (ContentHandler) 使用 ContentService,它实现 IContentService,它继承 IDependency。通常这会起作用,因为 Orchard 会将 ContentManager 注入(inject)到构造函数中:

public class ContentService : IContentService {
    public IContentManager content;

    public ContentService(IContentManager content) {
        this.content = content;
    }

    public IEnumerable<string> GetContentTypeDefinitionNames() {
        return content.GetContentTypeDefinitions().Select(d => d.Name);
    }
}

但是当我运行它时,我收到一个错误,因为 OpenRasta 不知道有关 Orchard 依赖项的任何信息,并且尝试创建 ContentService,而不是 Orchard,这很公平:

OpenRasta.DI.DependencyResolutionException: Could not resolve type ContentService because its dependencies couldn't be fullfilled Constructor: Orchard.ContentManagement.IContentManager

有没有办法实现这一点,我可以去某个 Orchard 类并说“给我一个 ContentManager 的实例”吗?

更新:请参阅我对 @rfcdejong 的回答的评论,了解我的进展更新。

最佳答案

您是否使用 ServiceRoute,添加到实现 IRouteProvider 的类中 查看 ServiceRoute 摘要,它显示“启用通过 HTTP 创建服务路由以支持 REST 方案。”

public class Routes : IRouteProvider
{
    public void GetRoutes(ICollection<RouteDescriptor> routes)
    {
        foreach (var routeDescriptor in GetRoutes())
            routes.Add(routeDescriptor);
    }

    private static ServiceRoute _rastaService = new ServiceRoute(
        "openrasta",
        new MyServiceHostFactory<IOpenRastaService>(), 
        typeof(IOpenRastaService));

    public IEnumerable<RouteDescriptor> GetRoutes()
    {
        return new[] 
        {
            new RouteDescriptor
            {
                Priority = -1,
                Route = _rastaService
            }
        };
    }
}

并且想要解析ContentService?您可能必须解析接口(interface)。

我猜你希望以下内容起作用:

var contentService = LifetimeScope.ResolveNew<IContentService>();

我直接使用了 HostContainer.Resolve,也遇到了问题。我将描述我目前在我自己的 ServiceHostFactory 中使用的解决方案

您有自己的从 OrchardServiceHostFactory 派生的 ServiceHostFactory 吗? 在这种情况下,您可以实现以下代码来帮助您解决实例

    private ILifetimeScope _lifetimeScope = null;
    private ILifetimeScope LifetimeScope
    {
        get
        {
            if (_lifetimeScope == null)
            {
                IHttpContextAccessor accessor = HostContainer.Resolve<IHttpContextAccessor>();
                IRunningShellTable runningShellTable = HostContainer.Resolve<IRunningShellTable>();
                ShellSettings shellSettings = runningShellTable.Match(accessor.Current());
                IOrchardHost orchardHost = HostContainer.Resolve<IOrchardHost>();
                ShellContext shellContext = orchardHost.GetShellContext(shellSettings);
                _lifetimeScope = shellContext.LifetimeScope;
            }
            return _lifetimeScope;
        }
    }

我还创建了具有以下代码的 LifetimeScopeExtensions

public static class LifetimeScopeExtensions
{
    public static T ResolveNew<T>(this ILifetimeScope scope)
    {
        IWorkContextAccessor workContextAccessor = scope.Resolve<IWorkContextAccessor>();
        WorkContext workContext = workContextAccessor.GetContext();
        if (workContext == null)
        {
            using (IWorkContextScope workContextScope = workContextAccessor.CreateWorkContextScope())
            {
                ILifetimeScope lifetimeScope = workContextScope.Resolve<ILifetimeScope>();
                return lifetimeScope.Resolve<T>();
            }
        }
        else
        {
            ILifetimeScope lifetimeScope = workContext.Resolve<ILifetimeScope>();
            return lifetimeScope.Resolve<T>();
        }
    }

    public static object ResolveNew(this ILifetimeScope scope, Type type)
    {
        IWorkContextAccessor workContextAccessor = scope.Resolve<IWorkContextAccessor>();
        WorkContext workContext = workContextAccessor.GetContext();
        if (workContext == null)
        {
            using (IWorkContextScope workContextScope = workContextAccessor.CreateWorkContextScope())
            {
                ILifetimeScope lifetimeScope = workContextScope.Resolve<ILifetimeScope>();
                return lifetimeScope.Resolve(type);
            }
        }
        else
        {
            ILifetimeScope lifetimeScope = workContext.Resolve<ILifetimeScope>();
            return lifetimeScope.Resolve(type);
        }
    }
}


        var settingsService = LifetimeScope.ResolveNew<ITokenServiceSettingsService>();

关于dependency-injection - Orchard CMS : Creating module for OpenRasta, 依赖注入(inject)问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9393014/

相关文章:

c# - 如何在没有 "new' ing"类实例并自己提供参数的情况下进行依赖注入(inject)?

teamcity - 使用 TeamCity 设置 Orchard 项目的部署

asp.net - Orchard CMS-Settings.txt排除了Webdeploy

json - openrasta xml 请求作为 json 返回

iis-7 - OpenRasta post 请求在 chrome 中取消,firefox 中的 500 状态代码,跨域请求

php - Symfony 4 Custom Bundle 使用 Logger Interface

android - Dagger 2构造函数注入(inject)在调用模块之前没有发生

c# - 通过依赖注入(inject)将配置传递给 webjobs

orchardcms - Orchard CMS 分类、导入术语

openrasta - 任何 OpenRasta 引用应用程序或示例?