權(quán)限,可分為“功能(操作)權(quán)限”和數(shù)據(jù)權(quán)限兩種,在系統(tǒng)中,兩種權(quán)限應(yīng)當同時有效。例如,在windows系統(tǒng)中,某用戶具有新建一個文件的功能權(quán)限,該用戶在C盤沒有寫權(quán)限,但在D盤有寫權(quán)限;則該用戶不能把他創(chuàng)建的文件保存在C盤而只能保存在D盤。
在上述例子中,能否創(chuàng)建文件是由功能權(quán)限來控制的,能否保存文件是由數(shù)據(jù)權(quán)限進行控制的。只有兩者同時有效,用戶的業(yè)務(wù)才能順利進行。
簡單地說,權(quán)限管理就是對資源的管理。權(quán)限管理的目的就是建立分配資源的規(guī)則,以便用戶能夠通過這套規(guī)則,獲取他們應(yīng)該獲得的資源。
2 功能權(quán)限:
也叫操作權(quán)限,指的是允許或拒絕用戶使用系統(tǒng)提供的某個功能。
2 數(shù)據(jù)權(quán)限:
指的是允許或拒絕用戶進行某個數(shù)據(jù)的增刪改查操作。
2 授權(quán):
指的是分配具體的權(quán)限給具體的人。
2 鑒權(quán):
指的是對具體人的行為,根據(jù)權(quán)限規(guī)則進行合法性鑒別。
對于授權(quán)來說,需要定義的有且只有權(quán)限和授權(quán)對象兩個要素。簡而述之,對于功能操作就是“什么功能授權(quán)給哪個用戶來操作”。同樣,對于數(shù)據(jù),就是“什么數(shù)據(jù)授權(quán)給哪個用戶來操作”。
一般情況下,我們并不會對單一的功能/數(shù)據(jù)進行單用戶的授權(quán)管理,因為這樣用戶操作起來顯然非常麻煩。為了方便和簡化操作,一般的授權(quán)規(guī)則是:
哪些功能/數(shù)據(jù)授權(quán)給哪些用戶
在實際的授權(quán)管理中,我們總是根據(jù)業(yè)務(wù)的需求,將一些在業(yè)務(wù)上不可分割的、需要允許用戶一起使用的功能,組合成一個權(quán)限集合進行統(tǒng)一授權(quán)。對于這樣的權(quán)限集合,我們一般稱之為“角色”。也就是說,我們通過角色來定義用戶被允許使用哪些功能和訪問哪些數(shù)據(jù)。當然,我們一般把功能和數(shù)據(jù)分開來進行授權(quán),以便獲得更加靈活的權(quán)限規(guī)則配置方法,以適應(yīng)更廣泛的授權(quán)需求。
由于某些不同用戶在該業(yè)務(wù)上需要具有相同的權(quán)限,那么這些不同的用戶在特定的業(yè)務(wù)上就具有了共性,可以作為一個抽象的用戶來進行權(quán)限的授予。授權(quán)管理使用的抽象的用戶,也就是用戶集合,除了普遍使用的“用戶組”外,還可以引用別的業(yè)務(wù)中所使用的對象。例如組織機構(gòu)管理中的“機構(gòu)/部門”、“職位”和工作流中使用的“崗位”等,在授權(quán)管理中都是作為用戶集合使用,本質(zhì)毫無二致。
通過讓抽象的用戶扮演角色,即可使這個抽象的用戶所代表的真實用戶獲得完成業(yè)務(wù)所需的權(quán)限。通過這樣的方式,可以簡化授權(quán)管理,方便用戶操作。
將特定的權(quán)限授予特定的人群的過程,我們稱之為“授權(quán)”。為了能夠方便地進行授權(quán)操作,我們必須要有一個能夠提供合理授權(quán)方法的用戶界面。
對于一個可擴展的系統(tǒng)來說,意味著功能是不斷變化的。為了適應(yīng)這種不能事先確定的變化,必須將功能權(quán)限進行分散管理。分散管理的好處如下:
2 天然地支持業(yè)務(wù)的動態(tài)變化,系統(tǒng)實現(xiàn)簡單。
2 權(quán)限的調(diào)整范圍可控制在局部范圍,方便權(quán)限的管理和操作。
功能權(quán)限是單維度的,可以通過簡單的在功能列表或功能樹上進行勾選來確定一個“角色”所允許的功能操作。然后,讓相應(yīng)用戶成為該“角色”的“扮演者”。這樣就可以把該角色所允許的功能操作授權(quán)給指定的用戶了。
如果需要有更多的不同角色,那么新建角色,勾選不同的被允許的功能操作,并分別讓相應(yīng)的用戶成為新角色的成員即可。
如果某個特定用戶張三需要額外的一個權(quán)限,那么新建一個允許該功能操作的角色,并讓張三成為該角色成員即可使張三擁有額外的權(quán)限。
如果某個特定用戶李四需要比同一項目組的其他人少一個權(quán)限,那么新建一個拒絕該功能操作的角色,并讓李四成為該角色成員即可使李四不能進行該項操作。因為在鑒權(quán)過程中,拒絕的優(yōu)先級要高于允許。
數(shù)據(jù)在系統(tǒng)中共同的特性有如下維度:
2 業(yè)務(wù)維度:不同的業(yè)務(wù)產(chǎn)生不同的數(shù)據(jù)
2 生產(chǎn)者維度:相同的業(yè)務(wù)會有多個數(shù)據(jù)生產(chǎn)者和生產(chǎn)部門
有些業(yè)務(wù)需要用戶訪問其他業(yè)務(wù)的數(shù)據(jù),或者是其他數(shù)據(jù)生產(chǎn)者中特定生產(chǎn)者的生產(chǎn)的數(shù)據(jù)。簡單的說,就是數(shù)據(jù)權(quán)限的授予必須支持跨業(yè)務(wù)和跨部門。
由于數(shù)據(jù)的特殊性質(zhì),實際上在有限范圍內(nèi)的授權(quán)比功能權(quán)限的授予更加方便。因為生產(chǎn)部門和生產(chǎn)者具有天然的分類屬性,所以象“本機構(gòu)”、“本部門”、“本人”這些對生產(chǎn)者維度的進一步抽象就有了用武之地。
在不對業(yè)務(wù)維度做限定的情況下,就可以配置例如“允許本部門的成員管理(增刪改查)本部門的數(shù)據(jù)”這樣的權(quán)限規(guī)則。那么對于不同部門的用戶,這條共同的規(guī)則所產(chǎn)生的效果并不相同,具體的效果是與用戶所在的部門的業(yè)務(wù)和產(chǎn)生的數(shù)據(jù)相對應(yīng)的。
根據(jù)以上分析,我們可以內(nèi)置一些抽象規(guī)則,例如:
2 允許管理本機構(gòu)(含下級機構(gòu)/部門)的數(shù)據(jù)
2 允許管理本部門(含下級部門)的數(shù)據(jù)
2 僅允許管理本部門的數(shù)據(jù)
2 僅允許管理本人的數(shù)據(jù)
2 允許查看本機構(gòu)(含下級機構(gòu)/部門)的數(shù)據(jù)
2 允許查看本部門(含下級部門)的數(shù)據(jù)
2 僅允許查看本部門的數(shù)據(jù)
2 僅允許查看本人的數(shù)據(jù)
一般數(shù)據(jù)權(quán)限的授予只能局限于符合高度抽象規(guī)則所限定的范圍。如果要在這個范圍之外的數(shù)據(jù)進行授權(quán),例如想讓財務(wù)部的人訪問采購部的數(shù)據(jù),顯然是一般數(shù)據(jù)授權(quán)所不能支持的。
這個時候,我們就必須要提供用戶在角色中自由定義允許或禁止用戶訪問的數(shù)據(jù)集的方法。上面說過,一個數(shù)據(jù)需要在業(yè)務(wù)和生產(chǎn)者兩個維度上進行描述,才能確定數(shù)據(jù)。那么在定義角色所允許訪問的數(shù)據(jù)集時,因為授權(quán)分散在不同的業(yè)務(wù)中,所以業(yè)務(wù)是確定的,剩下的就是需要指定一個或多個生產(chǎn)者。在這里,生產(chǎn)者可以使用抽象方法進行歸納分類。
最后,類同于功能權(quán)限的授權(quán)方式,我們把定義好的角色分配給一個抽象的用戶即可將一個自定義的數(shù)據(jù)權(quán)限授予抽象用戶代表的真實用戶。
權(quán)限管理的具體實現(xiàn)方法,離不開數(shù)據(jù)結(jié)構(gòu)的支持。相對來說,有具體的數(shù)據(jù)結(jié)構(gòu),我們也更容易理解權(quán)限的管理機制。在討論權(quán)限之前,我們還需要先了解權(quán)限管理的對象:功能資源和數(shù)據(jù)資源。這些資源同樣需要一個數(shù)據(jù)結(jié)構(gòu)去進行定義。
組織機構(gòu)表:
- CREATE TABLE Sys_Organization(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_Organization UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [ParentId] VARCHAR(36), --父節(jié)點ID
- [NodeType] INT NOT NULL, --節(jié)點類型:1、機構(gòu);2、部門;3、職位
- [Index] INT, --序號
- [Code] VARCHAR(32), --編碼
- [Name] NVARCHAR(32) NOT NULL, --名稱
- [Alias] NVARCHAR(16), --別名/簡稱
- [FullName] NVARCHAR(32), --全稱
- [PostId] VARCHAR(36), --崗位ID,字典
- [Validity] BIT DEFAULT 0 NOT NULL, --是否有效:0、無效;1、有效
- [CreatorUserId] VARCHAR(36), --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
用戶表:
- CREATE TABLE Sys_User(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED, --此ID與主數(shù)據(jù)ID相同
- [SN] BIGINT CONSTRAINT IX_Sys_User UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [Name] NVARCHAR(16) NOT NULL, --用戶名
- [LoginName] VARCHAR(36) NOT NULL, --登錄名
- [Password] VARCHAR(32) DEFAULT 'e10adc3949ba59abbe56e057f20f883e' NOT NULL, --登錄密碼,保存密碼的MD5值,初始密碼123456
- [Description] NVARCHAR(MAX), --描述
- [BuiltIn] BIT DEFAULT 0 NOT NULL, --是否預(yù)置:0、自定;1、預(yù)置
- [Validity] BIT DEFAULT 0 NOT NULL, --是否有效:0、無效;1、有效
- [CreatorUserId] VARCHAR(36), --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
3.2 資源模塊表:
- CREATE TABLE Sys_Module(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_Module UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [ParentId] VARCHAR(36), --父模塊ID
- [Level] INT NOT NULL, --模塊級別:0、主窗體模塊;1、普通業(yè)務(wù)模塊;2、業(yè)務(wù)子模塊
- [Name] NVARCHAR(64) NOT NULL, --名稱
- [Location] VARCHAR(MAX) NOT NULL, --文件安裝路徑
- [DataTable] NVARCHAR(64), --模塊主數(shù)據(jù)表名稱
- [Description] NVARCHAR(MAX), --描述
- [RegisterTime] DATETIME DEFAULT GETDATE() NOT NULL --模塊注冊時間
- )
- GO
模塊功能表:
- CREATE TABLE Sys_ModuleAction(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_ModuleAction UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [ModuleId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Module(ID) ON DELETE CASCADE NOT NULL, --模塊注冊ID
- [Name] NVARCHAR(64) NOT NULL, --名稱
- [SubModuleId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Module(ID), --子模塊ID(功能作為子模塊入口時)
- [Description] NVARCHAR(MAX) --描述
- )
- GO
3.2.2 業(yè)務(wù)數(shù)據(jù)物資數(shù)據(jù)表:
- CREATE TABLE MDG_Material(
- [MID] VARCHAR(36) PRIMARY KEY NONCLUSTERED FOREIGN KEY REFERENCES MasterData(ID) ON DELETE CASCADE, --主數(shù)據(jù)索引ID
- [SN] BIGINT CONSTRAINT IX_MDG_Material UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [Index] INT, --序號
- [BarCode] VARCHAR(16), --條形碼
- [Brand] NVARCHAR(16), --品牌
- [Model] NVARCHAR(32), --型號
- [Size] DECIMAL(20,6), --規(guī)格
- [SizeType] VARCHAR(36) FOREIGN KEY REFERENCES MasterData(ID), --規(guī)格單位ID,字典
- [Color] NVARCHAR(8), --顏色
- [Material] NVARCHAR(8), --材質(zhì)
- [StorageType] VARCHAR(36) FOREIGN KEY REFERENCES MasterData(ID), --存儲方式ID,字典
- [Description] NVARCHAR(MAX), --描述
- [Enable] BIT DEFAULT 1 NOT NULL, --是否可用:0、不可用;1、可用
- [CreatorDeptId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Organization(ID), --創(chuàng)建部門ID
- [CreatorUserId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_User(ID) NOT NULL, --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
3.3 RBAC模型角色表:
- CREATE TABLE Sys_Role(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_Role UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [Name] NVARCHAR(64) NOT NULL, --名稱
- [Description] NVARCHAR(MAX), --描述
- [BuiltIn] BIT DEFAULT 0 NOT NULL, --是否預(yù)置:0、自定;1、預(yù)置
- [CreatorUserId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_User(ID) NOT NULL, --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
3.3.2 角色成員角色成員(用戶)表:
- CREATE TABLE Sys_Role_User(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_Role_User UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [RoleId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Role(ID) ON DELETE CASCADE NOT NULL, --角色ID
- [UserId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_User(ID) NOT NULL, --用戶ID
- [CreatorUserId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_User(ID) NOT NULL, --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
3.3.3 角色權(quán)限角色權(quán)限表:
- CREATE TABLE Sys_RolePerm_Module(
- [ID] VARCHAR(36) PRIMARY KEY NONCLUSTERED DEFAULT NEWID(),
- [SN] BIGINT CONSTRAINT IX_Sys_RolePerm_Module UNIQUE CLUSTERED IDENTITY(1,1), --自增序列
- [RoleId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Role(ID) ON DELETE CASCADE NOT NULL, --角色ID
- [ModuleId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_Module(ID) ON DELETE CASCADE NOT NULL, --模塊注冊ID
- [Action] INT DEFAULT 0 NOT NULL, --操作行為:0、拒絕訪問;1、允許訪問
- [Mode] INT DEFAULT 0 NOT NULL, --數(shù)據(jù)授權(quán)范圍:-1、僅本人;0、僅本部門;1、本部門所有;2、本機構(gòu)所有;3、全部;4、自定義
- [Permission] INT DEFAULT 0 NOT NULL, --數(shù)據(jù)權(quán)限:0、只讀;1、讀寫
- [CreatorUserId] VARCHAR(36) FOREIGN KEY REFERENCES Sys_User(ID) NOT NULL, --創(chuàng)建人ID
- [CreateTime] DATETIME DEFAULT GETDATE() NOT NULL --創(chuàng)建時間
- )
- GO
3.4 如何獲取用戶的權(quán)限獲取指定用戶的功能權(quán)限需要先獲取該用戶可以訪問的模塊,此功能我們可以使用一個數(shù)據(jù)庫表值函數(shù)來返回指定用戶被授權(quán)訪問的模塊ID列表。在用戶啟動某一模塊時,使用一個數(shù)據(jù)庫表值函數(shù)來返回被授權(quán)功能的ID列表。
在用戶訪問數(shù)據(jù)時,我們需要對用戶訪問的數(shù)據(jù)根據(jù)授權(quán)情況進行過濾,并為這些數(shù)據(jù)加上權(quán)限標記,以便告知系統(tǒng)用戶被許可的操作方式(只讀/讀寫)。
我們可以在數(shù)據(jù)訪問層前端進行數(shù)據(jù)的過濾和標記,這種方式的優(yōu)點是:
2 安全,外部沒有注入、篡改的機會。
2 高效,數(shù)據(jù)訪問層獲取的數(shù)據(jù)已經(jīng)經(jīng)過篩選,不會返回?zé)o效的數(shù)據(jù)。
2 兼容性好,和應(yīng)用系統(tǒng)完全無關(guān),即使應(yīng)用系統(tǒng)通過存儲過程處理數(shù)據(jù),也能完全兼容。
簡單地來說,這種機制只需要你在獲取數(shù)據(jù)的時候使用inner join一個表值函數(shù),輸入函數(shù)的參數(shù)(模塊ID,登錄部門ID,用戶ID)即可。
- /*****表值函數(shù):獲取當前登錄用戶允許訪問模塊*****/
-
- CREATE FUNCTION Get_PermModule(
- @UserId VARCHAR(36), --當前登錄用戶ID
- @OrgId VARCHAR(36) --當前登錄部門ID
- )
-
- RETURNS TABLE AS
-
- RETURN
- with Roles as(
- select R.RoleId --獲取當前用戶作為成員的角色ID
- from Sys_Role_User R
- where R.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶所在用戶組作為成員的角色ID
- from Sys_Role_UserGroupR
- join Sys_UserGroupMemberG on G.GroupId = R.GroupId
- and G.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- and O.ParentId = @OrgId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID(職位對應(yīng)部門被合并)
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- join Sys_OrgMerger OM on OM.MergerOrgId = O.ParentId
- and OM.OrgId = @OrgId
- )
-
- select M.ModuleId from Roles R
- join Sys_RolePerm_ModuleM on M.RoleId = R.RoleId
- group by M.ModuleId
- having min(M.Action) > 0
-
- GO
4.1.2 獲取授權(quán)功能
- CREATE FUNCTION Get_PermAction(
- @ModuleId VARCHAR(36), --模塊ID
- @UserId VARCHAR(36), --當前登錄用戶ID
- @OrgId VARCHAR(36) --當前登錄部門ID
- )
-
- RETURNS TABLE AS
-
- RETURN
- with Roles as(
- select R.RoleId --獲取當前用戶作為成員的角色ID
- from Sys_Role_User R
- where R.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶所在用戶組作為成員的角色ID
- from Sys_Role_UserGroupR
- join Sys_UserGroupMemberG on G.GroupId = R.GroupId
- and G.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- and O.ParentId = @OrgId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID(職位對應(yīng)部門被合并)
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- join Sys_OrgMerger OM on OM.MergerOrgId = O.ParentId
- and OM.OrgId = @OrgId
- )
-
- select A.ActionId from Roles R
- join Sys_RolePerm_ActionA on A.RoleId = R.RoleId
- join Sys_ModuleActionM on M.ID = A.ActionId
- and M.ModuleId = @ModuleId
- group by A.ActionId
- having min(A.Action) > 0
-
- GO
- CREATE FUNCTION DataPerm_Org(
- @ModuleId VARCHAR(36), --模塊ID
- @UserId VARCHAR(36), --當前登錄用戶ID
- @OrgId VARCHAR(36) --當前登錄部門ID
- )
-
- RETURNS @PermScope TABLE(
- OrgId VARCHAR(36),
- Permission INT
- ) AS
-
- BEGIN
- DECLARE @Mode INT
- DECLARE @Permission INT
-
- select @Mode = Mode, @Permission = Permission --獲取指定模塊對于當前登錄用戶和登錄部門的數(shù)據(jù)授權(quán)訪問范圍代碼和權(quán)限代碼
- from Get_PermData(@ModuleId, @UserId, @OrgId)
-
- if @Mode = 0
- insert into @PermScope --授權(quán)訪問范圍為僅本部門時,返回本部門(當前登錄部門)ID、合并到該部門的部門ID和權(quán)限代碼
- select @OrgId, @Permission
- union
- select MergerOrgId, @Permission
- from Sys_OrgMerger
- where OrgId = @OrgId
-
- else if @Mode between 1 and 3
- begin
- if @Mode = 2
- select @OrgId = dbo.Get_SupOrg(@OrgId, 1) --獲取上級機構(gòu)ID
- if @Mode = 3
- select @OrgId = dbo.Get_SupOrg(@OrgId, 0) --獲取根機構(gòu)ID
- insert into @PermScope --授權(quán)訪問范圍為本部門及下屬、本機構(gòu)及下屬、全部時,返回本部門(當前登錄部門)和相應(yīng)機構(gòu)/部門ID、合并到上述部門的部門ID和權(quán)限代碼
- select ID, @Permission from Get_SubOrg(@OrgId)
- end
-
- else if @Mode = 4
- insert into @PermScope --自定義授權(quán)范圍和權(quán)限代碼
- select DC.OrgId, max(DC.Permission)
- from Sys_RolePerm_DataCustomDC
- join Sys_RolePerm_ModuleM on M.ID = DC.Perm_ModuleId
- and M.ModuleId = @ModuleId
- join Sys_OrganizationO on O.ID = DC.OrgId
- and O.Validity = 1
- group by DC.OrgId
- union
- select OM.MergerOrgId, max(DC.Permission)
- from Sys_RolePerm_DataCustomDC
- join Sys_RolePerm_ModuleM on M.ID = DC.Perm_ModuleId
- and M.ModuleId = @ModuleId
- join Sys_OrgMerger OM on OM.OrgId = DC.OrgId
- group by OM.MergerOrgId
-
- insert into @PermScope --無歸屬部門的數(shù)據(jù)可被所有人訪問
- select 'All', @Permission
-
- RETURN
- END
- GO
- CREATE FUNCTION DataPerm_User(
- @ModuleId VARCHAR(36), --模塊ID
- @UserId VARCHAR(36), --當前登錄用戶ID
- @OrgId VARCHAR(36) --當前登錄部門ID
- )
-
- RETURNS @PermScope TABLE(
- UserId VARCHAR(36),
- Permission INT
- ) AS
-
- BEGIN
- DECLARE @Mode INT
- DECLARE @Permission INT
-
- select @Mode = Mode, @Permission = Permission --獲取指定模塊對于當前登錄用戶和登錄部門的數(shù)據(jù)授權(quán)訪問范圍代碼和權(quán)限代碼
- from Get_PermData(@ModuleId, @UserId, @OrgId)
-
- if @Mode <0
- insert into @PermScope
- select @UserId, @Permission --授權(quán)訪問范圍為僅本人時,返回本人ID和權(quán)限代碼
-
- RETURN
- END
- GO
- CREATE FUNCTION Get_PermData(
- @ModuleId VARCHAR(36), --模塊ID
- @UserId VARCHAR(36), --當前登錄用戶ID
- @OrgId VARCHAR(36) --當前登錄部門ID
- )
-
- RETURNS TABLE AS
-
- RETURN
- with Roles as(
- select R.RoleId --獲取當前用戶作為成員的角色ID
- from Sys_Role_User R
- where R.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶所在用戶組作為成員的角色ID
- from Sys_Role_UserGroupR
- join Sys_UserGroupMemberG on G.GroupId = R.GroupId
- and G.UserId = @UserId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- and O.ParentId = @OrgId
- union
- select R.RoleId --獲取當前用戶的職位作為成員的角色ID(職位對應(yīng)部門被合并)
- from Sys_Role_PositionR
- join Sys_User_Org P on P.OrgId = R.OrgId
- and P.UserId = @UserId
- join Sys_OrganizationO on O.ID = R.OrgId
- join Sys_OrgMerger OM on OM.MergerOrgId = O.ParentId
- and OM.OrgId = @OrgId
- )
-
- select max(M.Permission) as Permission, max(M.Mode) as Mode from Roles R
- join Sys_RolePerm_ModuleM on M.RoleId = R.RoleId
- and M.ModuleId = @ModuleId
- group by M.ModuleId
-
- GO
- CREATE FUNCTION Get_SupOrg(
- @DeptId VARCHAR(36), --部門ID
- @Type INT --機構(gòu)類型:0、根機構(gòu);1、上級機構(gòu)
- )
-
- RETURNS NVARCHAR(36) AS
- BEGIN
-
- DECLARE @NodeType INT = 0
- DECLARE @ParentId VARCHAR(36)
-
- while @NodeType !=1
- begin
- select @NodeType = NodeType * @Type, @ParentId = ParentId from Sys_Organizationwhere ID = @DeptId
- if @ParentId is null
- set @NodeType = 1
- if @NodeType != 1
- set @DeptId = @ParentId
- end
-
- RETURN @DeptId
- END
- GO
- CREATE FUNCTION Get_SubOrg(
- @OrgId VARCHAR(36) --組織機構(gòu)ID
- )
-
- RETURNS TABLE AS
-
- RETURN
- with
- OrgList as (
- select @OrgId as ID
- union all
- select O.ID from Sys_OrganizationO
- join OrgList L on L.ID = O.ParentId
- where Validity = 1
- and NodeType < 3),
- MergerOrg as(
- select OM.MergerOrgId as ID from OrgList OL
- join Sys_OrgMerger OM on OM.OrgId = OL.ID
- union all
- select O.ID from Sys_OrganizationO
- join MergerOrg M on M.ID = O.ParentId
- where Validity = 1
- and NodeType < 3)
-
- select ID from OrgList
- union
- select ID from MergerOrg
-
- GO