Gurus,
Am newbie in MVC. I am developing a web application for an Order Management System. I have devised architecture to have the following projects as part of my solution:
Client (Presentation layer, MVC)
CrossCuttingServices ( framework components like logging, caching, Data, Class lib)
Data (Entity framework layer for DB interation, C# class lib)
Services (Services layer to be consumed by Presentation, Web API)
Q1. My question is, where should I create my entity classes or Models, which will be used across Presentation to Services to Data? Either in models of Presentation or in Web API service layer or as a seperate project (C# library)?
Q2. Also, let me know is there any generic implementation to invoke WebAPI services from Presentation controller.
Q1: You will be using the same entities throughout the entire solution so I recommend storing them in your Data project since it keeps all database related stuff bundled together separately from the remaining logic.
Q2: You could always send a request to the APIs to get the resulting data, it's essentially what they're there for.
I have decided to go with Architecture like
1. JS Enabled Presentation (webform or only HTML + JS)
2. Web API (Controller calling data services (EF+Repo) as my service layer for data, it can support my browser based front end and devices
Let me know any drawbacks on same
We have a similar problem, with a pretty complex domain model. As a result we have opted for
data entity models defined in a separate DomainModel DLL
UI mapper classes that map from datamodel to UI models
WebAPI mapper classes that map from datamodel to WebAPI models
An example of why we want this?
UI has concept of distributor catalogue item, which is a specialisation of catalogue item
WebAPI uses the basic catalogueitem datamodel, but then returns different data based on the specific resource [eg a search URL returns item ID and basic info; an item lookup URL returns full details for the catalogue item.
As a result of the above, the catalogueitem in our DomainModel is the full complete object, which the different "clients" then map as they see fit.
[This is in line with what Filip Stankovski said above]
Related
Right now I have a few layers to my project: Core <> Repository <> API... and I'll be building a "client" MVC web project layer. My question is - where do viewModels belong in this architecture?
Should the controller methods of the Web Project call the API (multiple times - getTheseObjects, getThoseObjects) to get data, and then build the viewModel? Or should the API support calls to construct the viewModel so that only one API call (getAllObjectsForThisPage) needs to be made per page for the application?
Your view models will belong in your client MVC app. They will be specific to the views in that individual client application, and usually will get populated by domain objects.
This is how it can work: the controller mediates the https requests thus calls a API endpoint and receives some data or domain objects, which in turn you use to populate your view models.
Take a look at automapper if you are returning domain objects from your api, it really helps with mapping domain object to view models.
You can place ViewModels into your MVC application, but you could create something that is called DTO (Data Transformation Object) and return that from Web API to your client. In essence it will be a class with only the necessary information that you pass to the client. If you want to call that ViewModel you might as well go ahead and call it like that. My suggestion would be to issue one call and to return all the necessary information. One call one trip.
My practice usually is to separate ViewModel from MVC and store it in some other project. The service layer would prepare a ViewModel and return it to MVC. The reason for this is that once I had a requirement to build WPF application after MVC was completed. It was quite a pain moving things around and retesting everything to make sure that it still works fine.
I'm about a month into MVC and from what I understand, a pretty good approach to app architecture is:
MVC <> Service <> Repository <> Core
Within MVC we have Views, and Controllers to populate viewModels for the controllers. My question is: Where exactly to Data Transfer Objects come in? I'm building a single-page web app and I'm trying to do it right from the beginning.
From the reading I've done, I should use DTOs to "flatten" the Model objects before passing them into the ViewModel. Do they act as a "only data that I need" object that gets passed from the service to the controller, at which point the viewModels are constructed? If so, is it generally true that each model definition (ie Sets, Cards, Users) should have corresponding DTO classes in the Core layer? Any clarifications here would be awesome, thank you for your time!
First of all, about this phrase: "a pretty good approach to app architecture is...": I don't believe there is a single good approach to all apps, and I would prefer always to use the simplest approach (i.e. fewer layers) that could solve your problem at hand.
When you say "Service", it appears to be a whole layer of web services, rather than just some domain service classes; in most cases I've seen with Asp.Net MVC, the controller itself can fulfill the role of a service, thus eliminating the need to add yet another layer. Of course there are exceptions, just be sure your reason to increase complexity is legitimate.
About DTO's and View models: DTO's, like you described, flatten the object model and return "only data that I need". DTO is a more generic term, usually used with web services where you don't know who is the consumer. Think of (Asp.Net MVC) View Models as a more specialized kind of DTO, that returns "only data that THE VIEW needs". Thus, if you don't need an extra layer of services, you also don't need an extra layer of DTO's, just use View Models to flatten the domain classes directly and return them from your controllers.
In fact, for very simple applications, even the separation of Models x ViewModels is overkill - it is possible to use a single Model layer to fulfill both roles, with the help of the ViewBag. I don't know your requirements, so I can't say which is better for you.
Finally, one comment: if you must build a single page application, Asp.Net MVC is not the best tool for the job. I'd recommend using Asp.Net Web Api (only services, no views) at the server and a client mvc framework, such as BackboneJs or AngularJs.
How would I go about abstracting the membership information in MVC3 c#
Currently the membership data is kept on a localhost SQL server and is linked to MVC via the Entity Framework.
As I want to perform some extensions, I need to abstract it, creating an interface and class for each entity in the SQL database?
Where would I start? Are there any examples available? I can only find ones that are out of date or irrelevant
I think you can rearrange your application, introducing a service layer separated from your presentation layer. The object model (domain model) that you define in the presentation layer for User and other entities should be distinct from the EF data model, so you need only that some sevices ( for example you can implement these as Web Services) read the data using EF and populate your domain model of the presentataion layer.
This approach allows your application to be more flexible to future changes or extensions.
The project I'm currently working on has a Core API which is used by everything: services, web, ...
This API has following layers:
Core
Core.Models
Core.DataProviders
Core.DataProviders.LinqToSql
Core.Utils
On top of this API is my ASP.NET MVC application. This looks like this:
Web
Web.Models (Some Web specific objects and logic. For example a class which builds a list of quarters to help me render a day in a scheduling table.)
Web.Extensions (Html Helpers, Controller base..)
Web.ViewModels (Composite objects to pass to the View.)
Web.Services (Layer which communicates with the Core and Web.Models. This layer builds ViewModels for my Controllers. Helps keeping my Controllers clean.)
Any serious flaws in this setup?
A more specific question: I need to parse some things coming from my View before I can pass them to the Core. Should I handle this in the Controller or in the Service layer?
Generally speaking data submitted from the view should be parsed by a ModelBinder, falling back to the Controller if using a ModelBinder doesn't seem to make sense.
Parsing in an application service makes sense if multiple sources can submit the data in the same format (like web service or file system persistance).
Are there any tutorials/examples on how to create an asp.net mvc app without the model being managed by a database (through linq2sql or entity framework).
I've to create a frontend for a server which has a json based api. I would like to use mvc 3 or 2 and have most of the features of mvc still in place (like data annotation and validation).
Any tutorials or examples on how to do this? I tried to search them but all examples i find are based on entity framework or linq.
I agree that most of the examples/tutorials out there are using entity framework. This being said the process would be similar:
Create your model classes.
Create a repository working with those model classes. This repository should implement an interface which contains all the operations you need with those models like GetUser, SaveUser, etc... In the implementation you connect to the remote JSON API server to fetch data.
You create a controller which takes the repository interface in the constructor. Setup a custom controller factory so that a DI framework could provide instances of your controllers.
Define views and view model classes.
Controller actions talk to the repository via the provided interface to fetch models, maps those models to view models and returns them to the corresponding view to be shown.
Useful tools:
MvcContrib (many useful helpers)
AutoMapper (for mapping between models and view models)
FluentValidation.NET (for validating models)
MVC 3 has extra support for JSON which you might want to look into.
Or use the futures with MVC 2.