using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using Service;
using Domain;

namespace WebSite.Controllers
{
    public class SysRoleGroupController : BaseController
    {
        private const int AuthorityID = 55;
        public ISysRoleManager SysRoleManager { get; set; }
        public ISysUserManager SysUserManager { get; set; }
        public ISysAuthorityManager SysAuthorityManager { get; set; }
        public ISysHotelGroupManager SysHotelGroupManager { get; set; }
        public ISysHotelManager SysHotelManager { get; set; }

        #region Action

        [Authorize]
        public ActionResult Index()
        {
            return View("SimonIndex");
        }

        [Authorize]
        public ActionResult Edit(int? id)
        {
            if (id.HasValue)
            {
                return View(SysRoleManager.Get(id));
            }

            return View(new SysRole { ID = 0, Name = "", Sort = 1, Remark = "" });
        }

        //[Authorize]
        //public ActionResult LoadAllByPage(int page, int rows, string order, string sort)
        //{
        //    long total = 0;
        //    var list = this.SysRoleManager.LoadAllByPage(out total, page, rows, order, sort);

        //    var result = new { total = total, rows = list };

        //    return Json(result);
        //}
        /// <summary>
        /// 装载到下拉框控件
        /// </summary>
        /// <param name="groupId"></param>
        /// <returns></returns>
        [Authorize]
        public ActionResult LoadAll(int? groupId)
        {
            //装载只有在该酒店分组下，且已授权访问酒店下的角色
            SysUsers user = this.SysUserManager.Get(User.Identity.Name);//当前用户角色不装载出来
            IList<SysRole> roles = SysRoleManager.LoadAll().Where(r => r.ID != 1 && r.ID != user.Role.ID && r.HotelID == 0 && r.SysHotelGroup.ID != user.SysHotelGroup.ID).OrderBy(o => o.Sort).ToList();
            if (groupId.HasValue && groupId != 1)
            {
                roles = roles.Where(r => r.SysHotelGroup.ID == groupId || (r.SysHotelGroup.Parent != null && r.SysHotelGroup.Parent.ID == groupId)
                    || (r.SysHotelGroup.Parent != null && r.SysHotelGroup.Parent.Parent != null && r.SysHotelGroup.Parent.Parent.ID == groupId)).ToList();
            }
            IList<object> result = new List<object>();
            foreach (SysRole role in roles)
            {
                result.Add(new { ID = role.ID, Name = role.Name });
            }
            return Json(result);
        }
        /// <summary>
        /// 角色管理主页面显示：只能装载自己所属分组的子分组的角色
        /// </summary>
        /// <param name="groupId"></param>
        /// <returns></returns>
        [Authorize]
        public ActionResult LoadAll2(int? groupId)
        {
            IList<object> result = new List<object>();
            try
            {

                SysUsers user = this.SysUserManager.Get(User.Identity.Name);//当前用户角色与同组的用户角色不装载出来
                if (user != null)
                {
                    IList<SysRole> roles = SysRoleManager.LoadAll().Where(r =>
                        {
                            var NNV = r.SysHotelGroup;
                            if (NNV != null)
                            {
                                bool bf = r.ID != 1 && r.ID != user.Role.ID && r.HotelID == 0 && r.SysHotelGroup.ID != user.SysHotelGroup.ID;
                                return bf;
                            }
                            return false;
                        }).OrderBy(o => o.Sort).ToList();

                    if (groupId.HasValue && groupId != 1)
                    {
                        roles = roles.Where(r => r.SysHotelGroup.ID == groupId || (r.SysHotelGroup.Parent != null && r.SysHotelGroup.Parent.ID == groupId)
                            || (r.SysHotelGroup.Parent != null && r.SysHotelGroup.Parent.Parent != null && r.SysHotelGroup.Parent.Parent.ID == groupId)).ToList();
                    }
                    foreach (SysRole role in roles)
                    {
                        string authorities = String.Join("、", role.Authorities.Select(r => ReturnNameByLanguage(r.Name, r.EName, r.TWName)).ToArray());
                        result.Add(new { ID = role.ID, Name = role.Name, GroupName = role.SysHotelGroup.Name, Sort = role.Sort, Authorities = authorities });
                    }
                }
            }
            catch (Exception ex)
            {
                logger.Error(ex.StackTrace);
            }
            return Json(new { IsSuccess = true, data = result }, JsonRequestBehavior.AllowGet);
        }

