Ошибка SQLAlchemy - «Пожалуйста, настройте один или несколько атрибутов для этих одноименных столбцов явно». - PullRequest
9 голосов
/ 17 октября 2011

Я новичок в sqlalchemy. Попытка заставить запрос работать и у меня возникли проблемы с объединением.

У меня есть две таблицы, в каждой из которых есть столбец с именем "Id", и мне нужно присоединиться к этой таблице. Мой код выглядит так:

table1 = server.tab1
table2 = server.tab2
joined = server.join(table1,table2, table1.Id == table2.Id)
where = table1.createDate > start
results = joined.filter(where).all()

Это приводит к следующему сообщению об ошибке:

Неявное объединение столбца table1.Id со столбцом table2.Id в атрибуте 'Id'. Пожалуйста, настройте один или несколько атрибутов для этих одноименных столбцов явно.

Вопрос в том, как настроить эти атрибуты?

ТИА!

Ответы [ 4 ]

1 голос
/ 23 февраля 2012

с супом sql

joined = server.session.query(table1).join((table2,table1.id == table2.id))
where = table1.createDate > start
results = joined.filter(where).all()
1 голос
/ 06 марта 2012

У меня была такая же проблема, поэтому я решил добавить решение, которое придумал (на основе http://www.mail-archive.com/sqlalchemy@googlegroups.com/msg23735.html). Это, конечно, не самая чистая вещь, которую я когда-либо кодировал, но, используя ваш пример сверху, это будет примерно:

from sqlalchemy import select
aliased_table1 = select([
    table1.c.Id.label("renamed_id_col"),
    table1.c.any_other_columns_you_want_returned_but_not_renamed,
    ...
]).correlate(None).alias()
joined = server.join(aliased_table1, table2, aliased_table1.c.renamed_id_col == table2.Id)
where = aliased_table1.c.createDate > start
results = joined.filter(where).all()
0 голосов
/ 19 марта 2012

Один из способов сделать это - пометить все столбцы в одной из таблиц, чтобы у вас не было коллизий имен столбцов:

table1 = server.tab1
table2 = server.with_labels(server.tab2)
joined = server.join(table1,table2, table1.Id == table2.tab2_Id)
where = table1.createDate > start
results = joined.filter(where).all()

table2 в конечном итоге становится помеченной таблицей,где все имена столбцов начинаются с имени таблицы, чтобы не мешать именам столбцов в таблице 1.

0 голосов
/ 18 октября 2011

Вы можете использовать функцию соединения, предоставляемую sqlalchemy, см. Пример ниже, нет необходимости делать это вручную, sqlalchme делает это за нас,

from sqlalchemy import create_engine, Column, String, Integer, Table, ForeignKey

from sqlalchemy.orm import mapper, relationship
from sqlalchemy.schema import MetaData
from sqlalchemy.orm.session import sessionmaker

from sqlalchemy.ext.declarative import declarative_base
Base = declarative_base()

class User(Base):
    __tablename__ = 'users'

    id = Column('user_id',Integer,primary_key = True)
    name = Column('user_name',String(20))

    addresses = relationship("Address",backref="user")

class Address(Base):
    __tablename__ = 'addresses'

    id = Column('user_id',ForeignKey('users.user_id'))
    address = Column('address',String(30))
    pk = Column('address_id',Integer,primary_key=1)

if __name__ == "__main__":
    engine = create_engine("sqlite://", echo = True)
    Base.metadata.create_all(engine)  
    session = sessionmaker(bind=engine)()

    u1 = User(name='japan')
    session.add(u1)
    session.commit()
    u1.addresses.append(Address(address='a1'))
    u1.addresses.append(Address(address='a2'))
    session.flush()
    q = session.query(User).join(User.addresses).all()
    print "="*23,q
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...