사용자 정의 유형이 이미 PostgreSQL에 있는지 확인
DB에 사용자 정의 유형을 생성했다고 가정 해 보겠습니다.
즉 CREATE TYPE abc ...
그러면 사용자 정의 유형이 존재하는지 여부를 판별 할 수 있습니까? 아마도 postgres 정보 테이블을 사용하고 있습니까?
그 주된 이유는 PostgreSQL이를 지원하지 않는 것 같고 CREATE OR REPLACE TYPE ...
특정 유형이 두 번 이상 생성되면 기존 유형을 먼저 삭제 한 다음 새 유형을 다시로드 할 수 있기를 바랍니다.
이 목적을 위해 함수를 생성 할 필요없이 간단한 스크립트로 유형을 생성하기위한 완전한 솔루션을 여기에 추가합니다.
--create types
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_type WHERE typname = 'my_type') THEN
CREATE TYPE my_type AS
(
--my fields here...
);
END IF;
--more types here...
END$$;
@Cromax의 답변에서 영감을 얻은 스키마에 대처하는 지금까지 찾은 가장 간단한 솔루션은 다음과 같습니다.
DO $$ BEGIN
CREATE TYPE my_type AS (/* fields go here */);
EXCEPTION
WHEN duplicate_object THEN null;
END $$;
실제로 예상 할 수있는대로-CREATE TYPE 문을 예외 처리기에 래핑하여 현재 트랜잭션을 중단하지 않습니다.
pg_type
표 에서 볼 수 있습니다 .
select exists (select 1 from pg_type where typname = 'abc');
그것이 사실이라면 abc
존재합니다.
실제로 Postgres에는 CREATE OR REPLACE
유형에 대한 기능 이 없습니다 . 따라서 가장 좋은 방법은 삭제하는 것입니다.
DROP TYPE IF EXISTS YOUR_TYPE;
CREATE TYPE YOUR_TYPE AS (
id integer,
field varchar
);
단순한 솔루션이 항상 최고의 솔루션입니다.
@bluish의 대답에 대한 @rog의 딜레마를 해결하려면 regtype
데이터 유형 을 사용하는 것이 더 적절할 수 있습니다 . 이걸 고려하세요:
DO $$ BEGIN
PERFORM 'my_schema.my_type'::regtype;
EXCEPTION
WHEN undefined_object THEN
CREATE TYPE my_schema.my_type AS (/* fields go here */);
END $$;
PERFORM
절은 비슷 SELECT
하지만 결과를 버리기 때문에 기본적으로 실제 등록 된 유형 으로 캐스트 할 수 있는지 'my_schema.my_type'
(또는 'my_type'
스키마에 특정하지 않은 경우) 확인합니다. 유형이 존재하면 "잘못된"일이 발생 RETURN
하지 않으며 전체 블록이 종료되므로 유형 my_type
이 이미 존재 하므로 변경 사항이 없습니다 . 그러나 캐스트가 불가능한 경우 42704
레이블이있는 오류 코드가 발생합니다 undefined_object
. 그래서 다음 줄에서 우리는 그 오류를 잡으려고 노력하고 만약 그럴 경우 우리는 단순히 새로운 데이터 유형을 생성합니다.
-- All of this to create a type if it does not exist
CREATE OR REPLACE FUNCTION create_abc_type() RETURNS integer AS $$
DECLARE v_exists INTEGER;
BEGIN
SELECT into v_exists (SELECT 1 FROM pg_type WHERE typname = 'abc');
IF v_exists IS NULL THEN
CREATE TYPE abc AS ENUM ('height', 'weight', 'distance');
END IF;
RETURN v_exists;
END;
$$ LANGUAGE plpgsql;
-- Call the function you just created
SELECT create_abc_type();
-- Remove the function you just created
DROP function create_abc_type();
-----------------------------------
나는 똑같은 일을하려고 노력하고 있는데, 유형이 존재하는지 확인하십시오.
--echo-hidden
( -E
) 옵션으로 psql을 시작 하고 다음을 입력했습니다 \dT
.
$ psql -E
psql (9.1.9)
testdb=> \dT
********* QUERY **********
SELECT n.nspname as "Schema",
pg_catalog.format_type(t.oid, NULL) AS "Name",
pg_catalog.obj_description(t.oid, 'pg_type') as "Description"
FROM pg_catalog.pg_type t
LEFT JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
WHERE (t.typrelid = 0 OR (SELECT c.relkind = 'c' FROM pg_catalog.pg_class c WHERE c.oid = t.typrelid))
AND NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type el WHERE el.oid = t.typelem AND el.typarray = t.oid)
AND n.nspname <> 'pg_catalog'
AND n.nspname <> 'information_schema'
AND pg_catalog.pg_type_is_visible(t.oid)
ORDER BY 1, 2;
**************************
List of data types
Schema | Name | Description
--------+------------------+-------------
public | errmsg_agg_state |
(1 row)
If you are using schemas and search_path (I am) then you'll probably need to keep the pg_catalog.pg_type_is_visible(t.oid)
check. I don't know what all the conditions in the WHERE are doing, but they didn't seem relevant to my case. Currently using:
SELECT 1 FROM pg_catalog.pg_type as t
WHERE typname = 'mytype' AND pg_catalog.pg_type_is_visible(t.oid);
A more generic solution
CREATE OR REPLACE FUNCTION create_type(name text, _type text) RETURNS
integer AS $$
DECLARE v_exists INTEGER;
BEGIN
SELECT into v_exists (SELECT 1 FROM pg_type WHERE typname = name);
IF v_exists IS NULL THEN
EXECUTE format('CREATE TYPE %I AS %s', name, _type);
END IF;
RETURN v_exists;
END;
$$ LANGUAGE plpgsql;
and then you can call it like this:
select create_type('lwm2m_instancetype', 'enum (''single'',''multiple'')');
ReferenceURL : https://stackoverflow.com/questions/7624919/check-if-a-user-defined-type-already-exists-in-postgresql
'programing' 카테고리의 다른 글
PHP : 배열에서 키 가져 오기? (0) | 2021.01.16 |
---|---|
O (n!)의 예? (0) | 2021.01.16 |
yum을 깨지 않고 파이썬 업그레이드 (0) | 2021.01.16 |
angular.js 링크 동작-특정 URL에 대한 딥 링크 비활성화 (0) | 2021.01.16 |
Twitter 부트 스트랩 모달 입력 필드 포커스 (0) | 2021.01.16 |