Jaka jest różnica między declarative_base () a db.Model?

86

Szybki poradnik do kolby-SQLAlchemy wtyczki zobowiązuje użytkowników do tworzenia modeli stołów dziedziczy db.Modelklasę, np

app = Flask(__main__)
db = SQLAlchemy(app)
class Users(db.Model):
    __tablename__ = 'users'
    ...

Jednak samouczek SQLAlchemy i plik README z pliku SQLAlchemy sugerują, że modele tabel dziedziczą Baseinstancję utworzoną z declarative_base().

Base = declarative_base()
class Users(Base):
    __tablename__ = 'users'
    ...

Jaka jest różnica między tymi dwoma podejściami?

drs
źródło

Odpowiedzi:

84

Przeglądając kod źródłowy Flask-SQLAlchemy, db.Modelklasa jest inicjowana w następujący sposób:

self.Model = self.make_declarative_base()

A oto make_declarative_base()metoda:

def make_declarative_base(self):
    """Creates the declarative base."""
    base = declarative_base(cls=Model, name='Model',
                            metaclass=_BoundDeclarativeMeta)
    base.query = _QueryProperty(self)
    return base

_BoundDeclarativeMetaMetaklasa jest podklasą SQLAlchemy użytkownika DeclarativeMeta, to po prostu dodaje wsparcie dla obliczania wartości domyślnej __tablename__(nazwa tabeli), a także wiąże uchwytem.

Ta base.querywłaściwość umożliwia modelom opartym na Flask-SQLAlchemy uzyskiwanie dostępu do obiektu zapytania Model.queryzamiast SQLAlchemy session.query(Model).

_QueryPropertyKlasa zapytanie jest również podklasy z zapytaniem sqlalchemy użytkownika. Kolby-SQLAlchemy podklasa dodaje trzy dodatkowe metody zapytań, które nie istnieją w SQLAlchemy: get_or_404(), first_or_404()i paginate().

Uważam, że to jedyne różnice.

Miguel
źródło
1
Po prostu szukałem tego dzisiaj dla tej aplikacji, którą budowałem przez mniej więcej rok, pierwotnie w oparciu o twój "Mega Flask Tutorial", który używa db.Model zamiast jawnie używać Base = Declarative_Base. Byłem zdezorientowany, ponieważ wszystkie moje modele wyraźnie używają rozszerzenia deklaratywnego, ale jeszcze nigdy nie wywołałem declarative_base (). Dzięki za świetne wyjaśnienie!
Chockomonkey,
Czy można używać db.Model w jednym modelu użytkownika i Base w modelu adresu. Na przykład: - klasa User (db.Model), class Address (Base)?
Saif ali Karedia
Nie jestem pewien, ale przypuszczam, że niektóre rzeczy nie będą działać. Flask-SQLAlchemy dodaje pewne zachowanie do bazy w db.Modelklasie, więc żadne modele, które dziedziczą bezpośrednio z bazy deklaratywnej, nie będą tego miały.
Miguel