G'day,
I need some guidance on writing unit tests for MVC controllers. I've created a controller that populates a view correctly, allows information to be saved but fails on the [Post] UpateModel(list,collection) method. Now I suspect its related to a known CSLA bug https://github.com/MarimerLLC/csla/issues/19. , but as this architecture is not my normal solution style, I want to fall-back into unit tests to isolate the offending code.
I just can't work out how to write appropriate MVC+CLSA Controller unit tests in any sane way? Please help.
Sample code that works around the issue.
public class DataSchemaMappingController : Csla.Web.Mvc.Controller
{
/// <summary>
/// Default page population with data entry on left and menu of alternative options on the left side of the page.
/// </summary>
/// <param name="id"></param>
/// <returns></returns>
public ActionResult Index(int id)
{
ViewData.Add("Files", FinServices.Contacts.Business.DataFileList.GetAll());
ViewData.Add("FieldDefinitions", new SelectList(FieldDefinitionList.GetAll(), "FieldDefinitionId", "FieldTitle"));
ViewData.Model = GetListByFileId(id);
return View();
}
/// <summary>
/// Code to save the collection of data that the user could edit
/// POST: /DataSchemaMapping/Edit/5
/// </summary>
/// <param name="id"></param>
/// <param name="collection"></param>
/// <returns></returns>
[HttpPost]
public ActionResult Index(int id, FormCollection collection)
{
ViewData.Add("Files", FinServices.Contacts.Business.DataFileList.GetAll());
ViewData.Add("FieldDefinitions", FieldDefinitionList.GetAll());
// -- new SelectList(FieldDefinitionList.GetAll(), "FieldDefinitionId","FieldTitle",Model.MappedFieldDefinitionReferenceId))
var list = GetListByFileId(id);
// Looks like there is a shortcoming in the CSLA MVC approach for Parent/Child collections see: https://github.com/MarimerLLC/csla/issues/19
//UpdateModel(list, collection);
// LL: Looks like this is a safe alternative to UpdateModel method above, but still fails with ChildCollection propblem.
//TryUpdateModel(list,collection);
int i = 0;
// Search through the form collection for a specific field.
// keys will be in the form [##].PropertyName or [GUID].PropertyName
foreach (var key in collection.AllKeys.Where(k => k.EndsWith("MappedFieldDefinitionReferenceId")))
{
// TODO: Review if we should we also be checking the [##] key prefix?
// ASSUMPTION: We are making an assumption that the DataPortal is retrieving Child collections in the same order, so a simple loop to populate is valid logic.
if (collection.GetValue(key).AttemptedValue != null)
{
// TODO: Work out how to make the left side of this generic (esentially side stepping MVC [Try]UpdateModel code).
list.MappedFieldDefinitionReferenceId = Convert.ToInt32(collection.GetValue(key).AttemptedValue);
}
else
{
list.MappedFieldDefinitionReferenceId = null;
}
i++;
}
i = 0;
foreach (var key in collection.AllKeys.Where(k => k.EndsWith("ColumnTitleSuppliedInDataFile")))
{
// TODO: Review if we should we also be checking the [##] key prefix?
// ASSUMPTION: We are making an assumption that the DataPortal is retrieving Child collections in the same order, so a simple loop to populate is valid logic.
if (collection.GetValue(key).AttemptedValue != null)
{
// TODO: Work out how to make the left side of this generic (esentially side stepping MVC [Try]UpdateModel code).
list.ColumnTitleSuppliedInDataFile = collection.GetValue(key).AttemptedValue.ToString();
}
else
{
list.ColumnTitleSuppliedInDataFile = null;
}
i++;
}
SaveObject(list, true);
return View();
}
}
Copyright (c) Marimer LLC