如何使用Topshelf,Autofac和自我托管的Owin进行注射

时间:2015-12-04 12:46:26

标签: asp.net-web-api2 owin autofac topshelf

无论我做什么,我都无法使用Topshelf,Autofac和自我托管的Owin进行注射。

我已按照http://autofac.readthedocs.org/en/latest/integration/webapi.html#owin-integration中的文档阅读Autofac WebApi 2 OWIN Not Working,但我仍然无法在我的apicontroller中注入一个简单的类。

“几乎”完整的应用程序已发布在此处。

无论我做什么,我都无法将一个IEmail实例注入到EmailController中。任何人都可以提出解决方案

// topshelf startup code
class Program
{
    static void Main(string[] args)
    {

        HostFactory.Run(c =>
        {
            //c.UseAutofacContainer(container);         
            c.RunAsNetworkService();

            c.Service<SampleService>(s =>
            {
                s.ConstructUsing(name => new SampleService());
                s.WhenStarted((service, control) => service.Start());
                s.WhenStopped((service, control) => service.Stop());
            });

        });
    }
}

// lifted from http://autofac.readthedocs.org/en/latest/integration/webapi.html#owin-integration
public class StartupConfig
{
    public void Configure(IAppBuilder appBuilder)
    {
        var config = new HttpConfiguration();
        config.MapHttpAttributeRoutes();    // using attribute based routing because I prefer it

        var builder = new Autofac.ContainerBuilder();                                    // Create the container builder.
        builder.RegisterApiControllers(Assembly.GetExecutingAssembly());                 // Register the Web API controllers.
        builder.RegisterWebApiFilterProvider(config);                                    // optional

        builder.RegisterType<Email>().As<IEmail>().InstancePerRequest();


        var container = builder.Build();
        config.DependencyResolver = new AutofacWebApiDependencyResolver(container);    

        appBuilder.UseAutofacMiddleware(container);
        appBuilder.UseAutofacWebApi(config);                                            // Make sure the Autofac lifetime scope is passed to Web API.
        appBuilder.UseWebApi(config);       // enable web-api


        string filedir = Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "../../web");
        appBuilder.UseFileServer(new FileServerOptions
        {
            EnableDefaultFiles = true,
            DefaultFilesOptions =
            {
                DefaultFileNames = new[] { "Index.html" }
            },
            EnableDirectoryBrowsing = true,
            FileSystem = new PhysicalFileSystem(filedir),
        });      
    }
}

// topshelf hosted service to start
public class SampleService
{
    public bool Start()
    {
        if (WebApplication == null)
        {
            WebApplication = WebApp.Start
            (
                 new StartOptions
                 {
                     Port = 1234
                 },
                 appBuilder =>
                 {
                     new StartupConfig().Configure(appBuilder);
                 }
            );
        }

        return true;
    }

    public bool Stop()
    {
        return true;
    }

    protected IDisposable WebApplication
    {
        get;
        set;
    }
}

// sample controller
public class EmailController : ApiController
{

    public IEmail MyModel; /** always NULL **/

    [HttpGet]
    [Route("api/emails/{id}")]
    public IHttpActionResult get(int id)
    {

    }
}

Nuget包

<packages>
      <package id="Autofac" version="3.5.0" targetFramework="net452" />
      <package id="Autofac.Owin" version="3.1.0" targetFramework="net452" />
      <package id="Autofac.WebApi" version="3.1.0" targetFramework="net452" />
      <package id="Autofac.WebApi2" version="3.4.0" targetFramework="net452" />
      <package id="Autofac.WebApi2.Owin" version="3.3.0" targetFramework="net452" />
      <package id="EntityFramework" version="6.0.0" targetFramework="net452" />
      <package id="Microsoft.AspNet.WebApi.Client" version="5.2.2" targetFramework="net45" />
      <package id="Microsoft.AspNet.WebApi.Core" version="5.2.2" targetFramework="net45" />
      <package id="Microsoft.AspNet.WebApi.Owin" version="5.2.2" targetFramework="net45" />
      <package id="Microsoft.Owin" version="3.0.1" targetFramework="net452" />
      <package id="Microsoft.Owin.FileSystems" version="3.0.1" targetFramework="net452" />
      <package id="Microsoft.Owin.Host.HttpListener" version="3.0.1" targetFramework="net452" />
      <package id="Microsoft.Owin.Hosting" version="3.0.0" targetFramework="net45" />
      <package id="Microsoft.Owin.StaticFiles" version="3.0.1" targetFramework="net452" />
      <package id="Newtonsoft.Json" version="6.0.4" targetFramework="net45" />
      <package id="Owin" version="1.0" targetFramework="net45" />
      <package id="Topshelf" version="3.1.4" targetFramework="net45" />
      <package id="Topshelf.Autofac" version="1.0.0" targetFramework="net452" />
    </packages>

2 个答案:

答案 0 :(得分:0)

为了在这里注入apicontroller

public class EmailController : ApiController
{

    public IEmail MyModel; // <--- 

    [HttpGet]
    [Route("api/emails/{id}")]
    public IHttpActionResult get(int id)
    {

    }
}

我在注册api控制器builder.RegisterApiControllers(Assembly.GetExecutingAssembly()).PropertiesAutowired();

时缺少[PropertiesAutowired]

答案 1 :(得分:0)

您还没有用于Api Controller的构造函数。有了构造函数后,如果服务位于容器中,则服务将自行解决。

public class EmailController : ApiController
{
    public IEmail MyModel;

    public EmailController(IEmail MyModel){
    this.MyModel = MyModel;
    }

    [HttpGet]
    [Route("api/emails/{id}")]
    public IHttpActionResult get(int id)
    {

    }
}