        [Authorize]
        public ActionResult Save(int id, string name, int sysHotelGroupID, int sort, IList<int> authorities)
        {
            var curUser = SysUserManager.Get(User.Identity.Name);
            if (sysHotelGroupID == curUser.SysHotelGroup.ID)
            {
                return Json(new { IsSuccess = false, Message = HttpContext.InnerLanguage("Flag") });
            }
            SysRole existRole = this.SysRoleManager.Get(name);
            SysRole entity = new SysRole();
            var newAuthorities = GetAuthorities(authorities);

            if (id == 0)
            {
                //新增
                if (null != existRole)
                {
                    return Json(new { IsSuccess = false, Message = HttpContext.InnerLanguage("RoleName") + "【" + name + "】" + HttpContext.InnerLanguage("AlreadyExist") });
                }

                entity.ID = id;
                entity.Name = name;
                entity.Authorities = newAuthorities;
                entity.Sort = sort;
                entity.ActiveIndicator = true;
                entity.CreatedBy = entity.ModifiedBy = this.User.Identity.Name;
                entity.CreatedDate = entity.ModifiedDate = DateTime.Now;
                entity.HotelID = 0;//0表示组角色，跟酒店无关
                entity.SysHotelGroup = SysHotelGroupManager.Get(sysHotelGroupID);

                SysRoleManager.Save(entity);

                SaveSystemLog(AuthorityID, HttpContext.InnerLanguage("New"), name);
            }
            else
            {
                //更新
                var role = this.SysRoleManager.Get(id);

                if (existRole != null && existRole.ID != role.ID)
                {
                    return Json(new { IsSuccess = false, Message = HttpContext.InnerLanguage("RoleName") + "【" + name + "】" + HttpContext.InnerLanguage("AlreadyExist") });
                }

                role.Name = name;
                role.Authorities.Clear();
                role.Authorities = newAuthorities;
                role.Sort = sort;
                role.ModifiedBy = this.User.Identity.Name;
                role.ModifiedDate = DateTime.Now;
                //role.HotelID = CurrentHotelID;//不修改所属酒店
                role.SysHotelGroup = SysHotelGroupManager.Get(sysHotelGroupID);

                SysRoleManager.Update(role);

                SaveSystemLog(AuthorityID, HttpContext.InnerLanguage("Edit"), name);
            }

            return Json(new { IsSuccess = true, Message = HttpContext.InnerLanguage("SaveSuccess") });
        }

        [HttpPost]
        [Authorize]
        public ActionResult Delete(int id)
        {
            try
            {
                SysRole role = this.SysRoleManager.Get(id);

                if (role.Name == HttpContext.InnerLanguage("SuperAdministrator"))
                {
                    throw new ApplicationException(HttpContext.InnerLanguage("SuperAdministratorRoleCanNotBeDeleted"));
                }

                this.SysRoleManager.Delete(id);

                SaveSystemLog(AuthorityID, HttpContext.InnerLanguage("Delete"), role.Name);

                return Json(new { IsSuccess = true, Message = HttpContext.InnerLanguage("DeleteSuccess") });
            }
            catch (ApplicationException ex)
            {
                return Json(new { IsSuccess = false, Message = ex.Message });
            }
        }

        //[Authorize]
        //public ActionResult LoadRoleAuthorities(int? roleId)
        //{
        //    SysRole role = null;

        //    if (roleId.HasValue)
        //    {
        //        role = SysRoleManager.Get(roleId);
        //    }

        //    return Json(BuildAuthoritiesTree(role, 0), JsonRequestBehavior.AllowGet);
        //}

        //[Authorize]
        //public ActionResult SaveRoleAuthorities(int roleId, IList<int> authorityIdList)
        //{
        //    try
        //    {
        //        SysRoleManager.SaveRoleAuthorities(roleId, authorityIdList);
        //        return Json(new { IsSuccess = true, Message = HttpContext.InnerLanguage("SaveSuccess") });
        //    }
        //    catch (ApplicationException ex)
        //    {
        //        return Json(new { IsSuccess = false, Message = ex.Message });
        //    }
        //}

        #endregion

        /// <summary>
        /// 构造权限树，用于设置角色权限
        /// </summary>
        /// <param name="role"></param>
        /// <param name="parentId"></param>
        /// <returns></returns>
        private IList<object> BuildAuthoritiesTree(SysRole role, int parentId)
        {
            IList<object> authoritiesTree = new List<object>();

            IList<SysAuthority> authorities = SysAuthorityManager.GetAuthorities(parentId);

            foreach (SysAuthority authority in authorities)
            {
                IList<object> children = BuildAuthoritiesTree(role, authority.ID);

                bool hasAuthority = (role != null ? role.Authorities.Contains(authority) : false);

                if (authority.ActiveIndicator)
                {
                    if (children.Count != 0)
                    {
                        authoritiesTree.Add(new { id = authority.ID, text = ReturnNameByLanguage(authority.Name, authority.EName, authority.TWName), @checked = hasAuthority, children = children });
                    }
                    else
                    {
                        authoritiesTree.Add(new { id = authority.ID, text = ReturnNameByLanguage(authority.Name, authority.EName, authority.TWName), @checked = hasAuthority });
                    }
                }
            }

            return authoritiesTree;
        }

        private IList<SysAuthority> GetAuthorities(IList<int> authorityIDs)
        {
            IList<SysAuthority> authorities = new List<SysAuthority>();

            if (authorityIDs != null)
            {
                foreach (int authorityId in authorityIDs)
                {
                    var authority = SysAuthorityManager.Get(authorityId);
                    if (authority != null && !authorities.Contains(authority))
                    {
                        authorities.Add(authority);
                    }
                }
            }

            return authorities;
        }
    }
}
