断続的なasp.net mvc例外:「パブリックアクションメソッドABCがコントローラーXYZで見つかりませんでした。」


92

asp.net mvcがアクションメソッドを見つけられないという断続的な例外が発生します。ここに例外があります:

パブリックアクションメソッド 'Fill'がコントローラー 'Schoon.Form.Web.Controllers.ChrisController'で見つかりませんでした。

このアプリケーションはほとんどの場合機能するため、ルーティングは正しく設定されていると思います。コントローラのアクションメソッドは次のとおりです。

[ActionName("Fill")]
[AcceptVerbs(HttpVerbs.Get | HttpVerbs.Post), UserIdFilter, DTOFilter]
public ActionResult Fill(int userId, int subscriberId, DisplayMode? mode)
{
     //…
}

ルート:

routes.MapRoute(
        "SchoonForm",
        "Form/Fill/{subscriberId}",
        new { controller = "ChrisController", action = "Fill" },
        new { subscriberId = @"\d+" }
    );

そしてここにスタックがあります:

System.Web.HttpException:パブリックアクションメソッド 'Fill'がコントローラー 'Schoon.Form.Web.Controllers.ChrisController'で見つかりませんでした。C:\ dev \ ThirdParty \ MvcDev \ src \ SystemWebMvc \ Mvc \ Controller.cs:line 197のSystem.Web.Mvc.Controller.HandleUnknownAction(String actionName)にCのSystem.Web.Mvc.Controller.ExecuteCore()に:\ dev \ ThirdParty \ MvcDev \ src \ SystemWebMvc \ Mvc \ Controller.cs:line 164 at System.Web.Mvc.ControllerBase.Execute(RequestContext requestContext)in C:\ dev \ ThirdParty \ MvcDev \ src \ SystemWebMvc \ Mvc \ ControllerBase.cs:line 76 at System.Web.Mvc.ControllerBase.System.Web.Mvc.IController.Execute(RequestContext requestContext)in C:\ dev \ ThirdParty \ MvcDev \ src \ SystemWebMvc \ Mvc \ ControllerBase.cs:line 87 CのSystem.Web.Mvc.MvcHandler.ProcessRequest(HttpContextBase httpContext)で:

これが私のフィルターの例です。これらはすべて同じように機能します。

public class UserIdFilter : ActionFilterAttribute
{
    public override void OnActionExecuting(ActionExecutingContext filterContext)
    {
        const string Key = "userId";

        if (filterContext.ActionParameters.ContainsKey(Key))
        {
            filterContext.ActionParameters[Key] = // get the user id from session or cookie
        }

        base.OnActionExecuting(filterContext);
    }
}

ありがとう、クリス


28
これは、上記の例外を検索したときにGoogleで最初に見つかった結果でしたので、ここで注目に値すると思います同様の問題がありました。無効なフォームを送信すると、アプリケーションがこの例外をスローしました。これは、RenderActionの呼び出しを(再)レンダリングしていたページと、部分的なビューをレンダリングするために呼び出されたアクションがHttpGet属性でマークされていたためです。この属性を削除すると、問題が解決しました。
s1mm0t 2010

3
私はこの動作にも気づきました。PartialViewResultsを返すコントローラーメソッドにHttp属性を適用しないのがおそらく最善です。
Stuart

1
@ s1mm0t:そうです。私の場合、彼のコメントは問題を解決しました
Mazdak Shojaie 2017

@ s1mm0t-郵送先住所をすぐに送ってください。スコッチのボトルが今年のクリスマスにあなたに向かっています!!!!!
シェーン

