I know this sound strange - allow me to explain:
I’m currently developing a standard web application with database. I chosen to utilize IoC framework (Ninject), Entity Code First, Bootstrap and few other related technologies. I have transcribed a database model in UML and now I’m trying to implement it, step by step. This usually goes like this:
First question is - does the above looks “normal” to you? Perhaps I’m missing something that could speed up my development ? Or perhaps I should add some more steps to - for example - catch more errors early on?
Now the next step is to create Views, so I do something like this:
The problem with above approach is:
I often have to create nearly a duplicate of POCO entity, then - during save procedure, I need to convert it back to the appropriate POCO entities, usually like this:
PocoEntity1 pocoEntity1 = new ()
{
UserName = ViewModel.UserName,
UserPicture = ViewModel.UserPicture
(and so on)
}
The above is pretty time consuming and error prone - on the other hand, if I would use POCO directly, I would have to add a lot of attributes like:
[Required]
[StringLength(128)]
[DisplayNameLocalizer("FirstName", typeof(TranslationStrings))]
and this is not recommended (and I sometimes want to have different name for some attributes, depending on the View).
Question is - isn’t there anything “in between” ? For example, something that would allow me to convert ViewModelEntity directly to POCO entity would be really helpful. Is there anything I can do to speed things up, or am I doing things the correct way as it is right now?
I'm sure someone will say to use the build-in controller scaffolding for entity framework, but my experience building real world MVC apps is that the build-in scaffolding is nice for hobby projects and POC, but always falls way short in the real world. You could build your own scaffolding functions, but this is not something I have tried before.
To answer your question about the "in between", e.g. mapping your viewmodel to POCO, I highly recommend using a mapper library like AutoMapper for this. You controller code then ends up something like this (not tested for syntax errors):
[HttpPost]
public ActionResult Edit(int id, YourViewModel model)
{
if (ModelState.IsValid)
{
var poco = repository.getPoco(id);
Mapper.Map<YourViewModel, YourPoco>(model, poco);
repository.Save();
return RedirectToAction("List");
}
return View(model)
}
... does the above looks “normal” to you?
It looks like normal for me. Another approach would be to create the Unit tests first. The Statement "no time for unit test" is very bad. I think it's simply not true.
Let me explain this: If you implement a feature without unit test, than you often do not find simple bug early. And this means you need at the end more time to implement it, because you can add certain time to fix the bugs right after you implement the feature.
- Check what database tables are required.
- Generate new database using migration tool
The 2. and 4. point are not really required. Imagine that you can use a simple "in memory" storage first (... can also be used for unit tests). You can really create the database and tables later.
often have to create nearly a duplicate of POCO entity, then - during save procedure, I need to convert it back to the appropriate POCO entities, usually like this:
PocoEntity1 pocoEntity1 = new () { UserName = ViewModel.UserName, UserPicture = ViewModel.UserPicture (and so on) }
I really agree with you this is sometimes cumbersome. But.. there is a solution. Use for that AutoMapper (There is a nuget package for it)
The above is pretty time consuming and error prone - on the other hand, if I would use POCO directly, I would have to add a lot of attributes like:
[...]
and this is not recommended (and I sometimes want to have different name for some attributes, depending on the View).
For this, there is another nice helper library out there: Fluent Validation (MVC)
This simply allows you to create validators for you view models. With that you can create many validators for the same view model - without decorating any model directly.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With