2012-10-12 73 views
0

的我有兩個表:獨家查詢,左外連接或添加查詢

nets_permissions 

    user_id INT NOT NULL, 
    network_id BIGINT UNSIGNED NOT NULL, 
    perm INT(3) NOT NULL, 
    PRIMARY KEY(user_id, network_id) 


devices_permissions 

    user_id INT NOT NULL, 
    network_id BIGINT UNSIGNED NOT NULL, 
    device_id INT UNSIGNED NOT NULL, 
    perm INT(3) NOT NULL, 
    PRIMARY KEY(user_id, network_id, device_id), 

nets_permissions table對每個用戶的權限。用戶可以具有不同的perm值:1表示讀取權限,2表示寫入權限,4表示讀取+命令權限。網絡管理員的perm值爲3.

第二張表的內容相同,但這次是針對特定網絡中的設備。當網絡和設備的管理員授予他們許可時,用戶將被添加到該表中。但網絡的管理員沒有在此表中註冊。他只在per_ = 3的nets_permission表中。

我必須創建一個查詢,在Tornado Web Server的處理程序中選擇當前用戶的權限。代碼是這種形式:

# Retrieve the current user 
    usr = self.get_current_user() 
    usr_id = usr['id'] 
    self.lock_tables("read", ['nets_permissions as n, devices_permissions as d']) 
    usrperm = self.db.query("SELECT * FROM nets_permissions as n 
     LEFT OUTER JOIN devices_permissions as d 
       ON n.network_id = d.network_id WHERE d.user_id=%s 
       AND d.device_id=%s", 
     int(usr_id), sens.id); 
    self.unlock_tables() 

在usr_id我檢索是當前用戶的ID。

當前用戶可以是網絡的管理員(所以他只能在nets_permissions中使用perm = 3)或者具有特定設備權限的用戶(所以他只在devices_permissions表中有一些值for perm)。

在查詢結果'userperm'中,我會使用一個整數來比較HTML頁面中的權限值並顯示或不顯示給用戶。

對不起我的英文,但很難解釋我的問題。我不知道我可以構造查詢來獲得我想要的結果。

非常感謝您的幫助。

回答

1
SELECT distinct 'net', network_id, perm 
FROM nets_permissions n 
JOIN devices_permissions d 
USING (user_id, network_id) 
WHERE n.user_id = '%s' 
AND d.device_id = '%s' 

UNION ALL 

SELECT 'device', network_id, perm 
FROM devices_permissions 
WHERE user_id = '%s' 
AND device_id = '%s' 

但是,它看起來像有一個問題你數據模型。如果某個設備沒有具有該設備權限的用戶,那麼devices_permissions中將不會有一行,因此我們將無法找到它的network_id。你需要更好地規範化:應該有一個device_network表來關聯它們。

+0

這非常有用!非常感謝你! – sharkbait

1

由於用戶可以位於一個或兩個表中,因此可能需要執行UNION而不是Join。

該聯盟的聲明是這樣的:

select * from (
    Select User_ID, network_id, network_id, perm from nets_permissions 
    union 
    Select User_ID, network_id, device_id, perm from devices_permissions) 
where user_id = 'id' 

上面的格式提供了更多的靈活性。您可以進一步修改外選擇讓每個用戶只有一行,或者每個用戶的最高燙髮,或每個用戶的燙髮總數等

+0

以這種方式我有一個錯誤。重複的'network_id'列。如果我取消了某一列,我有錯誤,說這兩個查詢的列數不同。 – sharkbait

+0

這不是重複的。第三列和第四列是一對。第二列是第三列的父代。當第三欄是網絡時,它是它自己的父母。 –