同じようなことが見つかりました。特定のケースでは、そのアクションへのリダイレクトの代わりに別のアクション結果を返すことが問題の原因でした。Ex PostSomething { return HomePageActionMethod() }PostSomething { return RedirectToAction(nameof(HomePageActionMethod)); }動作する場所で失敗します。(我々の場合にビュー内の問題行動が異なるコントローラに位置し、そしてコントローラが完全に呼び出すの第一の方法で初期化されていない、おそらくこと。
jleach

回答:


62

私たちは答えを見つけました。私たちはウェブログを調べました。これは、OPTIONS、PROPFIND、HEADなどの奇妙なhttpアクション(動詞/メソッド)を受け取っていることを示しています。

これは、これらの例外のいくつかの原因のようです。これは、断続的であった理由を説明しています。

curl.exeツールで問題を再現しました:

curl.exe -X OPTIONS http://localhost/v2.3.1.0/(S(boztz1aquhzurevtjwllzr45))/Form/Fill/273
curl.exe -X PROPFIND http://localhost/v2.3.1.0/(S(boztz1aquhzurevtjwllzr45))/Form/Fill/273
curl.exe -X HEAD http://localhost/v2.3.1.0/(S(boztz1aquhzurevtjwllzr45))/Form/Fill/273

使用した修正は、web.configに承認セクションを追加することでした。

<authorization>
  <deny users="*" verbs="OPTIONS, PROPFIND, HEAD"/>
</authorization>

3
また、ボットがリンクを見つけるために、サイト(場合によってはJavaScript)をクロールすることもあります。次に、間違ったHTTP動詞を使用してこれらのURIにリクエストを送信しようとします。たとえば、/ some-actionなどのアクションへのjQuery呼び出しがあり、このメソッドがPOSTを必要とする場合、ボットはGETを送信しようとする可能性があり、このエラーが表示されます。Webログは、これが事実であるかどうかを確認するのに役立ちます。googlebotがこれをしているのを見ることさえある。
jakejgordon 2016年

ライブサーバー(IIS 7.5)でのみ同じエラーが発生します。デプロイメントは、私の開発マシンでも、別のサポートマシンでも正常に機能します。これらの動詞を追加してHttpGetを削除しても問題は解決しませんでした。さらなる提案をお願いします。
bjan 2016年

着信HEADリクエストを拒否する代わりに、適切な応答を提供することができます。stackoverflow.com/a/3197128/12484を
Jon Schneider

15

同様の問題がありましたが、ログインがタイムアウトした後にユーザーがコントローラーに投稿しているために発生していることがわかりました。次に、システムはログイン画面にリダイレクトしました。ログイン後、ユーザーが投稿しようとしたURLにリダイレクトされましたが、今回は代わりにGETリクエストを実行していたため、[HttpPost]属性でマークされたアクションが見つかりませんでした。


私の現在の解決策は、アクションの最後に常にインデックスアクションにリダイレクトすることです。返事が遅くなってごめん。
Johann Strydom-

7

私はasp.net mvcでも同じ問題を抱えています。このエラー-404が見つかりません。私はこの方法で問題を解決します-このコードをMyAppControllerBase(MVC)に入れます

    protected override void HandleUnknownAction(string actionName)
    {
        this.InvokeHttp404(HttpContext);
    }

    public ActionResult InvokeHttp404(HttpContextBase httpContext)
    {
        IController errorController = ObjectFactory.GetInstance<PagesController>();
        var errorRoute = new RouteData();
        errorRoute.Values.Add("controller", "Pages");
        errorRoute.Values.Add("action", "Http404");
        errorRoute.Values.Add("url", httpContext.Request.Url.OriginalString);
        errorController.Execute(new RequestContext(
             httpContext, errorRoute));

        return new EmptyResult();
    }

6

アプリケーションで同じ問題が発生しただけで、javascript / jqueryの問題までたどることができました。Html.ActionLink()を使用して定義されたアプリケーションのリンクがあり、後でjqueryによってPOSTにオーバーライドされます。

最初にリンクを定義しました:

Html.ActionLink("Click Me", "SomeAction", new { id = Model.Id})

後で、SomePostEventHandler関数でデフォルトのアクションをオーバーライドします。

 $(document).ready(function() {
      $('#MyLink').click(SomePostEventHandler);
 }

これは、HttpPostフィルターを持つMVCアクションにヒットしていました。

 [HttpPost]
 public ActionResult SomeAction(int id)
 {
      //Stuff
 }

私たちが見つけたのは、ほとんどの場合これがうまく機能したということです。ただし、ページの読み込みが遅い(またはユーザーが本当に速い)場合、ユーザーはjquery $(document).ready()イベントが発生する前にリンクをクリックしていました。つまり、代わりに/ Controller / SomeAction / XXを取得しようとしていました。投稿。

ユーザーにそのURLを取得してほしくないので、フィルターを削除することはできません。代わりに、アクションリンクのonclickイベントを直接配線しました(これを機能させるには、SomePostEventHandler()を少し変更する必要がありました)。

string clickEvent = "return SomePostEventHandler(this);";

Html.ActionLink("Click Me", "SomeAction", new { id = Model.Id}, new { onclick = clickEvent })

したがって、少なくとも私たちにとって、この話の教訓は、これらのエラーが表示されている場合は、投稿先と考えているURLを追跡し、間違いがないことを確認することです。


2

私もこの問題を抱えていました。

私の場合、それは要求されたアクションの動詞の制限に関連しており、ビューはPOSTサポートされた範囲内GETHEADのみ要求された部分的なビューでした。(MVC 1.0で)にPOST動詞を追加するとAcceptVerbsAttribute、問題が解決しました。


2

IISログから、GooglebotがPOSTおよびPOSTのみのコントローラーアクションのGETを試行したことが原因で問題が発生しました。

この場合、ドミトリーの提案のように404を処理することをお勧めします。


1

現在受け入れられている回答は期待どおりに機能しますが、機能の主な使用例ではありません。代わりに、ASP.NETで定義されている機能を使用してください。私の場合、GETとPOST以外はすべて拒否しました。

  <system.webServer>
  <security>
      <requestFiltering>
          <verbs allowUnlisted="false">
              <add verb="GET" allowed="true"/>
              <add verb="POST" allowed="true"/>
          </verbs>
      </requestFiltering>
  </security>
 </system.webServer>

上記のコードスニペットを使用すると、MVCは正しく404を返します


0

それはすべきではない

routes.MapRoute(
        "SchoonForm",
        "Form/Fill/{subscriberId}",
        new { controller = "Chris", action = "Fill" },

また、フィルターは何をしますか?ActionMethodSelectorAttributeなどのアクションを非表示にできませんか?


それは編集ミスです。私は無実を守ろうとしていた。
Chris Schoon、

それらはいくつかのパラメータを入力します。たとえば、UserIdFilterは、セッション/ Cookie /などからユーザーIDを取得するヘルパーです。最初のパラメーターを設定します。投稿を編集して、含めます。
Chris Schoon、

0

qqファイルのアップロードで同様の問題があります

投稿アクションが/Document/Save例外になると、コントローラー「Project.Controllers.DocumentController」でパブリックアクションメソッド「Save」が見つかりませんでした。

ただし、投稿アクションがの/Document/Save/場合、投稿は正しく機能します。

神はセーブ/を


0

私の根本的な原因は、コメントで言及されたものと同様でした。

私はajaxSubmittingボタンをクリックしたときのフォームでした。フォームフィールドの1つがタイプDateでした。ただし、クライアントマシンとサーバーマシンの日付形式が異なるため、コントローラーでPOSTメソッドを実行しませんでした。サーバーは302応答を送信してGETから、同じメソッドの要求を再度送信しました。

ただし、コントローラーのアクションはHttpPost属性で装飾されているため、メソッドを見つけることができず、404応答を返しました。

日付形式の不一致によってエラーが発生しないようにコードを修正し、問題を修正しました。


0

[HttpGet]属性を削除すると機能します:)


この「解く」のエラーが、可能性はあなた(またはあなたの前に誰かが)ものは入れていることである[HttpGet]他の動詞を介して呼び出されてからアクションを防ぐために、目的にあっ属性
ニック・オーランド

0

angularjs、MVC、および{{imagepath}}タイプでこの問題を抱えている人は、画像のsrc属性に次のように挿入します。

「コントローラーでパブリックアクションメソッド '{{imagepath}} previous.png'が見つかりませんでした」

解決策は、srcの代わりにng-srcを使用することです。

これが誰かを助けることを願っています:)


ほぼ1年後、私はこれを探していました:) tnx!
Verthosa

