lo tanto, tengo tres tablas:¿Cómo puedo unir tres tablas con SQLalchemy y mantener todas las columnas en una de las tablas?
Los defenitions clase:
engine = create_engine('sqlite://test.db', echo=False)
SQLSession = sessionmaker(bind=engine)
Base = declarative_base()
class Channel(Base):
__tablename__ = 'channel'
id = Column(Integer, primary_key = True)
title = Column(String)
description = Column(String)
link = Column(String)
pubDate = Column(DateTime)
class User(Base):
__tablename__ = 'user'
id = Column(Integer, primary_key = True)
username = Column(String)
password = Column(String)
sessionId = Column(String)
class Subscription(Base):
__tablename__ = 'subscription'
userId = Column(Integer, ForeignKey('user.id'), primary_key=True)
channelId = Column(Integer, ForeignKey('channel.id'), primary_key=True)
NOTA: Sé user.username debe ser único, tienen que arreglar eso, y no estoy seguro de por qué sqlalchemy crea algunos nombres de fila con las comillas dobles.
Y estoy tratando de encontrar una manera de recuperar todos los canales, así como una indicación de en qué canales tiene un usuario en particular (identificado por user.sessionId junto con user.id) tiene una suscripción.
Por ejemplo, supongamos que tenemos cuatro canales: canal1, canal2, canal3, canal4; un usuario: usuario1; quién tiene una suscripción en channel1 y channel4. La consulta de usuario1 volvería algo como:
channel.id | channel.title | subscribed
---------------------------------------
1 channel1 True
2 channel2 False
3 channel3 False
4 channel4 True
Este es un resultado mejor de los casos, pero ya no tengo absolutamente ninguna pista sobre cómo llevar a cabo la columna suscrito, he estado en su lugar tratando de hacer que los usuarios particulares id en las filas donde el usuario tiene una suscripción y donde falta una suscripción, simplemente déjelo en blanco.
El motor de base de datos que estoy utilizando junto con SQLalchemy atm. es sqlite3
Me he estado rascando la cabeza por esto durante dos días, no tengo problemas para unir los tres por medio de la tabla de suscripción pero luego todos los canales donde el usuario no tiene una suscripción omitido
Espero haber logrado describir mi problema lo suficiente, gracias de antemano.
EDITAR: logró resolver esto de una manera un poco torpe que implica una sub-consulta:
# What a messy SQL query!
stmt = query(Subscription).filter_by(userId = uid()).join((User, Subscription.userId == User.id)).filter_by(sessionId = id()).subquery()
subs = aliased(Subscription, stmt)
results = query(Channel.id, Channel.title, subs.userId).outerjoin((subs, subs.channelId == Channel.id))
Sin embargo, voy a seguir buscando una solución más elegante, por lo que las respuestas siguen siendo muy muy bienvenido
¿Puede agregar las definiciones de su modelo/tabla? Dependiendo de si utiliza el asignador declarativo, el correlacionador normal o las tablas simples, la sintaxis difiere un poco. – Wolph
Pregunta hecha y actualizada, ese sería el mapeador declarativo a menos que esté equivocado. – jimka
Ese es el mapeador de declaracion de hecho :) – Wolph