【问题标题】:All ASP.NET Web API controllers return 404所有 ASP.NET Web API 控制器都返回 404
【发布时间】:2013-03-11 11:09:46
【问题描述】:

我正在尝试让 API 控制器在 ASP.NET MVC 4 Web 应用程序中工作。但是,每个请求都会导致 404,我很困惑。 :/

我有来自项目模板的标准 API 控制器路由,定义如下:

public static class WebApiConfig
{
    public static void Register(HttpConfiguration config)
    {
        config.Routes.MapHttpRoute(
            name: "DefaultApi",
            routeTemplate: "api/{controller}/{id}",
            defaults: new { id = RouteParameter.Optional }
        );
    }
}

注册在 Global.asax 中调用:

protected void Application_Start()
{
    AreaRegistration.RegisterAllAreas();

    // Register API routes
    WebApiConfig.Register(GlobalConfiguration.Configuration);

    FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);

    RouteConfig.RegisterRoutes(RouteTable.Routes);
}

我有一个这样的基本 API 控制器:

namespace Website.Controllers
{
    public class FavoritesController : ApiController
    {       
        // GET api/<controller>
        public IEnumerable<string> Get()
        {
            return new [] { "first", "second" };
        }

        // PUT api/<controller>/5
        public void Put(int id)
        {

        }

        // DELETE api/<controller>/5
        public void Delete(int id)
        {

        }
    }
}

现在,当我浏览到 localhost:59900/api/Favorites 时,我希望调用 Get 方法,但我得到的是 404 状态码和以下响应:

<Error>
   <Message>
       No HTTP resource was found that matches the request URI 'http://localhost:59900/api/Favorites'.
   </Message>
   <MessageDetail>
      No type was found that matches the controller named 'Favorites'.
   </MessageDetail>
</Error>

任何帮助将不胜感激,我在这里有点失去理智。 :) 谢谢!

【问题讨论】:

  • 您是否尝试过使用 Phil Haack 的 Route Tester 测试您的路线? haacked.com/archive/2008/03/13/url-routing-debugger.aspx
  • 路由测试器说 /api/Favorites 请求匹配 api/{controller}/{id} 路由模式。但是,还有其他外部路由匹配列表中的较高位置。也许那些路线正在拦截我的请求......
  • 清除了所有其他路由,结果还是一样。 :(
  • 为什么要覆盖 Application_Start?默认情况下,该方法将注册您在覆盖方法中拥有的内容。可能是两次注册的路由导致了问题。
  • 我有一个要继承的抽象基类。我试过跳过继承,但结果保持不变。不过感谢您的帮助!我将编辑问题以消除任何混乱。 :)

标签: asp.net-mvc asp.net-mvc-4 asp.net-web-api


【解决方案1】:

我有点难过,不确定这是否是由于 HTTP 输出缓存问题。

无论如何,“突然间它开始正常工作了”。 :/ 所以,上面的例子没有我添加或改变任何东西。

猜代码只需要坐下来煮一夜……:)

谢谢你们的帮助,伙计们!

【讨论】:

  • 这听起来像“Build --> Clean”+“Build --> Rebuild”(顺便说一句,Rebuild 比 Clean+Build 做的少,Clean 在临时 asp.net 文件清理方面做得更多)跨度>
  • @JonDavis 经过几个小时的挫折......你的评论帮助了我。我正在使用的项目过去已重命名,但文件夹中仍然有旧的 dll。 Build clean 不会清除它们,但是在我手动删除它们之后它现在可以工作了。
【解决方案2】:

我遇到的一件事是在我的 GLobal.asax 文件中以错误的顺序注册了我的配置,例如:

正确的顺序:

AreaRegistration.RegisterAllAreas();
WebApiConfig.Register(GlobalConfiguration.Configuration);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);

错误的顺序:

AreaRegistration.RegisterAllAreas();
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
WebApiConfig.Register(GlobalConfiguration.Configuration);

只是说,这是我的问题,更改顺序是显而易见的,但有时会被忽视,可能会导致很多挫败感。

【讨论】:

  • 挣扎了几个小时后,找到了这个答案……非常感谢!!
  • 我认为这个答案的投票率最高,因为提出这个问题的人很可能对订单有问题,正如我在这里展示的那样。但我认为这不是这个问题的答案。我提供了它作为替代答案,因为我知道来这里的人很可能会遇到与我相同的问题。不过我很感激你的要求!大声笑
  • 是因为RouteConfig的路由更通用,猛击WebApiConfig的路由?
  • 只是好奇,在 MVC5 中,自述文件状态是在首次创建 API 控制器以添加到 Global.asax.cs 上的 GlobalConfiguration.Configure(WebApiConfig.Register); 之后。我在这里注意到你有WebApiConfig.Register(GlobalConfiguration.Configuration);。也许我应该只阅读文档,但你这样做会有所不同吗?
  • @SomeShinyObject 如果我们在答案中这样做,我们必须添加GlobalConfiguration.Configuration.EnsureInitialized();。像GlobalConfiguration.Configure(WebApiConfig.Register); 那样做我们不这样做。
