简体   繁体   English

OWIN Startup类与WebAPIConfig.Register方法一起执行

[英]OWIN Startup class is being executed along with WebAPIConfig.Register method

I am using Microsoft.Owin.Hosting in my one of integration test project to self-host the Web API in order to test end to end functionality. 我在集成测试项目之一中使用Microsoft.Owin.Hosting自托管Web API,以便测试端到端功能。

[TestMethod]
public void GetLoanApplications()
{
    using (WebApp.Start<Startup>(url: url))
    {
        using (var client = new HttpClient())
        {
            // Create httpclient and send request-and-response-metadata-in-aspnet-web-api
        }
    }
}

I am able to self-host the web API and able to invoke the controller action. 我能够自行托管Web API,并能够调用控制器操作。 Owin requires some Startup class configuration, which is as follows: Owin需要一些Startup类配置,如下所示:

[assembly: OwinStartup(typeof(MyService.App_Start.Startup))]
namespace MyService.App_Start
{
    public class Startup
    {
        public void Configuration(IAppBuilder app)
        {
            HttpConfiguration config = new HttpConfiguration();
            config.MapHttpAttributeRoutes();

            config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
            app.UseWebApi(config);
        }
    }
}

Here is my Web API Config method looks like: 这是我的Web API Config方法,如下所示:

public class WebApiApplication : System.Web.HttpApplication
{
    protected void Application_Start()
    {
        GlobalConfiguration.Configure(WebApiConfig.Register);
    }
}

public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.MapHttpAttributeRoutes();

        config.Routes.MapHttpRoute(
            name: "DefaultApi",
            routeTemplate: "api/{controller}/{id}",
            defaults: new { id = RouteParameter.Optional }
        );            
    }
}

Problem 问题

  • When I run my main application (not the test project) both the Owin startup and web API config methods are getting called. 当我运行主应用程序(而不是测试项目)时,会同时调用Owin启动和Web API配置方法。
  • Let's say if I have some services or filters to be configured, it will get invoked twice. 假设我要配置一些服务或过滤器,它将被调用两次。
  • What I thought is IF I am running test project it should only invoke owin startup file ( which it is doing right now ) and when I am debugging my main app it should only call web API config register method. 我以为是,如果我正在运行测试项目,则它仅应调用owin启动文件( 它现在正在执行 ),而在调试主应用程序时,应仅调用Web API配置注册方法。

Any idea on is this the way it should work or I am doing something wrong? 知道这是应该的工作方式还是我做错了什么?

First the system would need a way to differentiate between the environments. 首先,系统将需要一种区分环境的方法。

<appSettings>
    <add key="APP_ENVIRONMENT" value="Development" />
    <!-- ... -->
</appSettings>

Since when run in production both the Owin startup and web api config methods are getting called then OWIN is already configured as a first class citizen in the project. 由于在生产环境中运行Owin启动和Web api配置方法时都会被调用,因此OWIN已被配置为项目中的头等公民。

I suggest moving the code from Application_Start into owin start up 我建议将代码从Application_Start移至owin启动

public class WebApiApplication : System.Web.HttpApplication {
    protected void Application_Start() {
        //REMOVE THIS AND LET OWIN STARTUP HANDLE SETUP
        //GlobalConfiguration.Configure(WebApiConfig.Register);
    }
}

so that it is only invoked once depending on the configured environment. 以便仅根据配置的环境调用一次。

[assembly: OwinStartup(typeof(MyService.App_Start.Startup))]
namespace MyService.App_Start {
    public class Startup {
        const string EnvironmentKey = "APP_ENVIRONMENT";
        const string PRODUCTION = "Production";
        const string TEST = "Test";

        public void Configuration(IAppBuilder app) {
            string ENVIRONMENT = ConfigurationManager.AppSettings[EnvironmentKey] 
                                    ?? Production;
            if(ENVIRONMENT == TEST) {
                var config = new HttpConfiguration();
                WebApiConfig.Register(config);
                app.UseWebApi(config);
            } else {
                GlobalConfiguration.Configure(WebApiConfig.Register);
            }
        }
    }
}

Note the reuse of the WebApiConfig.Register to avoid repeated code. 请注意WebApiConfig.Register的重用,以避免重复代码。 The same configuration will be applied for either environment and all in the same place if additional configurations were to be implemented (ie Development, Testing, Staging, Procustion...etc) 如果要实施其他配置(例如,开发,测试,登台,建议...等),则将相同的配置应用于这两种环境中的任何一种,并且全部应用于同一位置

The test project app.config would include the current environment's setting 测试项目app.config将包括当前环境的设置

<appSettings>
    <add key="APP_ENVIRONMENT" value="Test" />
    <!-- ... -->
</appSettings>

and invoke the start up configuration for self-hosting otherwise it will default back to production settings, but would have also been configured in the web.config 并调用用于自我托管的启动配置,否则它将默认返回到生产设置,但也已在web.config进行了配置

<appSettings>
    <add key="APP_ENVIRONMENT" value="Production" />
    <!-- ... -->
</appSettings>

You need to chose between init your web api from the OWIN pipeline or with the old method in the Application_Start , see the application lifecycle . 您需要从OWIN管道或通过Application_Start的旧方法初始化Web api之间进行选择,请参阅应用程序生命周期

If you keep Application_Start and OwinSartup then your web api is initialized twice 如果保留Application_StartOwinSartup则您的Web api将初始化两次

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM