Jak mogę zaktualizować informacje o wierszu?Flask-SQLalchemy aktualizuje informacje o rzędzie
Przykładowo będę się zmienić kolumnę Nazwa rzędu, która ma identyfikator 5.
Jak mogę zaktualizować informacje o wierszu?Flask-SQLalchemy aktualizuje informacje o rzędzie
Przykładowo będę się zmienić kolumnę Nazwa rzędu, która ma identyfikator 5.
pobrać obiekt za pomocą tutorial shown in the Flask-SQLAlchemy documentation. Kiedy już masz byt, który chcesz zmienić, zmień sam obiekt. Następnie db.session.commit()
.
Na przykład:
admin = User.query.filter_by(username='admin').first()
admin.email = '[email protected]'
db.session.commit()
user = User.query.get(5)
user.name = 'New Name'
db.session.commit()
skrzynkowego SQLAlchemy jest oparta na SQLAlchemy, więc pamiętaj o: sprawdzeniu SQLAlchemy Docs również.
Istnieje metoda update
dla obiektu BaseQuery w SQLAlchemy, która jest zwracana przez filter_by
.
admin = User.query.filter_by(username='admin').update(dict(email='[email protected]')))
db.session.commit()
Zaletą korzystania update
nad zmianą podmiotu przychodzi, gdy istnieje wiele obiektów mają być aktualizowane.
Jeśli chcesz dać add_user
pozwolenie na wszystkich admin
s
rows_changed = User.query.filter_by(role='admin').update(dict(permission='add_user'))
db.session.commit()
Uwaga, filter_by
bierze argumenty słów kluczowych (tylko jeden =
używania), w przeciwieństwie do filter
który trwa wyrażenia.
To nie działa, jeśli modyfikuje się piklowany atrybut modelu. Marynowane atrybuty powinny zostać zastąpione w celu uruchomienia aktualizacji:
from flask import Flask
from flask.ext.sqlalchemy import SQLAlchemy
from pprint import pprint
app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqllite:////tmp/users.db'
db = SQLAlchemy(app)
class User(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(80), unique=True)
data = db.Column(db.PickleType())
def __init__(self, name, data):
self.name = name
self.data = data
def __repr__(self):
return '<User %r>' % self.username
db.create_all()
# Create a user.
bob = User('Bob', {})
db.session.add(bob)
db.session.commit()
# Retrieve the row by its name.
bob = User.query.filter_by(name='Bob').first()
pprint(bob.data) # {}
# Modifying data is ignored.
bob.data['foo'] = 123
db.session.commit()
bob = User.query.filter_by(name='Bob').first()
pprint(bob.data) # {}
# Replacing data is respected.
bob.data = {'bar': 321}
db.session.commit()
bob = User.query.filter_by(name='Bob').first()
pprint(bob.data) # {'bar': 321}
# Modifying data is ignored.
bob.data['moo'] = 789
db.session.commit()
bob = User.query.filter_by(name='Bob').first()
pprint(bob.data) # {'bar': 321}
Wystarczy przypisywania wartości i zobowiązując je będzie działać dla wszystkich typów danych, ale JSON i marynowane atrybutów. Ponieważ wytłuszczony typ jest wyjaśniony powyżej, zapiszę nieco inny, ale łatwy sposób na aktualizację JSON-ów.
class User(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(80), unique=True)
data = db.Column(db.JSON)
def __init__(self, name, data):
self.name = name
self.data = data
Załóżmy, że model wygląda jak wyżej.
user = User("Jon Dove", {"country":"Sri Lanka"})
db.session.add(user)
db.session.flush()
db.session.commit()
Będzie dodać użytkownika do bazy danych MySQL z danymi { "kraju": "Sri Lanka"}
Modyfikowanie dane zostaną zignorowane. Mój kod, który nie działał, jest następujący.
user = User.query().filter(User.name=='Jon Dove')
data = user.data
data["province"] = "south"
user.data = data
db.session.merge(user)
db.session.flush()
db.session.commit()
Zamiast przeżywa bolesne pracy kopiowania JSON do nowego dict (nie przypisaniem go do nowej zmiennej, jak wyżej), które powinny pracował znalazłem prosty sposób aby to zrobić. Istnieje sposób oznaczenia systemu, który zmienił system JSON.
Poniżej znajduje się działający kod.
from sqlalchemy.orm.attributes import flag_modified
user = User.query().filter(User.name=='Jon Dove')
data = user.data
data["province"] = "south"
user.data = data
flag_modified(user, "data")
db.session.merge(user)
db.session.flush()
db.session.commit()
To działało jak czar. Jest jeszcze jedna metoda zaproponowana wraz z tą metodą. here Mam nadzieję, że pomogłem komuś.
Dzięki Mark. Jeszcze jedna rzecz. Widziałem, jak to robiono "db.add (użytkownik)", a następnie "dv.session.commit()". Dlaczego oba działają?i jaka jest różnica? – pocorschi
Ma to związek z różnicami między obiektami przejściowymi, odłączonymi i dołączonymi w SQLAlchemy (zobacz http://www.sqlalchemy.org/docs/orm/session.html#what-does-the-session-do). Przeczytaj także komentarz Michaela Bayera na liście mailingowej (http://groups.google.com/group/sqlalchemy/browse_thread/thread/e38e2aba57aeed92?pli=1), aby uzyskać więcej informacji. –
Jeśli nadal jesteś zdezorientowany różnicami po przeczytaniu tam, rozważ zadawanie innego pytania. –