2

首次設置Web API,所以可能很愚蠢的問題。我開始使用無身份驗證的API,然後通過基本上從標準項目複製來添加OAuth身份驗證。現在在API上註冊操作給出「沒有發現HTTP資源[...]」

,我面臨的挑戰是,當我嘗試使用郵差創建一個帳戶,我得到:

{ 
    "Message": "No HTTP resource was found that matches the request URI 'http://api.asanoapp.com/api/Account/Register'.", 
    "MessageDetail": "No action was found on the controller 'Account' that matches the request." 
} 

我做的是我發表的帖子中我的下面(截圖調用郵差:http://prntscr.com/gch0j9):

http://api.domain.com/api/Account/Register 

用下面的身體(生):

{ 
    "Email": "[email protected]", 
    "Password": "1234pass", 
    "ConfirmPassword": "1234pass" 
} 

AccountController這是從一個標準的項目複製,具有以下聲明:

[Authorize] 
[RoutePrefix("api/Account")] 
public class AccountController : ApiController 
{ 
    private const string LocalLoginProvider = "Local"; 
    private ApplicationUserManager _userManager; 

    // 400+ lines of more standard stuff 
} 

Register方法是這樣的:

// POST api/Account/Register 
[AllowAnonymous] 
[Route("Register")] 
public async Task<IHttpActionResult> Register(RegisterBindingModel model) 
{ 
    if (!ModelState.IsValid) 
    { 
     return BadRequest(ModelState); 
    } 

    var user = new ApplicationUser() { UserName = model.Email, Email = model.Email }; 

    IdentityResult result = await UserManager.CreateAsync(user, model.Password); 

    if (!result.Succeeded) 
    { 
     return GetErrorResult(result); 
    } 

    return Ok(); 
} 

現在,我不明白爲什麼我得到的"No action was found on the controller",因爲我都有這種方法,我打電話給正確的主體(RegisterBindingModel從默認項目viewmodel)。

我在這裏錯過了什麼?

編輯:

WebApiConfig:

public static void Register(HttpConfiguration config) 
     { 
      // Web API configuration and services 
      // Configure Web API to use only bearer token authentication. 
      config.SuppressDefaultHostAuthentication(); 
      config.Filters.Add(new HostAuthenticationFilter(OAuthDefaults.AuthenticationType)); 
      // Web API routes 
      config.MapHttpAttributeRoutes(); 

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

      config.Formatters.JsonFormatter.SupportedMediaTypes 
       .Add(new MediaTypeHeaderValue("text/html")); 

     } 

Startup.cs:

[assembly: OwinStartup(typeof(Asano.Websites.Api.Startup))] 

namespace Asano.Websites.Api 
{ 
    public partial class Startup 
    { 
     public void Configuration(IAppBuilder app) 
     { 
      ConfigureAuth(app); 
     } 
    } 
} 

Startup.Auth(其中ConfigureAuth是):

public partial class Startup 
    { 
     public static OAuthAuthorizationServerOptions OAuthOptions { get; private set; } 

     public static string PublicClientId { get; private set; } 

     // For more information on configuring authentication, please visit https://go.microsoft.com/fwlink/?LinkId=301864 
     public void ConfigureAuth(IAppBuilder app) 
     { 
      // Configure the db context and user manager to use a single instance per request 
      app.CreatePerOwinContext(AsanoWebsitesApiContext.Create); 
      app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create); 

      // Enable the application to use a cookie to store information for the signed in user 
      // and to use a cookie to temporarily store information about a user logging in with a third party login provider 
      app.UseCookieAuthentication(new CookieAuthenticationOptions()); 
      app.UseExternalSignInCookie(DefaultAuthenticationTypes.ExternalCookie); 

      // Configure the application for OAuth based flow 
      PublicClientId = "self"; 
      OAuthOptions = new OAuthAuthorizationServerOptions 
      { 
       TokenEndpointPath = new PathString("/Token"), 
       Provider = new ApplicationOAuthProvider(PublicClientId), 
       AuthorizeEndpointPath = new PathString("/api/Account/ExternalLogin"), 
       AccessTokenExpireTimeSpan = TimeSpan.FromDays(14), 
       // In production mode set AllowInsecureHttp = false 
       AllowInsecureHttp = true 
      }; 

      // Enable the application to use bearer tokens to authenticate users 
      app.UseOAuthBearerTokens(OAuthOptions); 

      // Uncomment the following lines to enable logging in with third party login providers 
      //app.UseMicrosoftAccountAuthentication(
      // clientId: "", 
      // clientSecret: ""); 

      //app.UseTwitterAuthentication(
      // consumerKey: "", 
      // consumerSecret: ""); 

      //app.UseFacebookAuthentication(
      // appId: "", 
      // appSecret: ""); 

      //app.UseGoogleAuthentication(new GoogleOAuth2AuthenticationOptions() 
      //{ 
      // ClientId = "", 
      // ClientSecret = "" 
      //}); 
     } 
    } 

的Global.asax.cs - 應用程序啓動:

public class WebApiApplication : System.Web.HttpApplication 
    { 
     protected void Application_Start() 
     { 
      AreaRegistration.RegisterAllAreas(); 
      GlobalConfiguration.Configure(WebApiConfig.Register); 
      FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters); 
      RouteConfig.RegisterRoutes(RouteTable.Routes); 
      BundleConfig.RegisterBundles(BundleTable.Bundles); 
     } 
    } 
+0

你可以嘗試添加/更改郵遞員中的Content-Type頭,所以它的值是application/json而不是文本 – JConstantine

+0

我剛剛試過這個@JLevett - http://prntscr.com/gcjn4a。仍然找回沒有發現的行動 –

+0

嗯 - 在這裏拉伸,但也許該網址是區分大小寫。在PM – JConstantine

回答

1

不幸的是,這篇文章的答案並沒有幫助我找到一個可行的解決方案。因此,我做了以下的這一切:

添加以下屬性我register方法:

[Route("api/account/register")] 

並將其加入後,它的工作原理。所以看起來底層的問題是控制器的前綴不起作用。

但是,做上面的事情工作(但顯然是一個黑客)。

+0

雖然很奇怪。必須對此進行一些研究。我建議的代碼在很多生產應用程序中都沒有問題。奇怪的。 – Nkosi

1

你缺少的,它可以讓路由表的動作[HttpPost]屬性知道操作可以處理匹配的路由模板POST請求。

[Authorize] 
[RoutePrefix("api/Account")] 
public class AccountController : ApiController { 
    //...code removed for brevity 

    [HttpPost]//<-- this guy 
    [AllowAnonymous] 
    [Route("Register")] //Matches POST api/Account/Register 
    public async Task<IHttpActionResult> Register(RegisterBindingModel model) { 
     //...code removed for brevity 
    } 
} 
+0

雖然我很確定這也是一個問題,但這並沒有解決我的挑戰。你有任何其他的想法可能是什麼? : -/ –

+0

@LarsHoldgaard自您使用屬性路由以來的假設是您還啓用了它。顯示'WebApiConfig'並確保啓用了屬性路由'config.MapHttpAttributeRoutes();' – Nkosi

+0

我剛剛添加了它。它似乎在那裏。其他任何有意義的外觀? –

相關問題