问题:
我正在使用闭包表来跟踪用户文件权限,并且在 a 之后JOIN
,这会导致read
跨多行的多个布尔值。如果所有连接的行都是可读的,我只想选择一行。使用UNION
显然不能做到这一点。
细节:
文件夹表:
CREATE TABLE IF NOT EXISTS folders
(
id INT NOT NULL AUTO_INCREMENT,
path VARCHAR(500) NOT NULL,
r BOOL NOT NULL DEFAULT FALSE,
PRIMARY KEY ( id )
)engine=innodb;
文件表:
CREATE TABLE IF NOT EXISTS files
(
id INT NOT NULL AUTO_INCREMENT,
parent_folder_id INT NOT NULL ,
path VARCHAR(500) NOT NULL,
r BOOL NOT NULL DEFAULT FALSE,
FOREIGN KEY ( parent_folder_id ) REFERENCES folders ( id ),
PRIMARY KEY ( id )
)engine=innodb;
文件夹-父文件夹关闭表:
CREATE TABLE IF NOT EXISTS parent_folders
(
id INT NOT NULL AUTO_INCREMENT,
folder_id INT NOT NULL,
parent_folder_id INT NOT NULL,
FOREIGN KEY ( folder_id ) REFERENCES folders ( id ),
FOREIGN KEY ( parent_folder_id ) REFERENCES folders ( id ),
PRIMARY KEY ( id )
)engine=innodb;
现在,如果我想获取所有可读文件(暂时忽略我完全省略用户的那一刻),我会像这样开始
SELECT
F.id, F.path, F.r, P.parent_folder_id, D.path, D.r
FROM
files AS F
LEFT JOIN parent_folders AS P
ON F.parent_folder_id = P.folder_id
LEFT JOIN folders AS D
ON P.parent_folder_id = D.id;
这将显示每个文件 ID、路径和读取权限的表格,可以从其每个父文件夹访问,如下所示
id path r id path r
......
0 /home/joe/foo/bar.txt True 1 /home/joe/foo True
1 /home/joe/foo/bar.txt True 2 /home/joe True
1 /home/joe/foo/bar.txt True 3 /home True
1 /home/joe/foo/bar.txt True 4 / True
2 /home/jim/foo/bar.txt True 5 /home/jim/foo True
2 /home/jim/foo/bar.txt True 6 /home/jim False
2 /home/jim/foo/bar.txt True 7 /home True
2 /home/jim/foo/bar.txt True 8 / True
....
在这种情况下,我想SELECT
/home/joe/foo/bar.txt
因为通向它的每个父文件夹都是可读的,但我不想SELECT
/home/jim/foo/bar.txt
因为它的父文件夹之一不可读。
编辑:或者,我可以这样改写这个问题:“我可以AND
跨多行的一列的值吗?”