2010-05-27 19 views
23

No soy un experto en bases de datos, solo sé lo básico, de verdad. Recogí SQLAlchemy para un proyecto pequeño, y estoy usando la configuración de base declarativa en lugar de la forma "normal". De esta manera parece mucho más simple.¿Cómo funcionan las relaciones simples de SQLAlchemy?

Sin embargo, al configurar mi esquema de base de datos, me di cuenta de que no entiendo algunos conceptos de relaciones de bases de datos.

Si tuviera una relación de muchos a uno antes, por ejemplo, artículos de autores (donde cada artículo podría ser escrito por un solo autor), pondría un campo author_id en mi columna articles. Pero SQLAlchemy tiene este objeto ForeignKey y una función de relación con un kwarg de respaldo, y no tengo idea de lo que SIGNIFICA.

Tengo miedo de descubrir cómo se ve una relación de muchos a varios con una tabla intermedia (cuando necesito datos adicionales sobre cada relación).

¿Alguien puede desmitificar esto para mí? En este momento estoy configurando para permitir la autenticación de openID para mi aplicación. Así lo he entendido:

from __init__ import Base 
from sqlalchemy.schema import Column 
from sqlalchemy.types import Integer, String 

class Users(Base): 
    __tablename__ = 'users' 
    id = Column(Integer, primary_key=True) 
    username = Column(String, unique=True) 
    email = Column(String) 
    password = Column(String) 
    salt = Column(String) 


class OpenID(Base): 
    __tablename__ = 'openid' 
    url = Column(String, primary_key=True) 
    user_id = #? 

creo que el ? debe sustituirse por Column(Integer, ForeignKey('users.id')), pero no estoy seguro - y necesito para poner openids = relationship("OpenID", backref="users") en la clase de usuarios? ¿Por qué? ¿Qué hace? ¿Qué es un backref?

Respuesta

35

Sí, necesita user_id = Column(Integer, ForeignKey('users.id')) o user_id = Column(Integer, ForeignKey('users.id'), nullable=False) si es obligatorio. Esto se traduce directamente a FOREIGN KEY en el esquema subyacente de la base de datos, sin magia.

La manera simple de declarar la relación es user = relationship(Users) en la clase OpenID. También puede usar users = relationship('OpenID') en la clase Users. El parámetro backref le permite declarar ambas relaciones con declaración única: significa instalar automáticamente una relación inversa en la clase relacionada. Personalmente prefiero usar backref -s solo para relaciones autorreferentes. La razón es que me gusta el código auto-documentado: cuando miras a través de su definición, ves todas las propiedades definidas, mientras que con backref necesitas mirar a través de otras clases (probablemente definidas en otros módulos).

+0

Gran respuesta, gracias. Estoy sorprendido de que haya tardado tanto, y nadie más haya respondido ... Parece algo que mucha gente sabría. Oh, bueno :) –

+2

Esta es una gran respuesta, muy clara. También prefiero el código auto-documentado. A tal efecto, SQLAlchemy, desde 0.5.1, proporciona una alternativa a 'backref' que es [' back_populates'] (http://docs.sqlalchemy.org/en/latest/orm/relationship_api.html#sqlalchemy.orm. relationship.params.back_populates). Los documentos presentan más aclaraciones y un ejemplo: http://docs.sqlalchemy.org/en/latest/orm/backref.html#relationships-backref – iled

Cuestiones relacionadas