Fork me on GitHub
基于Mvc3,Ef,领域驱动电子商务系统的EShop开发

基于Mvc3,Ef,领域驱动电子商务系统的EShop开发

最近做了2个小型的电子商务系统,最近的一个是自己带的项目,由于功能比较简单,业务关系又不是很复杂,所以想依靠了解许久但不觉深入的“领域驱动”思想自己,做一个开发的架构,完成之后希望在这里做一个记录:

今天只是个概述,希望以后有机会细致的展开。

1.大家都比较喜欢直接看层次图:

Domain.Entity存在上层领域比较关心领域实体,其中包含着自己的相应业务逻辑;

Domain.Respository中包含系统的数据持久处理,Interface提供相应的仓储接口及所有仓储类需要集成的公共仓储BaseRespository,其中包含都需要的基本的增删改查操作,对应的仓储接口则提供领域所关心的数据持久方法;

我这里仓储使用的是EF以及传统的Ado;

Service层主要提供了不太好归于各个领域实体本身的操作,在服务层进行相应的组合,如订单的提交,需要涉及到,诸如购物车商品状态的修改,商品虚拟库存的修改,用户身份等级及积分使用等,需要建立相应的OrderService进行组合封装,并且订单状态的改变,所带来相应领域实体的“状态回滚”。以及对于我等草根码农来说,快速修改代码及新功能新要求的满足,能够更好的找到单一修改代码的地方还是很方便的因为他就在OrderService中;

Web层使用的是MVC3,在上层来说相对于以前使用Mvc最大的特点就是知道尽量在Controller中写少的业务逻辑,不然我们又会回到以前WebForm时代点击一个Button后面有无数的逻辑及状态需要维护;web层中的Model更多的放了一些诸如第三方的API,以及实现的SSO,Cookie,Session的处理以页面所需要的ViewModel;

2.直接上代码(都是不全的代表了意思)

Domain.Respository

 

复制代码
namespace EShop.Domain {
    public interface IRespository<T> where T:class{
        IQueryable<T> All();
        T Create(T t);
        int Delete(T t);
        int Update(T t);
    }

    public class BaseResipository<T>:IRespository<T> where T:class
    {
       protected readonly DbContext Context;

       public BaseRepository(DbContext context)
       {
           Context = context;
       }

       public IQueryable<T> All()
       {
           return Context.Set<T>().AsQueryable();
       }

        public virtual T Create(T TObject)
       {
           var newEntry = Context.Set<T>().Add(TObject);
           Context.SaveChanges();
           return newEntry;
       }

        public virtual int Delete(T TObject)
       {
           Context.Set<T>().Remove(TObject);
           return Context.SaveChanges();
       }

        public virtual int Update(T TObject)
       {
            var entry = Context.Entry(TObject);
               Context.Set<T>().Attach(TObject);
               entry.State = EntityState.Modified;
               return Context.SaveChanges();
       }
    }
复制代码

实现仓储:

复制代码
namespace EShop.Domain
{
    public interface ItemRespository : IRespository<ItemEntity>
    {
        IEnumerable<dynamic> GetAllItems();
    }
}
复制代码

ItemRespository的实现:

复制代码
namespace EShop.Domain.Respository.RespsitoryContext {
    public class ItemEFRespository : BaseResipository<ItemEntity>, ItemRespository {
        private readonly ItemContext _context;

        public ItemEFRespository(ItemContext context)
           : base(context)
       {
           _context = context;
       }

        public IEnumerable<dynamic> GetAllItems()
       {
           return _context.Items;
       }
    }
}
复制代码
复制代码
        #region Cart

        /// <summary>
        /// 获取购物车明细里商品规格信息,根据商品sku编号
        /// </summary>
        /// <param name="ItemSkuId">商品sku编号</param>
        /// <returns></returns>
        public static string GetItemGgValue(int ItemSkuId)
        {
            string s = "";
            var queryResult = from i in _dp.mdc.SKU_Attribute_Value
                              where i.SKU_Id == ItemSkuId
                              select i;
            
            foreach(SKU_Attribute_Value sav in queryResult)
            {
                s += string.Format("{0}:{1};",sav.Attribute_Name,sav.Value_Name);
            }

            s = s.EndsWith(";") ? s.Substring(s.Length - 1) : s;
            return s;

        }

