EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(八)

前言

  • 本篇幅将对系统的菜单管理模块进行说明,系统的菜单采用树形结构,这样可以更好地方便层级设计和查看。本示例将说明如何通过EntityFramework读取递归的菜单树形结构,以及结合EasyUI的treegrid在Asp.net MVC上显示树形菜单和管理操作。

Easyui-treegrid的使用方法

  • 首先我们来看一下treegrid的基本使用方法。很简单,和easyui-datagrid差不多。
<table title="Folder Browser" class="easyui-treegrid" style="width:700px;height:250px"
            data-options="
                url: ‘treegrid_data1.json‘,
                method: ‘get‘,
                rownumbers: true,
                idField: ‘id‘,
                treeField: ‘name‘ ">
        <thead>
            <tr>
                <th data-options="field:‘name‘" width="220">Name</th>
                <th data-options="field:‘size‘" width="100" align="right">Size</th>
                <th data-options="field:‘date‘" width="150">Modified Date</th>
            </tr>
        </thead>
    </table>
  • 之前说过data-options可以通过GET方式发送异步请求,读取json数据后就可以加载数据呢。Treegrid中的data-options有两个关键参数idField(主键字段)、treeField(显示字段),上面很明显是利id作为主键字段,name作为显示字段。我们查看一下treegrid_data1.json文件究竟是怎样的格式。 
[{
    "id":1,
    "name":"C",
    "size":"",
    "date":"02/19/2010",
    "children":[{
        "id":2,
        "name":"Program Files",
        "size":"120 MB",
        "date":"03/20/2010",
        "children":[{
            "id":21,
            "name":"Java",
            "size":"",
            "date":"01/13/2010",
            "state":"closed",
            "children":[{
                "id":211,
                "name":"java.exe",
                "size":"142 KB",
                "date":"01/13/2010"
            },{
                "id":212,
                "name":"jawt.dll",
                "size":"5 KB",
                "date":"01/13/2010"
            }]
        },{
            "id":22,
            "name":"MySQL",
            "size":"",
            "date":"01/13/2010",
            "state":"closed",
            "children":[{
                "id":221,
                "name":"my.ini",
                "size":"10 KB",
                "date":"02/26/2009"
            },{
                "id":222,
                "name":"my-huge.ini",
                "size":"5 KB",
                "date":"02/26/2009"
            },{
                "id":223,
                "name":"my-large.ini",
                "size":"5 KB",
                "date":"02/26/2009"
            }]
        }]
    },{
        "id":3,
        "name":"eclipse",
        "size":"",
        "date":"01/20/2010",
        "children":[{
            "id":31,
            "name":"eclipse.exe",
            "size":"56 KB",
            "date":"05/19/2009"
        },{
            "id":32,
            "name":"eclipse.ini",
            "size":"1 KB",
            "date":"04/20/2010"
        },{
            "id":33,
            "name":"notice.html",
            "size":"7 KB",
            "date":"03/17/2005"
        }]
    }]
}]
  • 从treegrid_data1.json格式上可以看出还有一个很重要的属性,那就是children,所有的递归的子元素都会包含其中。这和我们的EntityFramework中的对象设计是一致的。所以接下来我们只要通过EntityFramework读取数据后,再利用ASP.NET MVC的json机制序列化出我们需要的json格式就可以绑定到Treegrid上呢。

示例中的treegrid使用方法

  • 首先,我们定义需要的ASP.NET MVC的Model,treegrid绑定的json数据就是按照此属性来序列化的。参考代码如下:
 public class mod_S_Menu
    {
        public long ID { get; set; }
        public long? PID { get; set; }
        public string MenuName { get; set; }
        public string Icon { get; set; }
        public string Link { get; set; }
        public string IsUse { get; set; }
        public int Level { get; set; }
        public int SerialNO { get; set; }
        public string Remark { get; set; }
        public List<mod_S_Menu> children { get; set; }
    }
  • 接下来我们定义菜单操作界面视图MenuList,其中绑定easyui-Treegrid的参考代码如下:
<table id="dg" class="easyui-treegrid" toolbar="#toolbar" style=" height:500px;" fitcolumns="true" singleselect="true"
       fit="true"
       data-options="
                url: ‘/System/GetMenus‘,
                method: ‘get‘,
                lines: true,
                rownumbers: true,
                idField: ‘ID‘,
                treeField: ‘MenuName‘
            ">
    <thead>
        <tr>
            <th data-options="field:‘ck‘,checkbox:true"></th>

            <th data-options="field:‘ID‘" width="50" hidden="true">
                主键ID
            </th>
            <th data-options="field:‘MenuName‘" width="100">
                菜单名称
            </th>
            <th data-options="field:‘Icon‘" width="150">
                菜单图标
            </th>
            <th data-options="field:‘Link‘" width="150">
                菜单链接
            </th>
            <th data-options="field:‘IsUse‘" width="80">
                是否启用
            </th>
            <th data-options="field:‘SerialNO‘" width="80">
                排序号
            </th>
            <th data-options="field:‘Remark‘" width="300">
                备注
            </th>
            <th data-options="field:‘PID‘" width="50" hidden="true">
                父级菜单
            </th>
        </tr>
    </thead>
