ASP.NET MVC 2.0: Making the POST Action receive my Model's sub-models
I'm trying to reuse some existing Models (and especially the Load/Save functions associated with them), so I've aggregated them into the current Model:
public class EditModel {
public SubModel1 {get; set; }
public SubModel2 {get; set; }
/* ID and some text fields */
}
The problem is, after I fill the form and hit submit, in the Action associated with POST these sub-models all have default/empty content.
/// POST for Edit
[OutputCache(NoStore = true, Duration = 0, VaryByParam = "*")]
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult EditCommunity(EditCommunityModel model) {
if (bad stuff happened)
return Json("Failure");
//model.SubModel1 is != null, but all fields are empty.
// ID and the aforementioned text fields come correctly.
Save(model.ID, model.SubModel1, model.SubModel2);
return Json("Succeeded");
}
I've done this reuse before without problems, when using an .aspx for the Edit equivalent, and would therefore call a GET Action to properly construct the Model. But now I'm restricted to an ascx, because I'm trying to edit in a modal dialog (if there's a way to load an aspx in a div, then this problem is over; but it occurs to me this would be contrary to what an aspx is intended for.)
开发者_运维问答This is, in short, what I'm trying to do; I'll also add two strategies I've tried to apply, both of which have the same effect: empty sub-models.
First try used an AJAX call to populate Edit.ascx.
In Edit.ascx
, the wrapper for edit dialog was included in Manage.aspx, and the EditModel was passed without any initialization
<div id="editDialog" style="display: none;">
<% Html.RenderPartial("Edit", new EditModel()); %>
</div>
In the grid, a cell would be marked as edit, and on click would call the following javascript function:
function onSelectRowEdit_Click(id) {
if (id) {
//Get data from selected row
var ret = jQuery("#table_grid").getRowData(id);
//Show Edit modal control
var actionUrl = '<%= Url.Action("EditInfo", "Manage") %>';
var data = "externalId=" + ret.OrgId + '&Id=' + ret.Id;
$.ajax({
type: "POST",
url: actionUrl,
data: data,
error: AjaxError,
success: ShowEdit
});
}
}
EditInfo(string, string)
would create and return a JsonResult, which was then received by ShowEdit; showEdit would fill Edit.ascx and use jQuery to present the div as a dialog:
function ShowRes(ret) {
$("#form_Edit").validate();
jQuery("#editDialog").dialog('destroy');
Init_EditDialog();
/* $('#...').val(ret...);, many times over */
//Show Dialog
$("#editCommunityDialog_Content").show();
$("#editCommunityDialog").dialog('open');
}
Second try attempted to bypass new EditModel()
, and to use a View returned by a Controller. It did achieve exactly what the first try did, with significantly less code, but had the same issue on Submit.
<div id="editDialog" style="display: none;"></div>
<!-- ... -->
function onSelectRowEdit_Click(id) {
if (id) {
//Get data from selected row
var ret = jQuery("#table_communities").getRowData(id);
//Show Edit community modal control
var actionUrl2 = '<%= Url.Action("ShowEdit", "Manage",
new { CommunityId="_COMMID_", ExternalId="_ORGID_" }) %>';
editImg = editImg.replace("_COMMID_", ret.Id);
editImg = editImg.replace("_ORGID_", ret.OrgID);
$.ajax({
type: "POST",
url: actionUrl2,
data: data,
error: AjaxError,
success: ShowRes
});
}
}
ShowEdit was rewritten to return View("Edit", model)
, and ShowRes would simply write the result to the div's html.
function ShowRes(ret) {
//...
$("#editDialog_Content").html(ret);
//Show Dialog
}
Needless to say, the form in Edit.ascx
has fields like <%= Html.HiddenFor(m => m.SubModel1.EditProfile)%>
so that's not where the problem comes from.
Try checking out my answer in this question to see if that helps: How to handle `PartialRender` Models?
精彩评论