user1075940
user1075940

Reputation: 1125

Elegant way to update model

Lets say I have a model with more then 20 properties.

Some of them can be edited in a view by the user, however for security reasons data like passwords are not kept in hidden fields, so when I post view model to controller some properties are nulls

How to check which properties changed without writing too much code?

bad idea:

    [HttpPost]
    public ActionResult Edit(BigModel model)
    {
        BigModel old=db.Get(new.id);
        if(model.Property1 !=null && old.Property1 != model.Property1) old.Property1=model.Property1
        if(model.Property2 !=null && old.Property2 != model.Property2) old.Property2=model.Property2
        if(model.Property3 !=null && old.Property3 != model.Property3) old.Property2=model.Property2
        ...
        if(model.Property20 !=null && old.Property20 != model.Property20) old.Property20=model.Property20
    }

Upvotes: 1

Views: 238

Answers (2)

GraemeMiller
GraemeMiller

Reputation: 12273

Have a look at using a ViewModel and something like AutoMapper. AutoMapper lets you take Domain Model and convert them to other format using a convention based approach. E.g. If you had a DateTime property called Start on your domain model and a ViewModel field called Start it would copy the value of Start in your Domain model to Start in your ViewModel just based on names matching. You can do more complex mappings like Start in domain model to StartYear in ViewModel etc.

A ViewModel should incorporate the display fields and the fields you want to post (possibly as a child edit model). Then post back to an EditModel.

The EditModel will only contain the fields you want to update. This can then be mapped back to your domain model or be done manually.

You can see a summary of it here. This Stack question and answer also illustrate the technique

Upvotes: 2

scartag
scartag

Reputation: 17680

You should use a viewmodel with the exact fields you have on the view (the non sensitive ones) and then call TryUpdateModel(old) the runtime will map the fields in your viewmodel to your model and you need not worry about fields that don't change .. EF will not mark them as changed if the values are the same.

  [HttpPost]
    public ActionResult Edit(BigViewModel model)
    {
        BigModel old=db.Get(new.id);

        UpdateModel(old);

        //db.SaveChanges();

    }

You may want to invest in a profiler to see what EF is doing when you send a query and what sql it is generating .. you could try ORM profiler or EFProf ... if you don't care for paid tools you could try Glimpse (Glimpse.EF).

Upvotes: 1

Related Questions