2011-10-07 36 views
4

場景:我們爲要求經理批准的請求生成記錄。在等待處理時,管理員會更改(從HR提要中過夜更新)。我們需要更新請求以指示新的經理。更新連接權限不足

這裏的查詢的簡化版本, 應該這樣做:

update (select grw.approver_user_id, gup.supervisor_id 
     from gs3.user_role gur 
      join gsu.user_profile gup 
      on gur.user_id = gup.user_id 
      join gs3.request_workflow grw 
      on gur.user_role_id = grw.user_role_id 
      and gup.supervisor_id != grw.approver_user_id -- records with new mgr 
     where grw.auth_status_cd = 'SUBMITTED') -- reapprovals currently open 
set grw.approver_id = gup.supervisor_id; 


問題:帳戶執行此查詢只對gsu.user_profile讀取權限。

內部選擇工作正常,並返回所有我需要更新的行...但即使我沒有更新gup.supervisor_id,似乎我需要有寫訪問該表。如果我以具有對gsu.user_profile的寫權限的用戶身份執行此操作,則更新成功。

這是否有合乎邏輯的原因?我寧願不授予其不需要的帳戶權限。

謝謝!


更新

接受託馬斯的答案...雖然它並沒有真正回答我爲什麼執行的更新帳戶加入將需要更新的權限它不是更新表的問題,我可以請參閱說「不要使用更新連接,它們不是ISO標準」的邏輯。

這是一個恥辱,因爲我有什麼和托馬斯的建議之間的差異是沒有任何嵌套的選擇在我的。如果有人知道沒有嵌套選擇的這種查詢的ISO標準方法,我很想知道!

謝謝,托馬斯!

回答

2

嘗試使用ISO批准的格式更新語句,看看是否有效。 ISO不提供在Update語句中直接使用Join。相反,您只能通過子查詢使用連接。

此外,這可能會說明您的原始更新語句中的一些問題,例如,如果用於設置approver_id的子查詢返回多個顯然會導致異常的行,您需要確定如何查找應該爲每一行設置一個且只有一個supervisor_id。

Update gs3.request_workflow 
Set approver_id = (
        Select gup.supervisor_id 
        From gs3.user_role As gur 
         Join gsu.user_profile As gup 
          On gur.user_id = gup.user_id 
        Where gup.user_role_id = gs3.request_workflow.user_role_id 
         And gup.supervisor_id != grw.approver_user_id 
        ) 
Where auth_status_cd = 'SUBMITTED'       
    And Exists (
       Select 1 
       From gs3.user_role As gur 
        Join gsu.user_profile As gup 
         On gur.user_id = gup.user_id 
       Where gup.user_role_id = gs3.request_workflow.user_role_id 
        And gup.supervisor_id != grw.approver_user_id 
       ) 
+0

因此,像這樣的選擇做更新的能力是Oracle特有的? –

+1

@James B - 將聯接烘焙到Update語句中的能力是供應商特定的,儘管供應商之間存在一些相似之處。微軟例如允許一個From子句,你可以把Joins。 MySQL將這些連接直接放入我認爲Oracle也提供的Update子句中。他們都有他們的細微差別。但是,所有供應商都支持ISO格式,這就是爲什麼我提出這個格式的原因,並且在可能出現問題的地方更清晰。 – Thomas

+0

也想問,你爲什麼說用於設置approver_id的子查詢返回多個行,並會導致異常?如果我在另一個帳戶下運行它,我寫的查詢將會正常執行,並正確更新290行。 我錯過了什麼嗎? –