0

問題のURLを参照するだけでエラーを再現できるかどうかを確認します。アクションがPOSTアクションとしてのみ定義されている場合です。これにより、エラーを自由に再現できます。

いずれの場合も、以下のようにグローバルにエラーを処理できます。ここで言及する別の答えHandleUnknownAction、不正なアクション名を持つURLのみを処理し、不正なコントローラ名は処理しません。次のアプローチは両方を処理します。

これをベースコントローラーに追加します(ここではコードを省略しています):

public ActionResult Error(string errorMessage)
{
    return View("Error");  // or do something like log the error, etc.
}

グローバル例外ハンドラをGlobal.asax.csに追加して、上記のメソッドを呼び出すか、キャッチされた404エラーで実行するその他の処理を行います。

void Application_Error(object sender, EventArgs e)
{
    Exception ex = Server.GetLastError();  // get the exception object
    HttpException httpException = ex as HttpException;

    if (httpException != null && httpException.GetHttpCode() == 404)  // if action not found
    {
        string errorMessage = "The requested page was not found.";

        RouteData routeData = new RouteData();
        routeData.Values.Add("controller", "Base");
        routeData.Values.Add("action", "Error");
        routeData.Values.Add("errorMessage", errorMessage);

        Server.ClearError();
        Response.TrySkipIisCustomErrors = true;

        // Go to our custom error view.
        IController errorController = new BaseController();
        errorController.Execute(new RequestContext(new HttpContextWrapper(Context), routeData));
    }
}
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.