Uw r
alias en de rights
tabel waarnaar het verwijst, vallen niet binnen het bereik van de inline-weergave die u aan het maken bent. U moet de hiërarchie genereren, wat u nog steeds kunt doen in een inline-weergave, en die vervolgens koppelen aan de rights
tabel via zijn folderid
.
U kunt de hiërarchie verkrijgen van:
select connect_by_root(folderid) as rootid, folderid,
sys_connect_by_path(folderid, '/') as path
from folders
connect by parentfolderid = prior folderid
order by rootid, path;
ROOTID FOLDERID PATH
---------- ---------- ------------------------------
5162 5162 /5162
5162 28568 /5162/28568
5162 6343 /5162/6343
5534 5534 /5534
5534 41578 /5534/41578
5534 113867 /5534/41578/113867
5534 127030 /5534/41578/127030
5534 5162 /5534/5162
5534 28568 /5534/5162/28568
5534 6343 /5534/5162/6343
5534 5538 /5534/5538
5538 5538 /5538
...
Dat is ongeveer wat je aan het doen was, maar dit vindt alle nakomelingen van elk startpunt en legt ook het startpunt vast als rootid
. (Ik heb path
ingevoerd ook alleen om de hiërarchie te visualiseren; dat wil je blijkbaar niet in de resultaten).
U kunt dat vervolgens toevoegen aan uw rechtentabel, waar de folderid
. van elke gebruiker komt overeen met elke rootid
. Dat zal duplicaten weergeven (bijv. 685 kan rechtstreeks of via 5534 naar 5538 gaan), dus u kunt distinct
gebruiken om deze te elimineren:
select distinct r.userid, f.folderid
from rights r
join (
select connect_by_root(folderid) as rootid, folderid
from folders
connect by prior folderid = parentfolderid
) f
on f.rootid = r.folderid
order by r.userid, f.folderid;
Die met uw gegevens 16 verschillende combinaties krijgt:
USERID FOLDERID
---------- ----------
685 5162
685 5534
685 5538
685 6343
685 28568
685 41578
685 113867
685 127030
686 5162
686 6343
686 28568
686 41578
686 113867
686 127030
725 113867
725 127030
U kunt ook recursieve subqueryfactoring gebruiken in plaats van een hiërarchische zoekopdracht:
with rcte (userid, folderid) as (
select r.userid, f.folderid
from rights r
join folders f on f.folderid = r.folderid
union all
select rcte.userid, f.folderid
from rcte
join folders f on f.parentfolderid = rcte.folderid
)
select distinct userid, folderid
from rcte
order by userid, folderid;
Het ankerlid is een eenvoudige join tussen de twee tabellen om de machtigingen op het hoogste niveau te krijgen. Het recursieve lid zoekt vervolgens naar eventuele onderliggende machtigingen van al gevonden. Zelfde resultaat, iets andere aanpak.