Black Sqlalchemy - Applicazione minima
-
21-12-2019 - |
Domanda
Sto iniziando con il pallone Sqlalchemy, ma non capisco come funziona la demo della homepage ( qui ).
Ciò creerà la struttura:
>>> from yourapplication import db
>>> db.create_all()
.
Ma non capisco dove vengono memorizzati questi utenti.
>>> from yourapplication import User
>>> admin = User('admin', 'admin@example.com')
>>> guest = User('guest', 'guest@example.com')
>>> db.session.add(admin)
>>> db.session.add(guest)
>>> db.session.commit()
.
Perché se lo faccio Select * from user;
Otterrò:
test=# \dt
List of relations
Schema | Name | Type | Owner
--------+------+-------+----------
public | user | table | postgres
(1 row)
test=# select * from user;
current_user
--------------
postgres
(1 row)
.
Tuttavia l'uscita è prevista:
>>> users = User.query.all()
>>> [<User u'admin'>, <User u'guest'>]
.
Allora, cosa sta succedendo qui?Gli utenti sono memorizzati nella cache?memoria?Perché non vedo alcun amministratore o ospite nella tabella user
.
Soluzione
Brick sta usando il nome della tabella estremamente sfortunato user
. Questa è una parola chiave riservata nel database ; Un alias per la funzione user
integrata, che è a sua volta un alias per current_user
. Ecco perché ottieni il nome della colonna current_user
quando select * from user
; Stai davvero eseguendo la pseudo-funzione current_user
.
Questo è reso più confuso dal fatto che "Utente" non utilizza la sintassi della funzione SQL, è indecortato, e dal fatto che è riscritto dal parser, quindi non c'è alcuna funzione da quel nome effettivamente definita, quindi il risultato confuso :
regress=> explain select * from user;
QUERY PLAN
--------------------------------------------------------------------
Function Scan on "current_user" (cost=0.00..0.01 rows=1 width=64)
(1 row)
.
Se si desidera descrivere o selezionare dalla tabella definita dall'utente denominata user
, per la documentazione sulle parole riservate, citano. Quindi devi scrivere:
select * from "user";
.
o
select * from public."user";
.
(Schema-qualificato).
Allo stesso modo:
\dt "user"
.
mostrerà la struttura del tavolo.
Si prega di segnalare un bug contro il pallone. Non dovrebbe usare una parola riservata SQL-92 come nome di relazione.
Modifica : il pallone sta creando una tabella chiamata 'utente' perché il nome di classe è utente. Per evitare ciò, si consiglia di fornire un'opzione __tablename__
durante la definizione del modello.
class User(db.Model):
__tablename__= 'MyUser'
....
.
In questo modo, è possibile evitare i conflitti con le convenzioni predefinite del database.