我尝试通过Ajax调用MVC操作失败了。当我这样做时,会发生以下错误:
HttpException: A public action method 'Find' was not found on controller 'MyProject.Controllers.LoanController'.
我尝试调用的操作方法具有以下签名:
[Route("Loan/Find/{loanNumber:int}")]
[AcceptVerbs(HttpVerbs.Get | HttpVerbs.Post)]
[ActionName("Find")]
[AllowAnonymous]
public ActionResult Find(int loanNumber)
{
var model = new LoanStatusModel
{
Record = Repository.GetRecord(loanNumber),
User = this.SecurityPrincipal
};
return this.PartialView("LoanStatusSearchResult", model);
}
尝试调用它的视图代码如下:
@using(Ajax.BeginForm("Find", new AjaxOptions
{
HttpMethod = "POST",
AllowCache = false,
InsertionMode = InsertionMode.Replace,
UpdateTargetId = "ajaxTarget",
LoadingElementId="loader"
}))
{
<fieldset>
<div class="col-sm-3">
<input type="text"
id="loanNumber"
name="loanNumber"
value="@Model.LoanNumber"
class="form-control"
minlength="8"
maxlength="10"/>
</div>
<div class="col-sm-7">
<input type="submit"
value="Search"
class="btn btn-primary"/>
</div>
</div>
</fieldset>
}
<div id="loader" style="display:none">
Working, please wait...
</div>
<div id="ajaxTarget">
</div>
这是我的RouteConfig.cs的内容:
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.MapMvcAttributeRoutes();
routes.MapRoute(
"Default",
"{controller}/{action}/{id}",
new
{
controller = "Home",
action = "Index",
id = UrlParameter.Optional
}
);
}
Fidler报告说,路由请求导致HTTP 401 Not Authorized,这是有道理的,因为这是一个最初配置为禁用匿名访问的Intranet站点。但是,已启用匿名访问,并且仍会出现错误。
要解决此问题,我在搜索了整个互联网(特别是StackOverflow)之后尝试了以下内容:
HttpPostAttribute
修饰。将其更改为使用AcceptVerbs
与结果无关。AllowAnonymous
,它与结果无关。如何解决此问题?它可以解决吗?我需要提供哪些其他信息?
答案 0 :(得分:2)
您有属性路线定义
[Route("Loan/Find/{loanNumber:int}")]
因此,当您尝试使用yourSite/Loan/Find/123123313
访问您的操作方法时,它将转到操作方法,但如果您尝试正常yourSite/Loan/Find?loanNumber=123123123
,它将无法正常工作!
您的Ajax.BeginForm
html帮助器会将表单标记的操作值生成为&#34; / Home / Find&#39;当您提交表单时,loanNumber的值将在帖子正文中提交。它不在您在属性路由定义中定义的路由模式中。
如果删除属性路由路由定义,您的代码将起作用。属性路由主要用于创建不错的seo友好类型URL。因此,最好是GET操作,而不是表单发布方案。
如果您仍想保留属性路由路由模式,我建议您不要使用Ajax.BeginForm
帮助方法并处理ajax调用您自己,您可以按照自己的方式构建URL。
所以建立一个普通的表格,给表格一个id。
@using (Html.BeginForm("Find","Home", FormMethod.Post,new {id="mySearchForm"}))
{
<div class="col-sm-3">
<input type="text" id="loanNumber" name="loanNumber"value="@Model.LoanNumber" />
</div>
<div class="col-sm-7">
<input type="submit" value="Search" />
</div>
}
并使用javascript来监听此表单上的提交事件,停止默认行为并使用我们想要的网址进行ajax调用!
$(function () {
$("#mySearchForm").submit(function(e) {
e.preventDefault();
var url = "@Url.Action("Find","Home")"; //change to your controller name
url = url + "/" + $("#loanNumber").val();
$.post(url, function(res) {
$("#ajaxTarget").html(res);
});
});
});