        public static int AddCart(newShopCar cart) 
        {
            _dp.mdc.newShopCar.InsertOnSubmit(cart);
            _dp.mdc.SubmitChanges();

            return cart.CartID;
        }

        public static int AddCartItem(newShopCartItem cartItem)
        {
            _dp.mdc.newShopCartItem.InsertOnSubmit(cartItem);
            _dp.mdc.SubmitChanges();

            return cartItem.CartItemID;
        }

        #endregion
复制代码

 

Domain.Entity:

复制代码
namespace EShop.Domain
{
    public class ItemEntity
    {
        #region 实体
        public int Itemid { get; set; }

        public string ItemName { get; set; }

        public float ItemPrice { get; set; }

        public int ItemCount { get; set; }
        #endregion

        ItemRespository _respository;
        public ItemEntity(ItemRespository Respository) {
            _respository = Respository;
        }

        #region 行为

        /// <summary>
        /// 获取指定商品
        /// </summary>
        /// <param name="itemID"></param>
        /// <returns></returns>
        public ItemEntity GetModel(int itemID)
        {
            return _respository.GetModel(itemID);
        }
        #endregion
    }
}
复制代码

Web层:

Controller:

复制代码
public class CartController : Controller
    {
        //
        // GET: /Cart/

        /// <summary>
        /// 商品添加至购物车
        /// </summary>
        /// <param name="id">itemID_count</param>
        /// <returns></returns>
        public ActionResult Index(string id)
        {
            //防Sql注入
            SqlChecker SqlChecker = new SqlChecker(this.Request, this.Response, Framework.Globals.SqlCheckRedirectUrl);
            SqlChecker.Check();

            //由Cookie中读取登录用户ID
            int _customerId = Framework.SSO.GetUid();
            int _itemID = 0;
            int _itemCount = 0;
            try
            {
                _itemID = int.Parse(id.Split('-')[0]);
                _itemCount = int.Parse(id.Split('-')[1]);
            }
            catch
            {
                return Content(string.Format("<Script language='javascript'>alert('{0}');history.go(-1);</Script>", "参数错误,非法访问URL!"));
            }

            try
            {
                ItemEntity item = new ItemEntity();
                item = item.GetModel(_itemID);

                ShopCartEntity shopCart = new ShopCartEntity();
                shopCart.AddItemToShopCart(_customerId, item);

                ShopCartViewModel v = new ShopCartViewModel();
                v.UserID = _customerId;
                v.ShopCartItem = shopCart.GetUserShopCart(_customerId);

                return View(v);
            }
            catch
            {
                return Content(string.Format("<Script language='javascript'>alert('{0}');history.go(-1);</Script>", "添加失败!"));
            }
        }

    }
}
复制代码

ViewModel:

复制代码
    public class ShopCartViewModel
    {
        public int UserID { get; set; }

        public List<ShopCartEntity> ShopCartItem { get; set; }

        public int ItemCount { get; set; }

        public float SumPrice { get; set; }
    }
复制代码
复制代码
        /// <summary>
        /// 首页
        /// </summary>
        /// <returns></returns>
        public ActionResult Index()
        {
            SqlChecker SqlChecker = new SqlChecker(this.Request, this.Response, Framework.Globals.SqlCheckRedirectUrl);
            SqlChecker.Check();
            HomeIndexViewModel v = new HomeIndexViewModel();

            v.HotProducts = ProductRules.GetHotProducts(5, "今日热销");
            v.RecommendProducts = ProductRules.GetHotProducts(5, "热点推荐");
            v.SecKillProducts = ProductRules.GetHotProducts(10, "秒杀专区");
            v.ZhiDeMai = ProductRules.GetHotProducts(10, "值得买");
            v.FeaturedProducts = ProductRules.GetFeaturedProducts(3); //精选区

            int userid = SSO.GetUid();

            return View(v);
        }
复制代码

由于项目时间比较短,所以有一些代码是直接用的以前的,掺杂在一起有时会显得比较混乱,也是第一次尝试“领域驱动”的开发,分享在这里,希望园子里的同学不管是架构方向的,领域驱动方向的,Mvc方向的针对于现有的层次提出宝贵意见,建议。小弟不剩感激。话说国足6:1新加坡,美国要对叙利亚动武了,生活再继续...

 

 
 
posted on 2013-09-08 22:07  HackerVirus  阅读(482)  评论(0编辑  收藏  举报