【解决方案3】:

基本上有同样的问题,在我的情况下通过添加解决了:

<modules runAllManagedModulesForAllRequests="true" />

到

<system.webServer>

</system.webServer>

web.config部分

【讨论】:

  • 我发现这对我有帮助,但在做了更多研究后,我发现你不应该在不了解它的含义的情况下启用它。查看this page on msdn 它说“如果您的网站在 IIS 7 上运行并且 IIS 已更新,则无需将 runAllManagedModulesForAllRequests 设置为 true。事实上,不建议将其设置为 true ”。有一个patch available 将使此设置变得不必要。
【解决方案4】:

我一直在研究与此类似的问题,我花了很长时间才找到问题。这不是这个特定帖子的解决方案,但希望添加它可以节省一些时间来尝试找到问题,因为他们正在搜索为什么他们的控制器可能会收到 404 错误。

基本上,我在班级名称末尾拼错了“Controller”。就这么简单!

【讨论】:

  • 我们花了 45 分钟试图找出 API 控制器为什么会出现 404。结果文件必须以“...Controller.cs”结尾。你的评论让我们走上了正轨。谢谢!
  • 非常感谢,在许多项目中使用 API,无法弄清楚为什么在一切设置正确后这不起作用,阅读您的帖子并检查,忘记添加“控制器” 。如此令人沮丧的小学生错误。谢谢。
【解决方案5】:

将此添加到您的 web.config 中的 &lt;system.webServer&gt;:

<handlers>
    <remove name="ExtensionlessUrlHandler-Integrated-4.0"/>
    <remove name="OPTIONSVerbHandler"/>
    <remove name="TRACEVerbHandler"/>
    <add name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="*" type="System.Web.Handlers.TransferRequestHandler"
        preCondition="integratedMode,runtimeVersionv4.0"/>
</handlers>

添加&lt;modules runAllManagedModulesForAllRequests="true" /&gt; 也可以,但由于性能问题不建议使用。

