public ActionResult Add(int?id = 0)
        {
            var model = new AddCategory();

            // Get category tree
            IList <CategoryNode> nodes = new List <CategoryNode>();

            CategoryHierarchy.AppendChildCategories(ref nodes, null);

            // Generate select list items
            model.SelectCategoryItems = nodes.Select(x => new SelectListItem
            {
                Text     = StringExtensions.Repeat("\xA0", x.Level * 4) + x.CategoryName,
                Value    = x.CategoryId.ToString(),
                Selected = (x.CategoryId == id)
            }).ToList();

            // Add top root category
            model.SelectCategoryItems.Insert(0, new SelectListItem
            {
                Text     = "-- Chọn loại hàng cha--",
                Value    = "0",
                Selected = (id == null || id == 0)
            });

            return(View(model));
        }
        //[OutputCache(Duration = 900, VaryByParam = "parrentId")]
        public JsonResult GetCategoryTree(int parrentId = 0)
        {
            try
            {
                IList <CategoryNode> categories = new List <CategoryNode>();
                if (parrentId == 0)
                {
                    // get root category tree
                    CategoryHierarchy.AppendChildCategories(ref categories, null);
                }
                else
                {
                    // get parrent category
                    var parrentNode = db.Categories.Where(c => c.CategoryId == parrentId).Select(x => new CategoryNode
                    {
                        CategoryId    = x.CategoryId,
                        CategoryName  = x.CategoryName,
                        Description   = x.Description,
                        ParrentId     = x.ParrentId,
                        SortIndex     = x.SortIndex,
                        TotalProducts = 0,
                        Level         = 0
                    })
                                      .FirstOrDefault();

                    // append child categories
                    if (parrentNode != null)
                    {
                        categories.Add(parrentNode);
                        CategoryHierarchy.AppendChildCategories(ref categories, parrentNode);
                    }
                }

                // calculate category products
                foreach (var node in categories)
                {
                    node.TotalProducts = CategoryHierarchy.CountCategoryProducts(node.CategoryId);
                }

                return(Json(new
                {
                    Success = true,
                    Message = "Get category tree success",
                    Categories = categories
                }));
            }
            catch (Exception ex)
            {
                // Write error log
                var log = new Log();
                log.LogDate = DateTime.Now;
                log.Action  = "Category - GetCategoryTree()";
                log.Tags    = "Error";
                log.Message = ex.ToString();
                db.Logs.Add(log);

                return(Json(new { Success = false, Message = ex.Message }));
            }
        }
        public ActionResult Edit(int id)
        {
            var model = new EditCategory();

            try
            {
                var category = db.Categories.Where(c => c.CategoryId == id).FirstOrDefault();
                if (category != null)
                {
                    model.CategoryId   = category.CategoryId;
                    model.CategoryName = category.CategoryName;
                    model.Description  = category.Description;
                    model.ParrentId    = category.ParrentId;

                    // Get category tree
                    IList <CategoryNode> nodes = new List <CategoryNode>();
                    CategoryHierarchy.AppendChildCategories(ref nodes, null);

                    // Generate select list items
                    model.SelectCategoryItems = nodes.Where(c => c.CategoryId != model.CategoryId).Select(x => new SelectListItem
                    {
                        Text     = StringExtensions.Repeat("\xA0", x.Level * 4) + x.CategoryName,
                        Value    = x.CategoryId.ToString(),
                        Selected = (x.CategoryId == model.ParrentId)
                    }).ToList();

                    // Add top root category
                    model.SelectCategoryItems.Insert(0, new SelectListItem
                    {
                        Text     = "-- Chọn loại hàng cha--",
                        Value    = "0",
                        Selected = (category.ParrentId == null)
                    });

                    return(View(model));
                }
                else
                {
                    ModelState.AddModelError("", "Không tìm thấy danh mục chỉnh sửa.");
                }
            }
            catch (Exception ex)
            {
                ModelState.AddModelError("", ex.Message);

                // Write error log
                var log = new Log();
                log.LogDate = DateTime.Now;
                log.Action  = "Category - Edit()";
                log.Tags    = "Error";
                log.Message = ex.ToString();
                db.Logs.Add(log);
            }
            return(View(model));
        }