1

I have a section of code in my MVC controller that works fine during run-time, but during testing fails. I do a call to the context with an include. During run-time, I can check thisCall and see that thisCall.CallForContentCustomForm is not null. But debugging during testing, it is null.

My models:

public partial class CustomForm : BaseEntity
{

    [Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)]
    public Guid CustomFormId { get; set; }
    //...
}

public class CallForContent : BaseEntity
{
    [Key, ForeignKey("CallForContentResource"), DatabaseGenerated(DatabaseGeneratedOption.None)]
    public Guid CallForContentId { get; set; }

    //...
    public Guid CallForContentFormId { get; set; }

    [ForeignKey("CallForContentFormId")]
    public CustomForm CallForContentCustomForm { get; set; }
}

In my controller:

public partial class ProjectController : BaseController
{
    private IMkpContext db;

    #region "Constructor"

    public ProjectController()
    {
        db = new MkpContext();
    }

    public ProjectController(IMkpContext dbContext)
    {
        db = dbContext;
    }

    #endregion

    public virtual ActionResult callforcontentedit(Guid? id)
    {
        var thisCall =
            db.CallForContent
                .Include(cfc => cfc.CallForContentCustomForm)
                .Include(cfc => cfc.Project)
                .FirstOrDefault(cfc => cfc.CallForContentId == id);
        // At this point during run-time thisCall.CallForContentCustomForm has a value,
        // but is null during testing

        // This row does return the expected result during testing.
        var customForms = db.CustomForms.Where(c => c.IsActive && c.CustomFormId == thisCall.CallForContentFormId);

        if (thisCall == null) return RedirectToAction("Index", "Submission");

        var viewModel = Mapper.Map<CallForContentViewModel>(thisCall);
        // ...
        ViewBag.Title = viewModel.CallForContentCustomForm.FormName; // Fails here during tests
    }
}

In my testing setup, I do add data to the FakeDbContext for the CustomForm table.

        var newCallForContentForm = FakeCallForContentForm(newProfile.ProfileId);
        fakeDb.CustomForms.Add(newCallForContentForm);
        //...

        var newCallForContentProposalForm = FakeCallForContentProposalForm(newProfile.ProfileId);
        fakeDb.CustomForms.Add(newCallForContentProposalForm);

My Test:

[TestMethod]
public void Project_CallForContent_Test()
{
    // Arrange
    var fakeDb = TestFakes.SetupFakeDbContext();
    var controller = TestFakes.ProjectController(fakeDb);

    // Act
    var result = controller.callforcontentedit(fakeDb.CallForContent.FirstOrDefault().CallForContentId) as ViewResult;

    // Assert
    Assert.IsNotNull(result);
}

Here is what my context looks like:

public class FakeMkpContext : AuditDbContext, IMkpContext
{
    #region Constructors

    static FakeMkpContext()
    {
        Database.SetInitializer<FakeMkpContext>(null);

    }

    public FakeMkpContext() : base("Name=FakeMkpContext")
    {
        this.Profile = new FakeProfileSet();
    }

    #endregion

    #region Property (Dbset)

    public IDbSet<Address> Address { get; set; }
    public IDbSet<Keyword> Keyword { get; set; }
    public IDbSet<CustomForm> CustomForms { get; set; }
    public IDbSet<SubmittedForm> SubmittedForms { get; set; }
    public IDbSet<SubmittedFormData> SubmittedFormData { get; set; }

    public IDbSet<Project> Project { get; set; }
    public IDbSet<ProjectType> ProjectType { get; set; }

    public IDbSet<CustomFieldGroup> CustomFieldGroup { get; set; }
    public IDbSet<CustomFormGroup> CustomFormGroup { get; set; }
    public IDbSet<CallForContent> CallForContent { get; set; }
    #endregion
    //...
}

I am not using Moq for the entity framework portion of my tests.

M Kenyon II
  • 4,136
  • 4
  • 46
  • 94

0 Answers0