【開源框架】EFW框架中的系統權限與頁面子權限詳解

 回《【開源】EFW框架系列文章索引》       html

 EFW框架源代碼下載V1.3:http://pan.baidu.com/s/1c0dADO0sql

 EFW框架實例源代碼下載:http://pan.baidu.com/s/1eQCc69G編程

 

使用EFW框架開發系統,框架中提供了兩個級別的權限控制:角色菜單權限與頁面子權限json

      角色菜單權限:就是不一樣的用戶登陸系統後,根據配置的權限動態生成的菜單,管理員通常所有菜單均可以看到,而通常用戶不少菜單就看不到;用戶綁定角色,角色配置系統菜單,系統根據登陸的用戶先查找綁定的角色,再根據角色查找配置的菜單,而後將菜單顯示框架中;角色放在用戶與菜單之間,主要就是簡化用戶的配置;若是沒有角色,給每一個用戶配置菜單,那配置得有多麻煩;框架

      頁面子權限:通常來講權限達到菜單級別就能知足大部分狀況,而有些系統或功能對權限控制要求更細,須要達到頁面中功能也要可以加入權限配置;爲了知足這種需求,EFW框架提供了頁面子權限的功能,固然配置起來比菜單級的確定要複雜些;先維護好每一個頁面的子權限清單,再配置好每一個角色與頁面子權限清單的關係,而後打開頁面的時候,根據頁面與用戶就能夠查出配置頁面子權限,根據這個配置信息界面須要進行額外編碼完成界面上不一樣權限的操做;ide

 

見下圖:頁面子權限的效果圖工具

給實例中的「書籍管理」界面設置頁面子權限,給界面的「新增」、「保存」和「導出」三個功能按鈕配置權限控制;學習

圖中上面兩個界面,前一個頁面子權限三個都沒勾,那麼後面界面上的三個按鈕顯示都不可操做;開發工具

圖中下面兩個界面,前一個頁面子權限三個都勾上,那麼後面界面上的三個按鈕就變成能夠操做了;編碼

 

 

1.如何使用頁面子權限

1)在「用戶權限管理」界面維護好菜單的頁面子權限清單,並給角色配置子權限

見下圖,在紅框部分輸入權限標識和名稱,點擊保存就能夠增長一個頁面子權限,選中網格一條記錄點擊刪除就移除頁面子權限;一個菜單的頁面子權限的標識不可以重複,頁面子權限能夠隨便增長,但確定要跟實際界面有關係;

維護好頁面子權限後,再選擇左邊網格中的角色,勾選頁面子權限完成權限配置;

 

2)界面控制器獲取頁面子權限數據,並編寫代碼控制界面展現

見下圖,bookwinController控制器能夠直接獲得父類BaseController中的GetPageRight屬性爲頁面子權限的數據,用DataTable存儲;而後編寫代碼判斷數據中的「new」、「delete」和「export」的值是0或1,用來設置三個按鈕的狀態;

還有BaseController如何取得頁面子權限的數據,是經過框架中的ExecuteFun對象實現的,ExecuteFun是用來調用框架中全部註冊到框架中的委託代碼;

 

2.關於「委託代碼」的調用

上文中在獲取頁面子權限數據的時候用到了框架中的「委託代碼」,講解「委託代碼」以前先了解一下調用外部程序集代碼的三種方式:

1)引用調用,選擇項目引用能夠右鍵添加外部程序集後,代碼中就能夠直接使用引用程序集中定義的公共對象;

2)反射調用,項目不用引用程序集,但要知道程序集的名稱、類的名稱與方法屬性,就能夠用反射方式動態調用程序集中的代碼;

3)經過框架中的委託代碼調用,程序集將代碼註冊到框架中,那麼項目中不用關心是哪一個程序集,只要使用框架中的Excutefun對象就能夠調用全部註冊到框架的代碼;

 

第一種方式是常常用到的,用起來很是方便,可是有些狀況下這種方式沒法使用,好比兩個程序集相互調用的時候,就不能相互引用,由於編譯就會報錯。那麼這時候就會用到「反射」第二種方式,反射就是用起來比較麻煩,須要記住一些名詞,並且不能書寫錯誤。當程序集中的調用關係很複雜的話,「反射」這種方式用起來也麻煩,調用入口太多,容易搞錯。這時候就須要用到第三種方式「委託代碼」,這樣調用都是調用框架中的對象,可是代碼是經過委託的方式下放到不一樣的程序集去的;

你可能會以爲,把引用關係設計這麼複雜幹嗎,所有單向引用,都須要用到的對象就另外新建一個公共類庫不就好了。這種想法是好的,一次前期的設計得很是全面才能把公共類庫規劃得很好,還有就是把一些對象與原有程序集分離到公共類庫中,從代碼的結構上有點影響代碼的閱讀,代碼的編寫也變得複雜不連貫;因此以爲「委託代碼」是一種解決這種問題的不錯方式;

 

委託代碼註冊:

public class BaseLibShareFunCode : ExecuteFun
    {
        public override void LoadFun(System.Collections.Hashtable codeList)
        {
            string funName;
            FunCode code;
            //getPageRight 頁面子權限數據獲取
            //調用方法:DataTable data=(DataTable)ExecuteFun.invoke("getPageRight",1,1);
            funName = "getPageRight";
            code = delegate(object[] para)
            {
                int menuId = Convert.ToInt32(para[0]);
                int userId = Convert.ToInt32(para[1]);
                DataTable data = null;
                string strsql = @"SELECT Code,Name,
                                            (
                                            CASE WHEN 
                                            (SELECT COUNT(*) FROM BaseGroupPage a 
                                            LEFT JOIN BaseGroupUser b ON a.GroupId=b.GroupId
                                            WHERE b.UserId={1} AND a.PageId=P.Id)>0 
                                            THEN 1 ELSE 0 END
                                            ) Val
                                             FROM BasePageMenu P WHERE MenuId={0}";
                strsql = string.Format(strsql, menuId, userId);
                data = oleDb.GetDataTable(strsql);
                return data;
            };
            codeList.Add(funName, code);

            //
        }
    }