</table>
  • 接下来,我们通过EntityFramework读取数据,再在SystemController中进行处理,之前说过使用延迟加载会一次性加载出所有与对象相关联的对象。由于S_Menu中的父级菜单ID是子菜单的外键,所以读取数据变得很简单呢。参考代码如下:
    public List<S_Menu> GetInfo()
        {
            context.Configuration.ProxyCreationEnabled = true;
            context.Configuration.LazyLoadingEnabled = true;

            List<S_Menu> listData = new List<S_Menu>();
            listData = context.S_Menus.Where(x => x.PID.Equals(null)).OrderBy(x => x.SerialNO).ToList();
            return listData;

        }
  • 最后,处理获得的GetInfo集合,因为我们需要序列化出treegrid的识别的json格式,而且我们也希望一次性序列化集合,所以我们可以使用递归的方式来绑定我们需要的数据格式(其实此时的EntityFramework加载的菜单体现的也是一种递归方式)。参考代码如下: 
  public ActionResult GetMenus(string page, string rows)
        {
            List<S_Menu> listDataParent = IS_Menu.GetInfo();
            List<mod_S_Menu> DataModel = new List<mod_S_Menu>();
            foreach (var item in listDataParent)
            {
                mod_S_Menu model = new mod_S_Menu();
                model.ID = item.ID;
                model.PID = item.PID;
                model.Icon = item.Icon;
                model.IsUse = item.IsUse;
                model.Level = item.Level;
                model.Link = item.Link;
                model.MenuName = item.MenuName;
                model.SerialNO = item.SerialNO;
                model.Remark = item.Remark;
                model.children = new List<mod_S_Menu>();

                GetRecursion(model, item);   //递归
                DataModel.Add(model);
            }
            return Json(DataModel, JsonRequestBehavior.AllowGet);
        }

        protected void GetRecursion(mod_S_Menu model,S_Menu item)
        {
            var children = item.Children.OrderBy(x => x.SerialNO).ToList();
            foreach (var childitem in children)
            {
                mod_S_Menu childmodel = new mod_S_Menu();
                childmodel.ID = childitem.ID;
                childmodel.PID = childitem.PID;
                childmodel.Icon = childitem.Icon;
                childmodel.IsUse = childitem.IsUse;
                childmodel.Level = childitem.Level;
                childmodel.Link = childitem.Link;
                childmodel.MenuName = childitem.MenuName;
                childmodel.SerialNO = childitem.SerialNO;
                childmodel.Remark = childitem.Remark;
                childmodel.children = new List<mod_S_Menu>();

                model.children.Add(childmodel);

                GetRecursion(childmodel, childitem);  //递归
            }

        }
  • 到此,我们通过treegrid加载出我们想要的树形结构数据呢。执行以下数据脚本:
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150704103806185, N‘系统权限管理‘, N‘icon-large-chart‘, N‘‘, N‘是‘, 1, 1, NULL, N‘设置权限管理的以及菜单‘)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150706103806185, N‘基本数据设置‘, N‘asd‘, N‘/bb/sss‘, N‘是‘, 1, 2, NULL, N‘基础数据管理‘)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150704103806181, N‘用户管理‘, N‘icon-large-picture‘, N‘/System/UserList‘, N‘是‘, 2, 1, 150704103806185, N‘asd‘)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150704103806182, N‘角色管理‘, N‘icon-large-clipart‘, N‘/System/RoleList‘, N‘是‘, 2, 2, 150704103806185, NULL)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150706162942028, N‘test1‘, N‘test1‘, N‘test1‘, N‘是‘, 1, 3, NULL, N‘asadas‘)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150706163404518, N‘test12‘, N‘test12‘, N‘test12‘, N‘是‘, 2, 2, 150706162942028, N‘assadasd‘)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150708114022584, N‘菜单管理‘, N‘icon-large-shapes‘, N‘/System/MenuList‘, N‘是‘, 2, 3, 150704103806185, NULL)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150708114134082, N‘权限设置‘, N‘icon-large-smartart‘, N‘/System/PermitList‘, N‘是‘, 2, 4, 150704103806185, NULL)
INSERT [dbo].[S_Menu] ([ID], [MenuName], [Icon], [Link], [IsUse], [Level], [SerialNO], [PID], [Remark]) VALUES (150706103806181, N‘承包合同数据录入‘, N‘ss‘, N‘/ss/ssss‘, N‘是‘, 2, 1, 150706103806185, N‘线程‘)
  • 运行效果如下:

  

时间: 2024-12-29 04:19:08

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(八)的相关文章

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(一)

