グループのリストを保存するために、ネストされたセット (別名、変更されたプレオーダー ツリー トラバーサル) を使用しています。すべてのグループのブレッドクラムを (テーブルではなく文字列として) 一度に生成する簡単な方法を見つけようとしています。私のデータも、隣接リスト モデルを使用して保存されます (2 つの同期を維持するためのトリガーがあります)。
たとえば、次のようになります。
ID Name ParentId Left Right
0 Node A 0 1 12
1 Node B 0 2 5
2 Node C 1 3 4
3 Node D 0 6 11
4 Node E 3 7 8
5 Node F 4 9 9
これはツリーを表します:
- ノード A
- ノード B
- ノード C
- ノード D
- ノード E
- ノード F
- ノード B
テーブルを返すユーザー定義関数を使用できるようにしたいと思います。
ID Breadcrumb
0 Node A
1 Node A > Node B
2 Node A > Node B > Node C
3 Node A > Node D
4 Node A > Node D > Node E
5 Node A > Node D > Node F
これをもう少し複雑にするために (質問の範囲外ですが)、尊重する必要があるユーザー制限もあります。たとえば、id=3 にしかアクセスできない場合、クエリを実行すると次のようになります。
ID Breadcrumb
3 Node D
4 Node D > Node E
5 Node D > Node F
ユーザーIDをパラメーターとして受け取り、有効なすべてのグループのIDを含むテーブルを返すユーザー定義関数があります。クエリのどこかに限り
WHERE group.id IN (SELECT id FROM dbo.getUserGroups(@userid))
それが動作します。
これを実行できる既存のスカラー関数がありますが、妥当な数のグループでは機能しません (2000 グループで 10 秒以上かかります)。グループ ID とユーザー ID をパラメーターとして取り、nvarchar を返します。指定されたグループの親を検索し (左/右の値を取得するための 1 つのクエリ、親を検索するための別のクエリ)、ユーザーがアクセスできるグループにリストを制限します (上記と同じ WHERE 句を使用するため、さらに別のクエリを使用します)。次に、カーソルを使用して各グループを調べ、それを文字列に追加してから、最終的にその値を返します。
これを行うには、その場ですばやく (たとえば、<= 1 秒) 実行されるメソッドが必要です。
これは SQL Server 2005 上にあります。