委託代碼調用:

/// <summary>
        /// 獲取頁面子權限
        /// </summary>
        public DataTable GetPageRight
        {
            get
            {
                DataTable data = (DataTable)ExecuteFun.invoke(oleDb,"getPageRight", MenuId, GetSysLoginRight.UserId);
                return data;
            }
        }

 

3.頁面子權限在不一樣系統Web、Winform、WCF下的區別

上文實例是講得Winform系統中的使用,其實三種不一樣系統原理都同樣,只是系統結構的差異因此實現方式有點區別而已;

Winform系統很簡單,直接調用BaseController中的GetPageRight屬性就能獲取頁面子權限數據,界面能夠直接操做GetPageRight屬性返回的DataTable數據,編寫權限控制代碼;

public class bookwinController : BaseController
    {
        IfrmBook frmBook;
        public override void Init()
        {
            frmBook = (IfrmBook)DefaultView;
            //初始化加載書籍目錄
            GetBooks();
            GetPie();
            //獲取頁面子權限
 frmBook.SetPageRight(GetPageRight);
        }
...

 

Web系統,能夠從AbstractJqueryController中獲取GetPageRight屬性,但數據是DataTable結構,因此界面還須要經過Ajax向調用後臺控制器將DataTable數據轉成json數據到界面JS中,再用JS代碼編寫權限控制代碼;

 

public class bookController : EFWCoreLib.WebFrame.Controller.AbstractJqueryController
    {
        [WebMethod]
        public void GetPageRightData()
        {
            int menuId = Convert.ToInt32(ParamsData["menuId"]);
            DataTable dt = GetPageRight(menuId);
            TxtJson = ReturnSuccess("", ToJson(dt));//前臺用requestAjax請求
        }
...

 

//頁面子權限控制代碼
function SetPageRight() {
    var menuId = $.query.get('MenuId');
    if (menuId) {
        requestAjax('Controller.aspx?controller=bookController&method=GetPageRightData', { menuId: menuId }, function (data) {
            PageRight = data;
            $.each(PageRight, function (i, n) {
                if (n.Code == 'new' && n.Val == 0) {
                    $('#btnNew').hide();
                }
                if (n.Code == 'delete' && n.Val == 0) {
                }
                if (n.Code == 'export' && n.Val == 0) {
                }
            });
        });
    }
}

 

WCF系統,跟Web系統同樣不能從BaseWCFClientController中直接獲取,須要使用WCF服務從後臺控制器中獲取GetPageRight數據,而後轉成Json數據傳遞給界面控制器,再編寫權限控制代碼;

 

[WCFController]
    public class bookWcfController : JsonWCFController
    {
        //根據界面傳遞的菜單ID獲取頁面子權限數據
        [WCFMethod]
        public string GetPageRightData()
        {
            int menuId = ToInt32(ParamJsonData);
            DataTable dt = GetPageRight(menuId);
            return ToJson(dt);
        }
...

 

public class bookwcfclientController : BaseWCFClientController
    {
        IfrmBook frmBook;
        public override void Init()
        {
            frmBook = (IfrmBook)DefaultView;
            //初始化加載書籍目錄
            GetBooks();
            //獲取頁面子權限數據
            PageRight = ToDataTable(InvokeWCFService("bookWcfController", "GetPageRightData", ToJson(MenuId))); frmBook.SetPageRight(PageRight);
        }
...

 

 

 

總結:EFW框架中的權限仍是能知足大部分的項目開發了,具備菜單級權限與頁面級權限,從粗到細;本文主要講解的是頁面子權限的內容,注意頁面子權限的兩部分操做是徹底獨立的,定義子權限清單與編寫權限控制代碼,可是後者又依賴前者,經過標識關聯起來;

 

下一章提早看:《掌握EFW框架的須要抓住如下幾個方面》

 

掌握和使用不一樣,若是你只要求會使用EFW框架那徹底不必深刻學習框架的代碼,博文也只學習前面幾章就好了,但若是你做爲一個開發團隊的頭,講EFW框架運用在項目中的話,那你就必須深刻掌握EFW框架,雖然不必把框架中的沒一段代碼搞清楚,但必定要作到內心有數,可以自主解決項目開發中遇到問題,也知道怎麼擴展框架。本章講得幾個方面是爲學習框架提供一個可參考的脈絡,防止深陷在衆多功能中。

 

1.必備的技術知識

2.框架核心的功能點之間的關聯

3.業務比代碼更重要

4.閱讀代碼的方法,瞭解「代碼層次結構」優先「代碼具體細節」

5.框架開源分享的意義是一些「編程思路的分享」,而不是又多一個開發工具供選擇而已。因此博文更注重把框架中的核心點拿出來討論,引導你們向更深層次的思考,找到更好的實現方法;要是寫成操做手冊同樣的文章,意義不大;

 

編程能力等級的提高是多麼的不容易,這個過程是沒有什麼具體的方法或操做步驟,而是那「一剎那」的豁然開朗;「一剎那」以後這一層的東西基本已經融會貫通、瞭然於胸,都能說出個之因此然來,但要達到這「一剎那」以前的積累是必不可少的,而代碼量是一個具體可參考的指標;

就跟刀客成爲一流高手以前的揮刀次數;

相關文章
相關標籤/搜索