我有一個web應用程序,我正在構建一個測試/問題/答案應用程序,我認識一位老師。其中一個要求是測試必須在一次會議中完成......即......不保存並繼續。我選擇通過使用jQuery UI的模式彈出窗口來實現這一點。在測試開始前,我有一個測試搜索頁面和一個模態確認對話框。我遇到的問題是在用戶選擇繼續測試之後,它需要重定向到一個新頁面,其中第一個問題將顯示模式彈出窗口(之後的每個問題將通過AJAX加載到相同的模式彈出窗口中)。我有搜索工作,以及確認彈出窗口,但我無法弄清楚如何重定向到問題頁面。我的TestingController中的Question操作被調用並且參數是正確的,但是一旦返回View,ASP.NET將引發一個異常,告訴我第一個參數爲null。以下是控制此行爲的片段:從ASP.NET MVC中成功的AJAX調用重定向
從Search.cshtml(這個div是模態確認彈出):
<div id="dialog" title="Confirm Test">
<p>
<span class="ui-icon ui-icon-alert" style="float:left; margin:0 7px 20px 0;"></span>Are you sure you want to take the selected test?
</p>
</div>
@section scripts
{
<script type="text/javascript">
$(document).ready(function() {
$(".takeTest").click(function (e) {
e.preventDefault();
var testId = $(this).data("test-id");
$("#selectedTestId").val(testId);
$("#dialog").dialog("open");
});
$("#dialog").dialog({
dialogClass: "no-close",
autoOpen: false,
modal: true,
resizable: false,
height: 180,
buttons: {
'Confirm': function() {
var appId = $("#applicantId").val();
var id = $("#selectedTestId").val();
$.ajax({
url: "/Testing/TakeTest/",
data: { applicantId: appId, testId: id },
type: "POST",
success: function (results) {
window.location.href = "/Testing/Question/";
}
});
},
'Cancel': function() {
$(this).dialog('close');
}
}
});
});
</script>
}
從TestingController:
[HttpPost]
public ActionResult TakeTest(int applicantId, int testId)
{
try
{
ApplicantTest test = TestingRepository.GetInstance().TakeTest(applicantId, testId);
return RedirectToAction("Question", "Testing", new { applicantId = applicantId, testId = testId });
}
catch
{
return RedirectToAction("Search", "Testing");
}
}
[HttpGet]
public ActionResult Question(int applicantId, int testId)
{
Question nextQuestion = TestingRepository.GetInstance().GetNextQuestion(applicantId, testId);
NextQuestionViewModel model = AutoMapper.Mapper.Map<NextQuestionViewModel>(nextQuestion);
model.ApplicantId = applicantId;
model.QuestionNumber = (nextQuestion.ApplicantTestAnswers.Count + 1);
return View(model);
}
來自Question.cshtml:
@Html.HiddenFor(x => x.ApplicantId, new { id = "applicantId" })
@Html.HiddenFor(x => x.TestId, new { id = "testId" })
<div id="dialog" title="Question: @Model.QuestionNumber">
@Html.Partial("_NextQuestionPartial", Model)
</div>
@section scripts
{
<script type="text/javascript">
$(document).ready(function() {
$("#dialog").dialog({
dialogClass: "no-close",
autoOpen: true,
modal: true,
resizable: false,
height: 400,
buttons: {
'Next': function() {
}
}
});
});
</script>
}
從_NextQuestionPartial.cshtml:
@Ajax.BeginForm("Question", "Testing", new AjaxOptions { HttpMethod = "POST", InsertionMode = InsertionMode.Replace, UpdateTargetId = "nextQuestionContainer" })
{
<fieldset>
<legend>Question # @Model.QuestionNumber</legend>
<div id="nextQuestionContainer">
<p>Q: @Model.QuestionText</p>
<ul>
@foreach (var answer in Model.QuestionAnswers)
{
<li>
@answer.Answer
</li>
}
</ul>
</div>
</fieldset>
}
在Search.cshtml模態確認彈出罰款和確認按鈕調用TestingController問題的行動(與斷點VS驗證)。 applicantId和testId都填充了正確的值。 NextQuestionViewModel被正確創建並且返回View(模型)被調用,但是這正是我所迷失的事情發生的地方。我得到了這個異常:參數字典包含一個空方法'System.Web.Mvc.ActionResult Question(Int32,Int32)'的非空類型'System.Int32'的參數'applicantId'的空項。
但是,如果我直接從URL中將這些參數添加到querystring中,頁面將加載並且問題的模式彈出窗口會正確顯示。看起來這是一個路由問題,但我是MVC的新手,我無法理解爲什麼TestingController :: TakeTest中的RedirectToAction正在拋出有關applicantId的此異常,因爲我可以在操作方法Question中看到它的值。
等待。當你從頭到尾地執行這個過程時,是否會發生異常*只是在用戶在第**行確認測試後返回RedirectToAction(「Question」,「Testing」,...'**或者第一個問題成功顯示並*然後*拋出異常? – William
它發生在第一個問題顯示之前。使用Fiddler,我已經確定有2個調用操作方法。第一個來自我的TakeTest操作方法,然後是第二個(從ajax成功函數中的window.location.href行猜測)。第一個參數是querystring,第二個參數不是......因此錯誤。我不確定最好的方法來做這個重定向,所以也許它 – user1011627
如果我刪除了window.location.href,那麼對話框並沒有關閉,但是隻有第一個請求被執行(帶有查詢字符串參數),但是對話框保持不變打開重定向不會發生。如果我將$(this).dialog('close')添加到成功函數中,我得到一個javascript錯誤:「JavaScript運行時錯誤:無法在初始化之前調用對話框上的方法;試圖調用方法'關閉'」 確定如何關閉模式對話框,然後將其重定向到問題頁面。 – user1011627