一、屌丝也有春天
"亲爱的,在不?"
"妹子,你电脑又感觉慢了么?您以后装软件的时候注意点行不,能不能不要装上7-8个浏览器,3-4个杀毒软件,啥配置的机子你都感觉卡。以后别到处瞎找动作类电影看,网上一般都挂马骗你们这些小白的,实在想看找我要种子不就行了。"
"没有啦,人家电脑好着呢,您不是做软件的么,公司有个小项目让我找供应商,我第一个就想到了你,对你好吧,需求你接下,看看能不能做。下周就要用,费用的话万儿八千不是问题。"
先看看需求吧,没准人家出个几千块让我整个ERP系统出来。。。不着边际的小客户我见多了,想出900块钱做个网站的人都有。
内容相当少,就是给他们公司的网站后台加一个后台新闻发布的功能。这就万把块?也太爽了吧?
"大妹子,你们的需求是在原有网站的基础上加一个后台新闻发布的功能么?"
"大叔,需求上不都写的明明白白的么?你还来问我,想搭讪找个其它理由可以不?就这一个功能,不过以前后台管理没有进行权限管理的,这次要顺便做进去"
"做个新闻发布的功能顺便把权限管理做进去!!太TM扯蛋了吧,这跟买套婚纱让店主顺便送个老婆有什么区别。。我先考虑下吧。。。"
"好吧,等你的信,下班前给我答复。"
"大雄,过来瞧瞧,我小学同学的大姨妈家的二舅舅的三婶子的四儿子的五姑娘的小女儿要找个人家嫁了,这里有照片,你过来瞅瞅,看有合适的人介绍没?"
"擦,这不小泽老师么?你丫忽悠我。"
"大爷的,你啥时候见小泽老师穿这么厚实过。"
"是哦,联系方式有么,我这不刚失恋,肥水别流外人田了。"
"我这有个小单子,你看看需求,你那边有差不多的代码改改用么?"
"没问题,我上星期刚整了通用权限管理系统,你拿去用,说明书也有,标准的ISO"
二、流水线式生产
大雄还真有心,给了我套框架,还配了说明书,按照流程走标准的流水线生产呀。
权限的事先不用操心了,那就先开始弄数据库了。
1、后台表创建
这里要记得给表和字段添加说明,这样在使用代码生成器的时候就可以带出注释。提高代码可读性
2、代码生成
2.1连接代码生成器
2.2代码生成
分层生成后台代码,复制到项目文件夹下
"大雄,代码生成完了,接下来我要怎么做呀?"
"配置权限呀,说明里不写着么!"
还是看说明吧,指望他帮我做东西是不现实的
3、配置模块
"大雄,这里配置模块有什么用呀?"
"看下源代码你不就明白了。。。你到底是不是程序猿呀?"
对呀,是该看一下源代码了
//手风琴导航菜单 var AccordionMenuJson = ""; function GetAccordionMenu() { var index = 0; var html = ""; getAjax("Frame.ashx", "action=LoadFirstMenu", function (data) { AccordionMenuJson = eval("(" + data + ")"); $.each(AccordionMenuJson, function (i) { if (AccordionMenuJson[i].ParentId == '9f8ce93a-fc2d-4914-a59c-a6b49494108f') { if (index == 0) { html += "<li><a style=\"border-top: 0px solid #ccc;\"><img src=\"/Themes/Images/32/" + AccordionMenuJson[i].Img + "\">" + AccordionMenuJson[i].FullName + "</a>"; } else { html += "<li><a><img src=\"/Themes/Images/32/" + AccordionMenuJson[i].Img + "\">" + AccordionMenuJson[i].FullName + "</a>"; } html += GetSubmenu(AccordionMenuJson[i].MenuId); html += "</li>"; index++; } }); }) $(".accordion").append(html); }
switch (active) { case "login"://登录 #region 登录 try { string IPAddress = RequestHelper.GetIPAddress(); objScan.IP = IPAddress; objScan.DataPath = context.Server.MapPath("/Themes/IPScaner/QQWry.Dat"); string IPAddressName = objScan.IPLocation(); if (code.ToLower() != context.Session["dt_session_code"].ToString().ToLower()) { Msg = "1";//验证码输入不正确 } else { //系统管理 if (Account == ConfigHelper.GetValue("CurrentUserName") && Md5Helper.MD5(Pwd, 32) == ConfigHelper.GetValue("CurrentPassword")) { SessionUser user = new SessionUser(); user.UserId = "System"; user.Account = "System"; user.UserName = "超级管理员"; user.Gender = "男"; user.Password = bpms_user.Password; user.Code = "System"; user.DepartmentId = "超级管理员"; user.DepartmentName = "超级管理员"; RequestSession.AddSessionUser(user); Msg = "3";//验证成功 bpms_syslogibll.AddSysLoginLog(bpms_user.Account, "登录成功", IPAddress, IPAddressName); } else { #region 验证 bpms_ipblacklistibll.TheIpIsRange(IPAddress); string outmsg; bpms_user = bpms_useribll.UserLogin(Account.Trim(), Pwd.Trim(), out outmsg); if (outmsg != "-1") { if (outmsg == "succeed") { if (bpms_user.Enabled == 1) { if (Islogin(context, Account.Trim())) { string DepartmentName = ""; bpms_organization = bpms_organizationibll.GetEntity(bpms_user.DepartmentId); if (bpms_organization != null) { DepartmentName = bpms_organization.FullName; } SessionUser user = new SessionUser(); user.UserId = bpms_user.UserId; user.Account = bpms_user.Account; user.UserName = bpms_user.RealName; user.Gender = bpms_user.Gender; user.Password = bpms_user.Password; user.Code = bpms_user.Code; user.Secretkey = bpms_user.Secretkey; user.DepartmentId = bpms_user.DepartmentId; user.DepartmentName = DepartmentName; user.RoleId = bpms_user.RoleId; RequestSession.AddSessionUser(user); Msg = "3";//验证成功 bpms_syslogibll.AddSysLoginLog(bpms_user.Account, "登录成功", IPAddress, IPAddressName); } else { context.Response.Write("6");//该用户已经登录,不允许重复登录 context.Response.End(); } } else { Msg = "2";//账户锁定 bpms_syslogibll.AddSysLoginLog(bpms_user.Account, "账户锁定", IPAddress, IPAddressName); } } else { Msg = "4";//账户或者密码有错误 bpms_syslogibll.AddSysLoginLog(bpms_user.Account, "登录失败", IPAddress, IPAddressName); } } else { Msg = DbErrorMsg.ReturnMsg;//服务连接不上 } #endregion } } } catch (Exception ex) { Msg = ex.Message; } context.Response.Write(Msg); context.Response.End(); #endregion break; case "Outlogin"://安全退出 UserId = RequestSession.GetSessionUser().UserId; CacheHelper.RemoveAllCache("Module" + UserId); CacheHelper.RemoveAllCache("Button" + UserId); CacheHelper.RemoveAllCache("Data" + UserId); context.Session.Abandon(); //取消当前会话 context.Session.Clear(); //清除当前浏览器所以Session context.Response.Write("1"); context.Response.End(); break; case "LoadFirstMenu": UserId = RequestSession.GetSessionUser().UserId; IList list = (IList)StorePermission.Instance.GetModulePermission(UserId); context.Response.Write(JsonHelper.DropToJson<BPMS_ModulePermission>(list, "JSON")); context.Response.End(); break; case "SetSystemId"://模块ID、访问模块 UserId = RequestSession.GetSessionUser().UserId; string SystemId = context.Request["SystemId"]; //模块ID List<BPMS_ModulePermission> Modulelist = IListHelper.IListToList<BPMS_ModulePermission>((IList)StorePermission.Instance.GetModulePermission(UserId)).FindAll(t => t.MenuId == SystemId); foreach (BPMS_ModulePermission entity in Modulelist) { BPMS_SysLogDAL.Instance.AddVisitLog(UserId, RequestSession.GetSessionUser().UserName, entity.FullName, "URL:" + entity.NavigateUrl); break; } //写入Session context.Session["SystemId"] = SystemId; context.Response.Write(SystemId); context.Response.End(); break; case "LeaveModule"://离开模块 break; default: break; } }
从源代码中可以看出来,在模块管理中记录了这个菜单模块的URL地址,显示图标等信息,登陆系统的时候在前台就能显示出这个菜单项。
然后原有权限框架根据模块的ID也能对这个模块进行权限管理。
做的真的很不多,源码还是要好好看的。
接下来就是公用按钮的分配了
分配过后点击保存再刷新一次界面
非常好,勾选的那几个按钮按顺序都显示出来了。但是按下去好像不起作用。。。
"大雄,我分配了公共按钮以后点击按钮为什么不起作用呢?"
"你在代码里面实现了按钮对应的方法函数没有?"
"我既然要一个个去写函数,还在这里来分配什么按钮,不如直接自己写好了,太麻烦了"
"那你自己写的按钮,进行权限判断的时候每个按钮里都要去判断一下么?"
"哦,我明白啦,你这里的按钮其实也跟菜单模块权限类似,这里并不是为了省多少代码。而是为了更细更方便的控制权限,权限系统能根据模块和按钮的ID来控制每一个按钮的操作权限。比如:新增、删除、修改什么的。"
"不错不错,一点就通"
//新增 function add() { var url = "/ExampleModule/News/NewsForm.aspx"; top.openDialog(url, 'NewsForm', '新闻信息 - 添加', 800, 500, 50, 50); } //编辑 function edit() { var key = GetPqGridRowValue("#grid_paging", 0); if (IsEditdata(key)) { var url = "/ExampleModule/News/NewsForm.aspx?key=" + key; top.openDialog(url, 'NewsForm', '新闻信息 - 编辑', 800, 500, 50, 50); } } //删除 function Delete() { var key = GetPqGridRowValue("#grid_paging", 0); if (IsDelData(key)) { var delparm = 'action=Delete&key=' + key; delConfig('NewsList.aspx', delparm); } } //刷新 function windowload() { $("#grid_paging").pqGrid("refreshDataAndView"); GetRowIndex = -1; }
这里写了一个每个按钮的操作函数,不管是js还是后台代码都可以被权限系统牢牢控制,非常好用呀,再次运行
OK,完全实现了功能。
掐表一算,整个过程才20分钟不到,而且我是第一次使用这个框架。流水线式生产就是好呀。
"大雄,我用了不到20分钟就全搞定了呀。明天请你吃饭噢。"
"20分钟?你也太慢了。。。先看看这篇博客了解下这个框架的详细结构《打造一套UI与后台并重.net通用权限管理系统》,10分钟你就能搞定"
附大湿教我写程序系列博文:
打造一套UI与后台并重.net通用权限管理系统
大湿教我写程序(1)之菜单导航篇
大湿教我写程序(2)之走向AV之路
大湿教我写程序(3)之自动补全(屌丝没有春天)篇
.NET框架交流群(二) 156560556