9
votes

Comment SQLalchemy gère-t-il la contrainte unique dans la définition de la table?

J'ai une table avec la définition déclarative suivante: xxx

la colonne "nom" a une contrainte unique, mais je suis capable de faire xxx < / Pré>

Ainsi, comme on peut le voir, la contrainte unique n'est pas vérifiée du tout, car j'ai ajouté à la session 2 objets avec le même nom.

quand je fais une session .Commouver () , je reçois une erreur MySQL car la contrainte est également dans la table MySQL.

Est-il possible que SQLalchemy me dit à l'avance que je ne puisse pas le faire ni l'identifier et ne pas insérer 2 entrées avec le même "nom" columm? Sinon, devrais-je garder en mémoire tous les noms existants, afin que je puisse vérifier si elles n'existent pas, avant de créer l'objet?


0 commentaires

4 Réponses :


10
votes

SQLalechemy ne gère pas la piqûre, car il n'est pas possible de faire du bon sens. Même si vous gardez une trace d'objets créés et / ou vérifiez si l'objet avec ce nom existe, il existe une condition de course: toute personne d'autre processus peut insérer un nouvel objet avec le nom que vous venez de vérifier. La seule solution consiste à verrouiller toute la table avant de vérifier et de libérer la serrure après l'insertion (certaines bases de données prennent en charge un tel verrouillage).


2 commentaires

Je serai le seul à insérer des données là-bas, alors je vais vous assurer que cela ne se produit pas. Ma question est spécifiquement sur la façon dont SQLALCHEMY gère l'unicité d'un champ


@duduklein il ne traite pas l'unicité. Et ma réponse décrit pourquoi.



9
votes

AFAIK, SQLALCHÉMY ne traite pas les contraintes de l'unicité dans le comportement de Python. Ces déclarations "uniques = vraies" ne sont utilisées que pour imposer des contraintes de table de niveau de base de données, et seulement si vous créez la table à l'aide d'une commande sqlalchemy, c'est-à-dire xxx

ou d'une autre. Si vous créez un modèle SA contre une table existante qui ne présente pas cette contrainte présente, ce sera comme s'il n'existe pas.

Selon votre cas d'utilisation spécifique, vous devrez probablement utiliser un motif comme xxx

ou une variante, ou vous devez juste prendre l'exception MySQL et récupérer de là.


0 commentaires

1
votes

.One () deux types d'exceptions: sqlalchemy.orm.exc.nforesultfound sqlalchemy.orm.exc.MultiPleresultsLounds

Vous devez créer cet objet lorsque la première exception se produit, si la seconde se produit, vous êtes vissé de toute façon et ne devrait pas faire est pire. xxx


0 commentaires

2
votes

6 commentaires

Quels sont les différents entre cela et en utilisant unique = true comme présenté dans la question initiale?


unique = true ne donne pas la possibilité de spécifier un nom unique pour l'index, qui causera des problèmes d'alumbie. Voir: alembic.sqlalchemy.org/en/latest/naming.html


Ok, mais cela répond-il à la question initiale? Je pense que certaines explications de votre relation avec la question de l'OP pourraient être utiles.


Pas sûr, mais cette question est presque une décennie maintenant, et ce n'est pas la réponse acceptée.


Cela ne signifie pas que ce n'est pas encore découvert souvent. J'essaie juste de comprendre votre réponse et d'expliquer mon -1.


Appréciez que vous essayez d'apprendre! Avez-vous des questions ou y a-t-il quelque chose de spécifique que vous souhaitez comprendre à propos de SQLalchemy que je pourrais vous aider? J'ai passé 8 ans depuis 8 ans depuis que j'ai répondu à cette question (mal?) S'améliorer à Sqlalchemy! Donc, je serais heureux de vous aider de quelque manière que je puisse vous aider