前言 本系列源自对EF6 CodeFirst的探索,但后来发现在自己项目中构建的时候遇到了一些问题以及一些解决方法,因此想作为一个系列写下来. 本系列并不是教你怎么做架构设计,但可以参照一下里面的方法,EF系列大都采用DDD的构建方式,这也是目前最流行的.如果你想对DDD有所了解,可以在园子当中寻找那些DDD方面的文章或者是在CodePlex上下载相关的DDD设计模型源码进行研究. 如果你是一个新人或者是没有用过EF6 CodeFirst的人,那么本系列将带你一步一步构建自己的解决方案平台.如果

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(六)

前言 在接下来的篇幅里将对系统的模块功能进行编写.主要以代码实现为主.这一篇我们需要完成系统模块“角色管理”的相关功能.完成后可以对系统框架结构有进一步了解. Abstract层 之前说过,Abstract层是对业务接口的定义,所以我们新建接口文件IS_UserRepository,定义增删改查业务的接口.这一层需要添加对Entities层的引用.代码如下: using Entities; using System.Collections.Generic; namespace Abstract

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(四)

前言 这一篇,我们终于到了讲解Entity Framework CodeFirst 的时刻了,首先创建实体对象模型,然后会通过配置Fluent API的方式来对实体对象模型进行完整的数据库映射操作. 此篇幅中会涉及到一些Entity Frame的相关概念,会给出初步的解释.如果需要详细了解,可以查阅相关的帮助文档. EF实体对象模型的创建 EF的实体对象模型大都采用POCO类的方式创建.POCO的全称为Plain_Old_CLR_Object(简单传统CLR对象),是指那些没有从任何类继承,也没

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(三)

前言 在上一篇中,我们依靠着EasyUI强大的前端布局特性把前端登录界面和主界面给搭建完成了.这一篇我们就要尝试着把整个解决方案部署到云端呢,也就是Visual Studio Online(TFVC)中. 在我们进行团队项目开发的过程中,或多或少的都会接触到一些源代码管理工具,比如vss.svn.tfs.git,这些工具都有着自己的特点.但最终目的都是方便团队的协作开发,提高工作效率.Visual studio从2013版本开始就为我们提供了云端管理源代码的能力.Visual Studio On

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(完)

前言 这一篇是本系列的最后一篇,虽然示例讲到这里就停止呢,但对于这些技术的学习远不能停止.虽然本示例讲的比较基础,但是正如我第一篇说到的,这个系列的目的不是说一些高端的架构设计,而是作为一个入门级,对学习EntityFramework6构建一个简单的示例以及对其进行设计,管理,编码的过程. 应部分园友要求,博客换了一个清爽的模板.之前的模板也是为了学习一下,所以按照其他模板的样式,把自己的博客园模板修该了一下.虽然这不是写博客的主要目的,但还是从中学习到了很多,比如小插件的应用.运行js和css

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(七)

前言 上一篇文章我们完成了系统角色管理的基本功能实现,也对系统层次结构进行了了解.这一篇我们将继续对系统的用户管理模块进行代码编写.代码没有做封装,所以大部分的逻辑代码都是相通的,只是在一些前端的细节上处理有些不同.源码将在文章的末尾给出,有兴趣的园友可以对代码做一些封装或重构,毕竟这可以减少很多的代码量. Abstract层 在这一层添加对用户管理操作的业务接口IS_UserRepository,里面定义增删改查的业务接口.代码如下: using Entities; using System.

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(二)

前言 今天早上,看到第一篇上首页呢,多谢支持! 写完第一篇后,我一直在想接下来应该从哪一方面开始讲.后来我觉得不用那么死板的把每一个课程和大纲都列出来吧,毕竟我又不是教书的,呵呵...我觉得就像做实验一样,我们一部分一部分的完成,最后总个结果应该就出来呢.那么这一篇就来把前端的样子弄出来,至少得知道长成什么样吧.接下来就应该开始捯饬了... 下载前端框架EasyUI 到EasyUI的官网下载压缩包.一个是基于GPL的开源版,一个是商业版.我们自己做研究就下个开源版呢.目前是1.4.3的版本,解压

EF6 CodeFirst+Repository+Ninject+MVC4+EasyUI实践(九)

前言 这一篇我们将完成系统的权限设置功能以及不同角色用户登录系统后动态加载菜单.注意:此示例权限只针对菜单级,如果园友需要更复杂的系统权限设置,可以拓展到按钮级或属性级. 用户的登录采用Form认证来实现,这样可以有效地防止非授权用户或页面链接对系统造成不安全的操作. 权限设置模块 页面采用角色列表和菜单列表勾选的方式,即选择角色后勾选可以操作的菜单,这样具有才角色的用户就具有操作这些菜单的权限.界面设置如下: 界面选择的roleID和menuID我们采用字符串的方式进行拼接.在controll

k8s实践(八):ConfigMap and Secret

环境说明: 主机名 操作系统版本 ip docker version kubelet version 配置 备注 master Centos 7.6.1810 172.27.9.131 Docker 18.09.6 V1.14.2 2C2G master主机 node01 Centos 7.6.1810 172.27.9.135 Docker 18.09.6 V1.14.2 2C2G node节点 node02 Centos 7.6.1810 172.27.9.136 Docker 18.09.