Calculez les horodatages dans votre base de données, pas dans votre client
Par souci de cohérence, vous souhaiterez probablement que tout soit datetimes
calculé par votre serveur de base de données, plutôt que par le serveur d'applications. Le calcul de l'horodatage dans l'application peut entraîner des problèmes car la latence du réseau est variable, les clients subissent une dérive d'horloge légèrement différente et différents langages de programmation calculent parfois l'heure légèrement différemment.
SQLAlchemy vous permet de le faire en passant func.now()
ou func.current_timestamp()
(ce sont des alias les uns des autres) qui indique à la base de données de calculer l'horodatage lui-même.
Utilisez SQLALchemy server_default
De plus, pour une valeur par défaut où vous dites déjà à la base de données de calculer la valeur, il est généralement préférable d'utiliser à la server_default
place de default
. Cela indique à SQLAlchemy de transmettre la valeur par défaut dans le cadre de l' CREATE TABLE
instruction.
Par exemple, si vous écrivez un script ad hoc sur cette table, l'utilisation server_default
signifie que vous n'aurez pas à vous soucier de l'ajout manuel d'un appel d'horodatage à votre script - la base de données le définira automatiquement.
Comprendre SQLAlchemy onupdate
/server_onupdate
SQLAlchemy prend également en charge onupdate
afin que chaque fois que la ligne est mise à jour, il insère un nouvel horodatage. Encore une fois, mieux vaut dire à la base de données de calculer l'horodatage lui-même:
from sqlalchemy.sql import func
time_created = Column(DateTime(timezone=True), server_default=func.now())
time_updated = Column(DateTime(timezone=True), onupdate=func.now())
Il y a un server_onupdate
paramètre, mais contrairement à server_default
cela, il ne définit rien côté serveur. Il indique simplement à SQLalchemy que votre base de données changera la colonne lorsqu'une mise à jour se produit (peut-être avez-vous créé un déclencheur sur la colonne ), donc SQLAlchemy demandera la valeur de retour afin de pouvoir mettre à jour l'objet correspondant.
Un autre gotcha potentiel:
Vous serez peut-être surpris de constater que si vous apportez un ensemble de modifications dans une seule transaction, elles ont toutes le même horodatage. C'est parce que la norme SQL spécifie que CURRENT_TIMESTAMP
renvoie des valeurs basées sur le début de la transaction.
PostgreSQL fournit la non-SQL standard statement_timestamp()
et clock_timestamp()
qui ne le changement dans une transaction. Docs ici: https://www.postgresql.org/docs/current/static/functions-datetime.html#FUNCTIONS-DATETIME-CURRENT
Horodatage UTC
Si vous souhaitez utiliser les horodatages UTC, un stub d'implémentation pour func.utcnow()
est fourni dans la documentation SQLAlchemy . Vous devez cependant fournir vous-même les fonctions spécifiques au pilote.