【讨论】:

    【解决方案6】:

    检查你的控制器类是否有 [RoutePrefix("somepath")] 属性,所有控制器方法也有一个 [Route()] 属性集。

    我也遇到过这个问题,并且摸不着头脑。

    【讨论】:

      【解决方案7】:

      我通过将调试器附加到应用程序初始化解决了类似的问题。只需启动网络服务器(例如,访问 localhost),附加到 w3wp 并查看应用程序初始化是否正确完成。在我的情况下,出现了异常,并且控制器没有注册。

      【讨论】:

        【解决方案8】:

        我遇到了同样的 404 问题,但这里没有一个被赞成的解决方案。就我而言,我有一个带有自己的 web.config 的子应用程序,并且在父级的 httpModules web.config 部分中有一个清晰的标签。在 IIS 中,所有父级的 web.config 设置都适用于子应用程序。

        <system.web>    
          <httpModules>
            <clear/>
          </httpModules>
        </system.web>
        

        解决方案是删除“清除”标签,并可能在父级的 web.config 中添加 inheritInChildApplications="false"。 inheritInChildApplications 是为了让 IIS 不将配置设置应用于子应用程序。

        <location path="." inheritInChildApplications="false">
          <system.web>
          ....
          <system.web>
        </location>
        

        【讨论】:

          【解决方案9】:

          添加以下行

          GlobalConfiguration.Configure(WebApiConfig.Register);
          

          在 Global.ascx.cs 文件中的Application_Start() 函数中。

          【讨论】:

          • 如果此代码回答了问题,请考虑在您的答案中添加一些解释代码的文本。这样一来,您就更有可能获得更多支持,并帮助提问者学习新知识。
          • 这个解决方案对我来说适用于 WebApi 2.0,但是接受的答案中的“WebApiConfig.Register(GlobalConfiguration.Configuration)”引发了异常。
          • WebApiConfig.Register(GlobalConfiguration.Configuration) 和你的答案有什么区别?为什么刚创建项目时没有在app start中添加?
          • @BalintBako 根据您遇到的异常情况,您可能只需要在页面顶部导入命名空间:using System.Web.Http; - 我必须这样做,然后添加 WebApiConfig.Register(GlobalConfiguration.Configuration);很好。而且我必须进入 WebApiConfig 类并将命名空间设置为没有.App_Start,这样 Global.asax.cs 就不必将using MyProject.App_Start; 添加到页面顶部。
          【解决方案10】:

          为您的方法创建一个 Route 属性。

          例子

                  [Route("api/Get")]
                  public IEnumerable<string> Get()
                  {
                      return new string[] { "value1", "value2" };
                  }
          

          你可以像这样打电话http://localhost/api/Get

          【讨论】:

          • 路由应该在 WebApiConfig 中自动处理。只有在偏离那里注册的模式时才需要这样做。
          【解决方案11】:

          我遇到了同样的问题,然后我发现我在其他项目中有重复的 api 控制器类名称,尽管 "routePrefix" 和命名空间和项目名称不同,但它们仍然存在返回 404,我更改了类名并且它起作用了。

          【讨论】:

          • 我很高兴读到这篇文章。我也把所有东西都分开了,但它返回 404。更改控制器的名称修复了它。
          【解决方案12】:

          由于我不清楚的原因,我已将我的所有方法/操作声明为静态 - 显然,如果您这样做,它将不起作用。所以把static 关掉

          [AllowAnonymous]
          [Route()]
          public static HttpResponseMessage Get()
          {
              return new HttpResponseMessage(System.Net.HttpStatusCode.OK);
          }
          

          成为:-

          [AllowAnonymous]
          [Route()]
          public HttpResponseMessage Get()
          {
              return new HttpResponseMessage(System.Net.HttpStatusCode.OK);
          }
          

          【讨论】:

            【解决方案13】:

            我将在这里添加我的解决方案,因为我个人讨厌那些编辑 web.config 而不解释发生了什么的人。

            对我来说,这是在 IIS 中设置默认处理程序映射的方式。要检查这个...

            1. 打开 IIS 管理器
            2. 点击你服务器的根节点(通常是服务器的名字)
            3. 打开“处理程序映射”
            4. 在右窗格中的“操作”下,单击“查看有序列表”

            这是处理请求的处理程序的顺序。如果你的和我的一样,“ExtensionlessUrlHandler-*”处理程序都在 StaticFile 处理程序之下。那是行不通的,因为 StaticFile 处理程序有一个通配符 * 并且会在到达无扩展控制器之前返回 404。

            因此,重新排列并将“ExtensionlessUrlHandler-*”移动到 TRACE、OPTIONS 和 StaticFile 的通配符处理程序上方,将首先激活无扩展处理程序,并且应该允许您的控制器在系统中运行的任何网站中正确响应。

            注意: 这基本上是当您在 web.config 中删除和添加模块时发生的情况,但只有一个地方可以解决所有问题。而且它不需要额外的代码!

            【讨论】:

              【解决方案14】:
              WebApiConfig.Register(GlobalConfiguration.Configuration);
              

              应该在 App_start 事件中排在第一位。我已经在 APP_start 事件的最后位置尝试过,但没有成功。

              【讨论】:

              • 这与接受的答案基本相同,但错误,因为它不必是第一个,只是在 RouteConfig 注册之前,因为如果你用路由调用你的 API,你就是使用ApiController,它将假定您实际上是在尝试使用您在RouteConfig 中为Controller 注册的任何内容进行路由。我不会投反对票,因为如果有人真的这样做,它会起作用,但推理不正确。
              【解决方案15】:

              一个令人尴尬的简单解决方案的类似问题 - 确保您的 API 方法是 public。省略任何方法访问修饰符也会返回 HTTP 404。

              将返回 404:

              List<CustomerInvitation> GetInvitations(){
              

              将按预期执行:

              public List<CustomerInvitation> GetInvitations(){
              

              【讨论】:

              • 谢谢@BRass .. 看到你的回答后我觉得自己很愚蠢:)
              【解决方案16】:

              有这个问题。必须取消选中 Precompile during publishing。

              【讨论】:

              • 这也是我的问题。 Tnx。
              【解决方案17】:

              我的应用程序安装了几十个不同的客户端,它们都运行良好,然后这个在所有 api 调用上总是返回 404。事实证明,当我在 IIS 中为此客户端创建应用程序池时,它默认为 .net framework 2.0 而不是 4.0,我错过了它。这导致了 404 错误。在我看来,这应该是一个 500 错误。非常误导微软!

              【讨论】:

                【解决方案18】:

                我遇到了这个问题:我在 .NET 4.7.2 上的 Web API 2 项目按预期工作,然后我更改了项目属性以使用 Web 选项卡下的特定页面路径。从那以后我每次运行它时,它都会给我一个 404 错误 - 它甚至没有击中控制器。

                解决方案:我在我的 VS 解决方案文件的父目录(有时是同一目录)中找到了 .vs 隐藏文件夹,并将其删除。当我再次打开我的 VS 解决方案、清理它并使用 Rebuild 选项重建它时,它又运行了。 Visual Studio 创建的缓存文件存在问题。当这些被删除并重建解决方案时,文件被重新创建。

                【讨论】:

                  【解决方案19】:

                  如果您管理 IIS 并且您是必须创建新站点的人,请检查“应用程序池”并确保必须选择 CLR 版本。在我的情况下,它已被选中“无托管代码”。改成 v4.0 后就开始工作了。

                  【讨论】:

                    猜你喜欢
                    • 1970-01-01
                    • 2013-05-24
                    • 2017-12-31
                    • 1970-01-01
                    • 2021-07-21
                    • 2017-03-02
                    • 1970-01-01
                    • 2013-06-23
                    • 2013-04-01
                    相关资源
                    最近更新 更多