角色表 有角色字段,命名某个产品P属于角色C,角色C就可以修改查询等,但角色B包含角色C所有权限,角色A包含角色B,现在角色A如果要访问产品P时需要查询权限,如果用普通方法就是先查询产品P属于角色C,然后查询角色C被角色B包含了,然后再向上推一层至角色A,如何列简单查询?因为现在这方法如果是多级权限,可能要查询很多次。有没有简单方法一个语句或过程就可以查询出角色A也有修改产品P?

解决方案 »

  1.   

    树形数据?USE tempdb
    GO-- 建立演示环境
    CREATE TABLE Dept(
    id int PRIMARY KEY, 
    parent_id int,
    name nvarchar(20))
    INSERT Dept
    SELECT 0, 0, N'<全部>' UNION ALL
    SELECT 1, 0, N'财务部' UNION ALL
    SELECT 2, 0, N'行政部' UNION ALL
    SELECT 3, 0, N'业务部' UNION ALL
    SELECT 4, 0, N'业务部' UNION ALL
    SELECT 5, 4, N'销售部' UNION ALL
    SELECT 6, 4, N'MIS' UNION ALL
    SELECT 7, 6, N'UI' UNION ALL
    SELECT 8, 6, N'软件开发' UNION ALL
    SELECT 9, 8, N'内部开发'
    GO-- 查询指定部门下面的所有部门
    DECLARE @Dept_name nvarchar(20)
    SET @Dept_name = N'MIS'
    ;WITH
    DEPTS AS(
    -- 定位点成员
    SELECT * FROM Dept
    WHERE name = @Dept_name
    UNION ALL
    -- 递归成员, 通过引用CTE自身与Dept基表JOIN实现递归
    SELECT A.*
    FROM Dept A, DEPTS B
    WHERE A.parent_id = B.id
    )
    SELECT * FROM DEPTS
    GO-- 删除演示环境
    DROP TABLE Dept
      

  2.   

    -->Title:Generating test data
    -->Author:wufeng4552
    -->Date :2009-09-30 08:52:38
    set nocount on
    if object_id('tb','U')is not null drop table tb
    go
    create table tb(ID int, ParentID int)
    insert into tb select 1,0  
    insert into tb select 2,1  
    insert into tb select 3,1  
    insert into tb select 4,2  
    insert into tb select 5,3  
    insert into tb select 6,5  
    insert into tb select 7,6
    -->Title:查找指定節點下的子結點
    if object_id('Uf_GetChildID')is not null drop function Uf_GetChildID
    go
    create function Uf_GetChildID(@ParentID int)
    returns @t table(ID int)
    as
    begin
       insert @t select ID from tb where ParentID=@ParentID
       while @@rowcount<>0
       begin
          insert @t select a.ID from tb a inner join @t b
          on a.ParentID=b.id and 
          not exists(select 1 from @t where id=a.id)
       end 
    return
    end
    go
    select * from dbo.Uf_GetChildID(5)
    /*
    ID
    -----------
    6
    7
    */
    -->Title:查找指定節點的所有父結點
    if object_id('Uf_GetParentID')is not null drop function Uf_GetParentID
    go
    create function Uf_GetParentID(@ID int)
    returns @t table(ParentID int)
    as
    begin
       insert @t select ParentID from tb where ID=@ID
       while @@rowcount!=0
       begin
         insert @t select a.ParentID from tb a inner join @t b
           on a.id=b.ParentID and 
           not exists(select 1 from @t where ParentID=a.ParentID)
       end
      return
    end
    go
    select * from dbo.Uf_GetParentID(2)
    /*
    ParentID
    -----------
    1
    0
    */
      

  3.   

    /*
    原始数据及要求结果如下:
    --食品 
      --水果 
        --香蕉 
        --苹果    
      --蔬菜 
        --青菜
    id          pid         name                 
    ----------- ----------- -------------------- 
    1           0           食品
    2           1           水果
    3           1           蔬菜
    4           2           香蕉
    5           2           苹果
    6           3           青菜要求得到各节点的父路径即如下结果:
    id  pid name  路径                         
    --- --- ----- ---------------
    1   0   食品  食品
    2   1   水果  食品,水果
    3   1   蔬菜  食品,蔬菜
    4   2   香蕉  食品,水果,香蕉
    5   2   苹果  食品,水果,苹果
    6   3   青菜  食品,蔬菜,青菜 
    */create table tb (id int , pid int , name nvarchar(20)) 
    insert into tb values(1 , 0 , '食品')
    insert into tb values(2 , 1 , '水果')
    insert into tb values(3 , 1 , '蔬菜')
    insert into tb values(4 , 2 , '香蕉')
    insert into tb values(5 , 2 , '苹果')
    insert into tb values(6 , 3 , '青菜')
    go--查询各节点的父路径函数
    create function f_pid(@id int) returns varchar(100)
    as
    begin
      declare @re_str as varchar(100)
      set @re_str = ''
      select @re_str = name from tb where id = @id
      while exists (select 1 from tb where id = @id and pid <> 0)
        begin
          select @id = b.id , @re_str = b.name + ',' + @re_str from tb a , tb b where a.id = @id and a.pid = b.id
        end
      return @re_str
    end
    goselect * , dbo.f_pid(id) 路径 from tb order by iddrop table tb
    drop function f_pid/*----结果
    id          pid         name                 路径
    ----------- ----------- -------------------- ----------------------------------------------------------------------------------------------------
    1           0           食品                   食品
    2           1           水果                   食品,水果
    3           1           蔬菜                   食品,蔬菜
    4           2           香蕉                   食品,水果,香蕉
    5           2           苹果                   食品,水果,苹果
    6           3           青菜                   食品,蔬菜,青菜
    *
      

  4.   

    我这个问题的数据表如下ID  用户ID  角色名
    1   1      总经理
    2   1      部门经理
    3   2      部门经理
    4   2      销售人员A
    5   5      销售人员A
    6   6      销售人员B就是用户ID为1的总经理,包括了总经理及部门经理权限,部门经理也包括了销售人员A的权限,现在就是一个属于销售人员A可以查看的资料,现在要判断总经理及部门经理是否有权限,因为包括关系,所以他们都有权限,现在就是要如何简单的查询呢?否则一级一级向上查询,太慢了。