2013-10-25 4 views
2

사용자, 그룹 및 멤버쉽 테이블이 3 개 있습니다.
사용자에는 ID와 이름이 있습니다.
그룹에도 ID와 이름이 있습니다.
회원는 ID, 그룹 ID 및 MEMBERID재귀 쿼리 재 작성 그래프

것은이 MEMBERID 사용자 그룹 모두가 될 수 있다는 것입니다있다.

내가 원하는 것은 사용자가 속한 모든 그룹을 얻는 것입니다. .

이 작업을 수행하려면 나는 아래 표와 같이 CTE를 사용하고 있습니다 :

WITH MyGroups AS(
select *,1 as GLevel from [Group] as g where g.id IN (SELECT groupId FROM Membership m where m.memberId='MYID') 

UNION ALL 

select g.*,2 from [Group] g inner JOIN MyGroups my on my.id=g.id --where g.id IN (SELECT groupId FROM ACLTests.dbo.Membership m where m.groupid=g.id)) 

Select * from MyGroups 

하지만 난 ... 사람이 도움을 줄 수 재귀의 100 개 수준을 넘어 갈거야?

샘플 데이터 :

사용자 테이블 :
ID ---------- | 제목 ---------
myUser1 | 존
myUser2 | 레오

그룹 :
ID ---------- | 제목 ---------
myG1. . 그룹 1
myG2. . . 그룹 2

회원 테이블 :
ID | GROUPID | 회원이
01 | myG1 ... . . myUser1
02 | myG1 ... . . myG2
03 | myG2 ... . . MyUser2

예상 결과 MyUser1 FOR : 그룹 1
예상 결과 FOR MyUser2 : 그룹 1, 그룹 2 (G2은 G1의 멤버이고, 사용자 2는 G1의 부재하므로 사용자 2는 G2의 구성원이다)

+0

문제는 무엇인가? 몇 가지 샘플 데이터와 예상 결과를 게시 할 수 있습니까? – Rachcha

+0

@ 라차 편집 됨! 그것을 확인하십시오 ... – Leonardo

답변

1

여기에 필요한 검색어입니다. 만일 당신이 정말로 필요하다면 option (maxrecursion 0)을 입력하십시오. 그렇다면 아래의 쿼리에도 그것을 추가하십시오.

SET NOCOUNT ON 
    DECLARE @User TABLE 
    (
     id  sysname NOT NULL 
     ,title sysname NOT NULL 
    ) 
    DECLARE @Groups TABLE 
    (
     id  sysname NOT NULL 
     ,title sysname NOT NULL 
    ) 
    DECLARE @Membership TABLE 
    (
     id  INT NOT NULL 
     ,groupid sysname NOT NULL 
     ,memberid sysname NOT NULL 
    ) 

    INSERT INTO @User(id, title) SELECT 'myuser1','John' UNION ALL SELECT 'myuser2','Leo' 
    INSERT into @Groups(id, title) SELECT 'myG1','Group1' UNION ALL SELECT 'myG2','Group2' 
    INSERT into @Membership(id, groupid, memberid) SELECT 1,'myG1','myuser1' UNION ALL SELECT 2,'myG1','myG2' UNION ALL SELECT 3,'myG2','myuser2' 



    DECLARE @SearchUsergroup sysname='myUser2' 
    ;WITH mType(id,title,mType) 
    AS 
    (
     SELECT id,title,'user' AS mType 
     FROM @User 
     UNION ALL 
     SELECT id,title,'Group' AS mType 
     FROM @Groups 
    ), 
    Ugroups(id,mType,mLevel) 
    AS 
    (
     SELECT groupid,'Group' as mType, 1 AS mLevel 
     FROM @Membership 
     WHERE memberid = @SearchUsergroup 

     UNION ALL 
     SELECT ms.groupid,'Group' as mType, ug.mLevel+1 AS mLevel 
     FROM mType mt 
     JOIN Ugroups ug 
      ON mt.id=ug.id AND ug.mType='Group' 
     JOIN @Membership ms 
      ON ms.memberid=ug.id 
    ) 
    SELECT id AS GroupID,mLevel AS MembershipLevel 
    FROM Ugroups 

enter image description here

0

검색어 끝에 option (maxrecursion 0)을 추가하십시오.

UPD.

WITH MyGroups AS (
    select g.id, 1 as GLevel 
    from Group as g 
    where g.id IN (
     SELECT groupId 
     FROM Membership m 
     where m.memberId = 'MyUser2' 
    ) 
    UNION ALL 
    select m.GroupId, my.GLevel + 1 
    from Membership m 
    inner JOIN MyGroups my on m.memberId=my.id 
) 

Select * from MyGroups 
+0

hummmm interesting ... 오류가 사라졌지 만 지금은 끝없는 결과를 얻습니다 ... – Leonardo

+0

중지 할 때 재귀 쿼리를 지정하지 마십시오. 내 업데이트 답변을 참조하십시오. – GriGrim