[PYTHON] Conseils de définition de table sqlalchemy

tips

--Spécifier le moteur de base de données

La version est 0.9.4

Spécification du moteur de base de données

Peut être spécifié avec __table_args__

__table_args__ = {'mysql_engine': 'InnoDB'}

Contrainte unique

Facile pour une seule colonne, mais pour mettre des contraintes uniques sur plusieurs colonnes Vous devez utiliser sqlalchemy.schema.UniqueConstraint

#Seule colonne
name = Column("name", String(255), unique=True)
#Colonnes multiples
__table_args__ = (UniqueConstraint("personid", "address", name="unique_idx_personid_address"))
#le nom ne doit pas être spécifié

De plus, il semble qu'il soit nécessaire d'inclure «Unique Constraint» dans »()« pour se combiner avec la spécification InnoDB ci-dessus.

__table_args__ = (
            (UniqueConstraint('personid', 'address', name='unique_idx_personid_address')),
            {'mysql_engine': 'InnoDB'})

Contrainte de clé externe

Utilisez sqlalchemy.ForeignKey pour les contraintes de clé externe Prend en charge ʻON UPDATE et ʻON DELETE Spécifiez également du côté référencé avec sqlalchemy.orm.relationship Si backref est spécifié, ce sera une référence dans les deux sens. Référence: http://docs.sqlalchemy.org/en/rel_0_9/orm/relationships.html

#Référent
#Nom de la table dans la clé étrangère.Spécifiez le nom de la colonne
personid = Column('personid', Integer(unsigned=True), \
                  ForeignKey('person.id',onupdate='CASCADE', ondelete='CASCADE'))
#Côté référencé
#Relation avec le même retrait que la définition de colonne(Nom de classe de table(Pas un nom de table))
address = relationship("Address")
# address = relationship("Address", backref="person")

NULL

Écrivez simplement «nullable = [True or False]» dans la définition de la colonne

Int non signé dans MySQL

Utilisez sqlalchemy.dialects.mysql.INTEGER et définissez ʻINTEGER (unsigned = True)` Je ne connais rien d'autre que «mysql», mais il semble qu'il soit supporté car il existe d'autres SGBDR tels que «oracle» et «sqlite» dans «sqlalchemy.dialects».

Modèle de définition de table?

Il semble que vous pouvez l'utiliser simplement en copiant et en jouant un peu avec Prend en charge mysql Notez que create database [db_name] default charset utf8; doit être exécuté du côté mysql.

# -*- encoding:utf-8 -*-

from sqlalchemy import (Column, String, Text, ForeignKey, \
                create_engine, MetaData, DECIMAL, DATETIME, exc, event, Index)
from sqlalchemy.schema import UniqueConstraint
from sqlalchemy.orm import (sessionmaker, relationship, scoped_session)
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.dialects.mysql import INTEGER as Integer
from datetime import datetime

engine = create_engine('mysql://{user}:{passwd}@{host}/{db}'\
        .format(user=user, passwd=passwd, host=host, db=db_name),\
        encoding='utf-8', echo=False)

Session = scoped_session(sessionmaker(autocommit=False, autoflush=False, bind=engine))

metadata = MetaData(engine)
Base = declarative_base()


class Person(Base):
    __tablename__ = 'person'
    __table_args__ = {'mysql_engine': 'InnoDB'}
    id = Column('id', Integer(unsigned=True), primary_key=True, autoincrement=True)
    name = Column('name', String(255), index=True, unique=True)
    age = Column('age', Integer)
    created = Column('created', DATETIME, default=datetime.now, nullable=False)
    modified = Column('modified', DATETIME, default=datetime.now, nullable=False)
    address = relationship('Address')

    def __init__(self, name, age):
        self.name = name
        self.age = age
        now = datetime.now()
        self.created = now
        self.modified = now


class Address(Base):
    __tablename__ = 'address'
    __table_args__ = (
            (UniqueConstraint('personid', 'address', name='unique_idx_personid_address')),
            {'mysql_engine': 'InnoDB'})
    id = Column('id', Integer, primary_key=True, autoincrement=True)
    personid = Column('personid', Integer(unsigned=True), ForeignKey('person.id',
        onupdate='CASCADE', ondelete='CASCADE'))
    address = Column('address', String(255), nullable=False)
    created = Column('created', DATETIME, default=datetime.now, nullable=False)
    modified = Column('modified', DATETIME, default=datetime.now, nullable=False)

    def __init__(self, personid, address):
        self.personid = personid
        self.address = address
        now = datetime.now()
        self.created = now
        self.modified = now

if __name__ == "__main__":
    # create table
    Base.metadata.create_all(engine)

Lorsque ceci est exécuté, le tableau suivant sera créé.

mysql> desc person; +----------+------------------+------+-----+---------+----------------+ | Field | Type | Null | Key | Default | Extra | +----------+------------------+------+-----+---------+----------------+ | id | int(10) unsigned | NO | PRI | NULL | auto_increment | | name | varchar(255) | YES | UNI | NULL | | | age | int(11) | YES | | NULL | | | created | datetime | NO | | NULL | | | modified | datetime | NO | | NULL | | +----------+------------------+------+-----+---------+----------------+ 5 rows in set (0.00 sec)

mysql> desc address; +----------+------------------+------+-----+---------+----------------+ | Field | Type | Null | Key | Default | Extra | +----------+------------------+------+-----+---------+----------------+ | id | int(11) | NO | PRI | NULL | auto_increment | | personid | int(10) unsigned | YES | MUL | NULL | | | address | varchar(255) | NO | | NULL | | | created | datetime | NO | | NULL | | | modified | datetime | NO | | NULL | | +----------+------------------+------+-----+---------+----------------+

mysql> show index from person \G; *************************** 1. row *************************** Table: person Non_unique: 0 Key_name: PRIMARY Seq_in_index: 1 Column_name: id Collation: A Cardinality: 0 Sub_part: NULL Packed: NULL Null: Index_type: BTREE Comment: *************************** 2. row *************************** Table: person Non_unique: 0 Key_name: ix_person_name Seq_in_index: 1 Column_name: name Collation: A Cardinality: 0 Sub_part: NULL Packed: NULL Null: YES Index_type: BTREE Comment: 2 rows in set (0.00 sec)

ERROR: No query specified

mysql> show index from address \G; *************************** 1. row *************************** Table: address Non_unique: 0 Key_name: PRIMARY Seq_in_index: 1 Column_name: id Collation: A Cardinality: 0 Sub_part: NULL Packed: NULL Null: Index_type: BTREE Comment: *************************** 2. row *************************** Table: address Non_unique: 0 Key_name: unique_idx_personid_address Seq_in_index: 1 Column_name: personid Collation: A Cardinality: 0 Sub_part: NULL Packed: NULL Null: YES Index_type: BTREE Comment: *************************** 3. row *************************** Table: address Non_unique: 0 Key_name: unique_idx_personid_address Seq_in_index: 2 Column_name: address Collation: A Cardinality: 0 Sub_part: NULL Packed: NULL Null: Index_type: BTREE Comment: 3 rows in set (0.00 sec)

ERROR: No query specified

Recommended Posts

Conseils de définition de table sqlalchemy
Définition de table dans SQL Alchemy
Obtenez la table dynamiquement avec sqlalchemy
Générer des définitions de table SQL Alchemy à partir d'un serveur MySQL existant à l'aide de sqlacodegen
Traitement des insertions de table DB à l'aide de sqlalchemy
sqlalchemy