开发者

Please help on choosing the right arhitecture of n-tier web application

Please help on choosing the right way to use the entities in n-tier web application. At the present moment I have the following assembleis in it:

Please help on choosing the right arhitecture of n-tier web application

  1. The Model (Cust开发者_运维百科om entities) describes the fields of the classes that the application use.
  2. The Validation is validating the data integrity from UI using the reflection attributes method (checks data in all layers).
  3. The BusinessLogicLayer is a business facade for additional logic and caching that use abstract data providers from DataAccessLayer.
  4. The DataAccessLayer overrides the abstarct data providers using LinqtoSql data context and Linq queries. And here is the point that makes me feel i go wrong... My DataLayer right before it sends data to the business layer, maps (converts) the data retrieved from DB to the Model classes (Custom entities) using the mappers. It looks like this:

    internal static model.City ToModel(this City city)
    {
        if (city == null)
        {
            return null;
        }
    
        return new model.City
        {
            Id = city.CountryId,
            CountryId = city.CountryId,
            AddedDate = city.AddedDate,
            AddedBy = city.AddedBy,
            Title = city.Title
        };
    }
    

So the mapper maps data object to the describing model. Is that right and common way to work with entities or do I have to use the data object as entities (to gain a time)? Am I clear enough?


You could use your data entities in your project if they are POCOs. Otherwise I would create separate models as you have done. But do keep them in a separate assembly (not in the DataAccess project)

But I would not expose them through a webservice.

Other suggestions

imho people overuse layers. Most applications do not need a lot of layers. My current client had a architecture like yours for all their applications. The problem was that only the data access layer and the presentation layer had logic in them, all other layers just took data from the lower layer, transformed it, and sent it to the layer above.

The first thing I did was to tell them to scrap all layers and instead use something like this (requires a IoC container):

  • Core (Contains business rules and dataaccess through an orm)
  • Specification (Seperated interface pattern. Contains service interfaces and models)
  • User interface (might be a webservice, winforms, webapp)

That works for most application. If you find that Core grows and becomes too large too handle you can split it up without affecting any of the user interfaces.

You are already using an ORM and have you thought about using a validation block (FluentValidation or DataAnnotations) for validation? Makes it easy to validate your models in all layers.


It may be a common practice to send out DTOs from serivce boundary (WCF service, etc.) but if you are directly using your "entities" in your presentation model, I don't see any benefit in doing that.

As to the code snippet you have provided, why not use AutoMappter? It helps by eliminating writing of boiler-plate mapping codes and does that for you if you have a set of convention in place.


Get rid of the model now, before removing it later will require refactoring the whole application. The last project i worked on used this architecture and maintaining the DTO layer and mappings to the database model layer is a huge pain in the arse and offers no usefull benefits. One of the main things that is anoying is that LinkToSql does not effectively support a disconnected data model. You cannot update a database table by creating a new DB entity with a primary key matching an existing record and then stick it into the data context. You have to first retrieve the entity from the database, update it then commit the changes. Managing this results in really nasty update methods to map all the properties from your DTOs to your LinqtoSql classes. It also breaks the whole deferred execution model of LinqToSql. Don't even get me started on the problems it causes with properties on parent classes that are collections of child DTOs (e.g. a customer DTO with an Orders property that contains a collection of order DTOs), managing those mappings is really really fiddly, i had to do some extensive optimisations because retrieving a few hundred records ended up causing LinqToSql to make 200,000 database calls (admittedly there was also some pretty dumbass code as well but you get the picture).

The only valid reason to use DTOs is if you want to have multiple pluggable Data Access Layers e.g. LinqToSql and NHibernate for supporting different DB servers. That way you can swap out the data access later without having to change any other layers. If you don't need to do this then save yourself a world of pain and just use the LinqToSql entities.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