簡短故事: 我有一個分區postgres數據庫和一個表來跟蹤分區和觸發器。觸發器需要更改分區表上的約束(它們的valid_date [daterange]根據另一個分區的valid_date而改變),並且最好能夠刪除表,但是這是由於觸發鏈正在使用這些表而導致的錯誤。帶觸發器的Postgres分區管理。問題修改表
cannot ALTER TABLE "core_geometryrecord_8_2" because it is being used by active queries in this session
FULL問題: 我給我的模式和觸發架構的情況下進行徹底的解釋是需要或有人想知道爲什麼我覺得對於一個「令人費解」的必要性系統,儘管它可能沒有必要。
我正在重構幾何數據的大型數據庫,以便使用起來更加方便快捷。舊系統具有保持相關幾何形狀的「幾何圖表」(美國的I.E.縣)。數據應該真正按「date_valid」和「geometrytable_id」分組。
我們決定在date_valid(日期範圍)和geometrytable_id(外鍵)上使用帶有約束的postgres分區。
因爲日期很敏感,並且需要大量的記錄以保持正確,所以我試着用管理大部分數據庫的觸發器(我已經知道我需要分區表的插入觸發器,所以爲什麼不)。
我設計了一組觸發器來管理分區列表,並在插入或刪除幾何時執行所有記錄。這是他們做的。
- 在插入分區列表表中創建分區表並應用約束。如果對於與新的重疊的日期(呼叫更新觸發器)存在分區有效,請對其進行修改。如果有一個分區在此日期之後有效,則修剪新的分區結束日期以開始下一個分區的日期(保持連續的時間軸)。
- 從分區列表中刪除時,刪除分區表。重新計算已刪除分區(如果有)的partition_list條目的日期範圍(Call Update Trigger)以使日期連續。
- 在更新分區列表表中,DROP OLD DATE CONSTRAINT,將分區表中所有行的date_valid更改爲分區的新date_valid值,然後使用新日期創建DATE CONSTRAINT(約束條件是項目具有完全相同date_valid作爲分區)。
- 在插入到geometryrecord(分區表)中時,找到應該使用的分區,或INSERT插入分區列表表(TRIGGERS ON INSERT)。將NEW插入正確的分區。
- 從geometryrecord刪除時,如果分區表現在爲空,請從分區列表表(CALLS DELETE TRIGGER)中刪除分區條目。
如果我試圖以任何方式改變表格,只要我在鏈條中的任何觸發器上觸摸它,它就會一直生氣。如果我直接插入到該表中,分區列表表格的觸發器可以很好地工作,但從幾何表(即調用同一個觸發器)中刪除即使它正在做的只是一個select(查看分區表是否爲空),也會彈出。插入到分區幾何表中也會導致問題,因爲我必須刪除約束才能更改行的date_valid。
必須有一種方法可以做到這一點,我只是不明白。 (我還必須刪除表格,使其更加被動'標記爲由cron作業刪除',因爲我無法從源自我要刪除的表格的觸發器調用中刪除表格)。
任何建議將非常受歡迎。我無法相信沒有人需要做這樣的事情,所以我假設我只是不知道自己在做什麼:)。
你是從觸發器內部做DDL的嗎? – wildplasser
哇,我想我剛剛瞭解DDL和DML之間的區別(主要是有差異)。是的,我需要在觸發器內進行修改或刪除。 –