sql >> Database >  >> RDS >> PostgreSQL

Postgres ENUM-gegevenstype of CHECK CONSTRAINT?

Op basis van de opmerkingen en antwoorden hier, en wat rudimentair onderzoek, heb ik de volgende samenvatting te bieden voor opmerkingen van de Postgres-erati. Zal uw inbreng zeer op prijs stellen.

Er zijn drie manieren om vermeldingen in een kolom van een Postgres-databasetabel te beperken. Overweeg een tabel om "kleuren" op te slaan waar u wilt dat alleen 'rood', 'groen' of 'blauw' geldige vermeldingen zijn.

  1. Genummerd gegevenstype

    CREATE TYPE valid_colors AS ENUM ('red', 'green', 'blue');
    
    CREATE TABLE t (
        color VALID_COLORS
    );
    

    Voordelen zijn dat het type eenmaal kan worden gedefinieerd en vervolgens in zoveel tabellen als nodig kan worden hergebruikt. Een standaardquery kan alle waarden voor een ENUM-type weergeven en kan worden gebruikt om aanvraagformulier-widgets te maken.

    SELECT  n.nspname AS enum_schema,  
            t.typname AS enum_name,  
            e.enumlabel AS enum_value
    FROM    pg_type t JOIN 
            pg_enum e ON t.oid = e.enumtypid JOIN 
            pg_catalog.pg_namespace n ON n.oid = t.typnamespace
    WHERE   t.typname = 'valid_colors'
    
     enum_schema | enum_name     | enum_value 
    -------------+---------------+------------
     public      | valid_colors  | red
     public      | valid_colors  | green
     public      | valid_colors  | blue
    

    Nadelen zijn dat het ENUM-type wordt opgeslagen in systeemcatalogi, dus een zoekopdracht zoals hierboven is vereist om de definitie ervan te bekijken. Deze waarden zijn niet zichtbaar bij het bekijken van de tabeldefinitie. En aangezien een ENUM-type eigenlijk een gegevenstype is dat losstaat van de ingebouwde gegevenstypes NUMERIEK en TEKST, werken de reguliere numerieke en tekenreeksoperatoren en functies er niet op. Je kunt dus geen zoekopdracht als

    SELECT FROM t WHERE color LIKE 'bl%'; 
    
  2. Beperkingen controleren

    CREATE TABLE t (
        colors TEXT CHECK (colors IN ('red', 'green', 'blue'))
    );
    

    Twee voordelen zijn dat, één, "wat je ziet is wat je krijgt", dat wil zeggen dat de geldige waarden voor de kolom direct in de tabeldefinitie worden vastgelegd, en twee, alle oorspronkelijke tekenreeks- of numerieke operatoren werken.

  3. Buitenlandse sleutels

    CREATE TABLE valid_colors (
        id SERIAL PRIMARY KEY NOT NULL,
        color TEXT
    );
    
    INSERT INTO valid_colors (color) VALUES 
        ('red'),
        ('green'),
        ('blue');
    
    CREATE TABLE t (
        color_id INTEGER REFERENCES valid_colors (id)
    );
    

    In wezen hetzelfde als het maken van een ENUM-type, behalve dat de native numerieke of tekenreeksoperators werken, en dat men geen systeemcatalogi hoeft te doorzoeken om de geldige waarden te ontdekken. Een join is vereist om de color_id . te koppelen naar de gewenste tekstwaarde.



  1. Is het voorvoegsel sp_ nog steeds een nee-nee?

  2. Operand moet 1 kolom bevatten - MySQL NIET IN

  3. Kan niet zomaar de PostgreSQL-tabelnaam gebruiken (relatie bestaat niet)

  4. Foutcode:1005. Kan tabel '...' niet maken (fout:150)