領域驅動設計-從貧血模型到充血模型

背景

領域模型對象只是用來存儲應用的數據。業務邏輯位於服務層中,管理域對象的數據。在服務層中,應用的每個實體對應一個服務類。這種模式大家是不是很熟悉,尤其是在中小項目或者項目剛啓動的時候,都是怎麼方便怎麼來;沒錯,這就是貧血模型。

一般畫風是這樣的。

1、Web層:接收用戶輸入,將數據傳至服務層;

2、服務層:處理業務邏輯、權限管理與授權,並與存儲層通信;

using BQoolCommon.Interface.Repository.Dapper;
using BQoolCommon.Interface.Service;
using BQoolCommon.Models.BQoolCommon_SetMain;
using BQoolCommon.Models.Enum;
using BQoolCommon.Models.ViewModel;
using System;
using System.Collections.Generic;
using System.Configuration;

namespace BQoolCommon.Service
{
    public class UserPermissionService : IUserPermissionService
    {
        private readonly IInnerSiteMapDapperRep _innerSiteMapDapperRep;

        private readonly IInnerSiteMapService _innerSiteMapService;
        private readonly IAccountChannelRelService _accountChannelRelService;
        private readonly IUserMgmtService _userMgmtService;

        public UserPermissionService(
            IInnerSiteMapDapperRep innerSiteMapDapperRep,
            IInnerSiteMapService innerSiteMapService, 
            IAccountChannelRelService accountChannelRelService, 
            IUserMgmtService userMgmtService)
        {
            _innerSiteMapDapperRep = innerSiteMapDapperRep;
            _innerSiteMapService = innerSiteMapService;
            _accountChannelRelService = accountChannelRelService;
            _userMgmtService = userMgmtService;
        }
.................................................

3、存儲層:與數據庫進行通信,對數據進行持久化;

using System.Linq;
using BQoolCommon.Interface.Factory;
using BQoolCommon.Interface.Repository.Entity;
using BQoolCommon.Models.BQoolCommon_SetMain;
using BQoolCommon.Models.ViewModel;

namespace BQoolCommon.Repository.Entity
{
    public class WeChatSubscribeEntityRep : GenericEntityRep<WeChat_Subscribe>, IWeChatSubscribeEntityRep
    {
        public WeChatSubscribeEntityRep(IBqoolSetMainDbContextFactory factory) : base(factory)
        {
        }
    }
}

問題窺探

問題出在了服務層,他承受了太多的職責,像業務邏輯、權限檢查等等,這違反了單一職責原則,併產生了大量的依賴。當業務複雜度上升時,服務層所包含的代碼將會非常龐大和複雜。服務層需要包含應用邏輯、用戶會話的管理;領域層應該包含業務邏輯,可以處理與業務相關的會話狀態。

改進思路

我們需要將業務邏輯從服務層移動到領域模型中,這樣的好處是,服務層可以只負責應用邏輯(如數據有效性驗證、授權檢查、開始結束事務等),領域模型可以專門負責其相關的業務邏輯。以電商系統來舉例,架構設計時完全可以針對訂單、商品、庫存等多個領域模型進行建模,相關的業務可以分別放到不同的領域模型中,一些很有可能重複的業務代碼都會被集中到一處,從而降低了複製-粘貼的可能性,這就是充血模型。

影響

充血模型將服務類變得更小,使之只負責單一的職責。例如商品的CRUD和其他操作,就可以將其放到兩個不同的服務類中,一個負責商品的CRUD操作,另外一個負責與商品相關的其他操作。這樣就能使服務類變得小巧、鬆散、可測試了,同時還能降低其他人理解與重用的成本。

總結

1、從規範和長遠來看肯定是充血模型合適些。

2、但是如果只是小項目、求快的話,當然是開發成本低的貧血模型。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章