297 votes

Comment définir une clé primaire auto incrémentée dans PostgreSQL ?

J'ai une table dans PostgreSQL avec de nombreuses colonnes, et je veux ajouter une clé primaire auto incrémentée.

J'ai essayé de créer une colonne appelée id de type BIGSERIAL mais pgadmin a répondu avec une erreur :

ERROR: sequence must have same owner as table it is linked to.

Quelqu'un sait-il comment résoudre ce problème ? Comment ajouter ou créer une clé primaire auto-incrémentée dans PostgreSQL sans recréer la table ?

4 votes

Dans Postgres 10 ou plus, considérez qu'un IDENTITY au lieu d'une colonne serial : stackoverflow.com/a/9875517/939860

336voto

A.H. Points 23369

Essayez cette commande :

ALTER TABLE your_table ADD COLUMN key_column BIGSERIAL PRIMARY KEY;

Essayez-le avec le même utilisateur de la base de données que celui que vous avez. créé la table.

80 votes

(la clé ici est d'utiliser un type de données SERIAL ou BIGSERIAL, qui crée une séquence en coulisse et l'incrémente/utilise au moment de l'insertion).

18 votes

Et si vous voulez le référencer à partir d'une autre table, utilisez integer, ou bigint

0 votes

Est-il possible de créer une clé primaire (colonne existante) dans une table sans ajouter de nouvelle colonne ?

285voto

Eric Leschinski Points 14289

Clé primaire auto incrémentée dans postgresql :

Étape 1, créez votre tableau :

CREATE TABLE epictable
(
    mytable_key    serial primary key,
    moobars        VARCHAR(40) not null,
    foobars        DATE
);

Etape 2, insérez des valeurs dans votre table comme ceci, remarquez que mytable_key n'est pas spécifié dans la première liste de paramètres, cela provoque l'auto-incrémentation de la séquence par défaut.

insert into epictable(moobars,foobars) values('delicious moobars','2012-05-01')
insert into epictable(moobars,foobars) values('worldwide interblag','2012-05-02')

Étape 3, sélectionnez * dans votre tableau :

el@voyager$ psql -U pgadmin -d kurz_prod -c "select * from epictable"

Étape 4, interpréter le résultat :

mytable_key  |        moobars        |  foobars   
-------------+-----------------------+------------
           1 | delicious moobars     | 2012-05-01
           2 | world wide interblags | 2012-05-02
(2 rows)

Observez que la colonne mytable_key a été auto incrémentée.

ProTip :

Vous devriez toujours utiliser une clé primaire sur votre table car postgresql utilise en interne des structures de table de hachage pour augmenter la vitesse des insertions, suppressions, mises à jour et sélections. Si une colonne de clé primaire (qui est obligatoirement unique et non nulle) est disponible, on peut compter sur elle pour fournir une graine unique pour la fonction de hachage. Si aucune colonne de clé primaire n'est disponible, la fonction de hachage devient inefficace car elle sélectionne un autre ensemble de colonnes comme clé.

24 votes

Un petit problème, SERIAL crée un sequence dans les coulisses : postgresql.org/docs/9.2/static/

1 votes

Est-il possible de créer une clé primaire (colonne existante) dans une table sans ajouter de nouvelle colonne ?

0 votes

Une clé étrangère déclarée avec thing_id int references epictable(mytable_key) travail ?

42voto

Eric Leschinski Points 14289

Créer une clé primaire auto incrémentée dans postgresql, en utilisant une séquence personnalisée :

Étape 1, créez votre séquence :

create sequence splog_adfarm_seq
    start 1
    increment 1
    NO MAXVALUE
    CACHE 1;
ALTER TABLE fact_stock_data_detail_seq
OWNER TO pgadmin;

Étape 2, créez votre tableau

CREATE TABLE splog_adfarm
(
    splog_key    INT unique not null,
    splog_value  VARCHAR(100) not null
);

Étape 3, insérer dans votre tableau

insert into splog_adfarm values (
    nextval('splog_adfarm_seq'), 
    'Is your family tree a directed acyclic graph?'
);

insert into splog_adfarm values (
    nextval('splog_adfarm_seq'), 
    'Will the smart cookies catch the crumb?  Find out now!'
);

Étape 4, observez les rangs

el@defiant ~ $ psql -U pgadmin -d kurz_prod -c "select * from splog_adfarm"

splog_key |                            splog_value                             
----------+--------------------------------------------------------------------
        1 | Is your family tree a directed acyclic graph?
        2 | Will the smart cookies catch the crumb?  Find out now!
(3 rows)

Les deux rangées ont des clés qui commencent à 1 et sont incrémentées de 1, comme défini par la séquence.

Bonus Elite ProTip :

Les programmeurs détestent taper, et taper le nextval('splog_adfarm_seq') est ennuyeux. Vous pouvez taper DEFAULT pour ce paramètre à la place, comme ceci :

insert into splog_adfarm values (
    DEFAULT, 
    'Sufficient intelligence to outwit a thimble.'
);

Pour que la méthode ci-dessus fonctionne, vous devez définir une valeur par défaut pour cette colonne clé dans la table splog_adfarm. Ce qui est plus joli.

2 votes

Quels sont les avantages des séquences personnalisées ? Probablement la sécurité ?

2 votes

@Masi Une des utilisations d'une séquence personnalisée pourrait être de faciliter la réplication maître-maître - ce qui serait utile si le lien de données entre deux centres de données est rompu - en permettant la création d'enregistrements sur les deux serveurs avec des ID différents, ce qui facilite ensuite la synchronisation des bases de données tout en conservant les ID générés dans les différents emplacements.

18voto

toing_toing Points 945

Si vous voulez faire cela dans pgadmin, c'est beaucoup plus facile. Il semble que dans postgressql, pour ajouter un auto-incrément à une colonne, nous devons d'abord créer une séquence d'auto-incrément et l'ajouter à la colonne requise. J'ai fait comme ceci.

1) Tout d'abord, vous devez vous assurer qu'il existe une clé primaire pour votre table. Gardez également le type de données de la clé primaire en bigint ou smallint. (J'ai utilisé bigint, je n'ai pas pu trouver un type de données appelé serial comme mentionné dans d'autres réponses ailleurs)

2)Ensuite, ajoutez une séquence en faisant un clic droit sur la séquence->. ajouter une nouvelle séquence . S'il n'y a pas de données dans le tableau, laissez la séquence telle qu'elle est, n'effectuez aucune modification. Enregistrez-la simplement. S'il y a des données existantes, ajoutez la dernière valeur ou la valeur la plus élevée de la colonne de clé primaire à la valeur actuelle dans l'onglet Définitions, comme indiqué ci-dessous. enter image description here

3)Enfin, ajoutez la ligne nextval('your_sequence_name'::regclass) à la valeur par défaut de votre clé primaire, comme indiqué ci-dessous.

enter image description here Assurez-vous que le nom de la séquence est correct ici. C'est tout et l'auto-incrémentation devrait fonctionner.

14voto

acaruci Points 130

Si vous voulez utiliser des nombres dans une séquence, définissez une nouvelle séquence avec quelque chose comme

CREATE SEQUENCE public.your_sequence
    INCREMENT 1
    START 1
    MINVALUE 1
;

puis modifiez la table pour utiliser la séquence pour l'identifiant :

ALTER TABLE ONLY table ALTER COLUMN id SET DEFAULT nextval('your_sequence'::regclass);

0 votes

Dois-je créer une nouvelle séquence pour chaque table ?

0 votes

Vous pouvez partager la même séquence pour différentes tables, mais la séquence augmentera pour chaque enregistrement de chaque table.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X