2012-10-17 69 views
1

有沒有一種方法可以刪除基於列名的約束?Postgres刪除列名限制

我有postgres 8.4,當我升級我的項目升級失敗,因爲約束被命名不同的版本不同。

基本上,我需要刪除一個約束,如果它存在或我可以刪除約束使用列名稱。

約束的名稱是唯一已更改的。任何想法,如果這是可能的?

在這種情況下,我需要刪除「patron_username_key」

discovery=# \d patron 
         Table "public.patron" 
      Column   |   Type    | Modifiers 
--------------------------+-----------------------------+----------- 
patron_id    | integer      | not null 
create_date    | timestamp without time zone | not null 
row_version    | integer      | not null 
display_name    | character varying(255)  | not null 
username     | character varying(255)  | not null 
authentication_server_id | integer      | 
Indexes: 
    "patron_pkey" PRIMARY KEY, btree (patron_id) 
    "patron_username_key" UNIQUE, btree (username, authentication_server_id) 
+0

什麼樣的約束?外鍵?檢查約束?不是空? –

+0

我編輯了原帖 –

回答

1

假設唯一索引是加入了獨特的約束的結果,你可以使用下面的SQL語句刪除約束:

do $$ 
declare 
    cons_name text; 
begin 
    select constraint_name 
    into cons_name 
    from information_schema.constraint_column_usage 
    where constraint_schema = current_schema() 
    and column_name in ('authentication_server_id', 'username') 
    and table_name = 'patron' 
    group by constraint_name 
    having count(*) = 2; 

    execute 'alter table patron drop constraint '||cons_name; 
end; 
$$ 

我不知道,如果你有「只這將工作「添加了一個唯一的索引(而不是唯一的約束)。

如果您需要對2列以上的數據執行此操作,則還需要調整having count(*) = 2部件以匹配column_name in ..條件中的列數。

(因爲你沒有指定你的PostgreSQL版本,我假設當前版本)

1

您可以使用System Catalogs找到回合約束。儘管如此,在單獨的pg_constraint表中提到了一些約束,如密鑰,而其他約束如NOT NULL基本上是pg_attribute表中的列。

對於按鍵,您可以使用此查詢來獲取的約束定義的列表:

SELECT pg_get_constraintdef(c.oid) AS def 
    FROM pg_class t 
    JOIN pg_constraint c ON c.conrelid=t.oid 
WHERE t.relkind='r' AND t.relname = 'table'; 

然後,您可以過濾掉引用您的列的那些和動態構造ALTER TABLE ... DROP CONSTRAINT ...語句。