Supposons que le tableau comporte trois colonnes: username
, password
et no_of_logins
.
Lorsque l'utilisateur essaie de se connecter, il recherche une entrée avec une requête telle que
user = User.query.filter_by(username=form.username.data).first()
Si le mot de passe correspond, il continue. Ce que je voudrais faire, c'est compter le nombre de fois que l'utilisateur s'est connecté. Ainsi, chaque fois qu'il se connecte avec succès, je voudrais incrémenter le no_of_logins
champ et le stocker dans la table des utilisateurs. Je ne sais pas comment exécuter une requête de mise à jour avec SqlAlchemy.
python
sqlalchemy
flask-sqlalchemy
webminal.org
la source
la source
user.no_of_logins += 1
peut créer des conditions de course. Utilisez plutôtuser.no_of_logins = user.no_of_logins + 1
. Traduit en sql cette dernière manière correcte devient:SET no_of_logins = no_of_logins + 1
.user.no_of_logins = User.no_of_logins + 1
, ou en d'autres termes, utilisez l'attribut instrumenté du modèle pour produire une expression SQL. Tel quel, votre commentaire affiche 2 façons de produire la même condition de concurrence.Il existe plusieurs façons d'
UPDATE
utilisersqlalchemy
la source
setattr(query_result, key, value)
pour certaines mises à jour de Flask SQLAlchemy suivies d'un commit. Une raison d'écarter ce modèle?setattr(query_result, key, value)
, ce qui équivaut exactement à l'écriturequery_result.key = value
Exemples pour clarifier la question importante dans les commentaires des réponses acceptées
Je ne l'ai pas compris jusqu'à ce que j'aie joué avec moi-même, alors j'ai pensé qu'il y en aurait d'autres qui seraient également confus. Supposons que vous travaillez sur l'utilisateur dont
id == 6
et dontno_of_logins == 30
vous démarrez.Le point
En référençant la classe au lieu de l'instance, vous pouvez rendre SQLAlchemy plus intelligent dans l'incrémentation, en faisant en sorte que cela se produise du côté de la base de données au lieu du côté Python. Le faire dans la base de données est mieux car il est moins vulnérable à la corruption des données (par exemple, deux clients tentent d'incrémenter en même temps avec un résultat net d'un seul incrément au lieu de deux). Je suppose qu'il est possible de faire l'incrémentation en Python si vous définissez des verrous ou augmentez le niveau d'isolement, mais pourquoi vous embêter si vous n'êtes pas obligé?
Une mise en garde
Si vous allez incrémenter deux fois via du code qui produit du type SQL
SET no_of_logins = no_of_logins + 1
, vous devrez alors valider ou au moins vider entre les incréments, sinon vous n'obtiendrez qu'un seul incrément au total:la source
Avec l'aide de la
user=User.query.filter_by(username=form.username.data).first()
déclaration, vous obtiendrez l'utilisateur spécifié dans lauser
variable.Vous pouvez maintenant changer la valeur de la nouvelle variable objet comme
user.no_of_logins += 1
et enregistrer les modifications avec lasession
méthode de commit de.la source
J'ai écrit un robot de télégramme et j'ai des problèmes avec les lignes de mise à jour. Utilisez cet exemple, si vous avez Model
Pourquoi utiliser
db.session.flush()
? C'est pourquoi >>> SQLAlchemy: Quelle est la différence entre flush () et commit ()?la source
flush()
commit()