summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2013-12-12 12:49:57 -0500
committerMike Bayer <mike_mp@zzzcomputing.com>2013-12-12 12:53:34 -0500
commit69154698d20d1c15cee83990ec719d1deaf193ae (patch)
treeb1e6dd953a1e4a126c85c4ec5e3efdb09f82238c
parenta6eaf1cceb00f81053a3139c38e9650ecc297cc0 (diff)
downloadsqlalchemy-69154698d20d1c15cee83990ec719d1deaf193ae.tar.gz
- Error message when a string arg sent to :func:`.relationship` which
doesn't resolve to a class or mapper has been corrected to work the same way as when a non-string arg is received, which indicates the name of the relationship which had the configurational error. [ticket:2888] Conflicts: lib/sqlalchemy/orm/relationships.py
-rw-r--r--doc/build/changelog/changelog_08.rst13
-rw-r--r--lib/sqlalchemy/orm/properties.py28
-rw-r--r--test/ext/declarative/test_basic.py32
3 files changed, 59 insertions, 14 deletions
diff --git a/doc/build/changelog/changelog_08.rst b/doc/build/changelog/changelog_08.rst
index 7fd698ad6..b65dd77cd 100644
--- a/doc/build/changelog/changelog_08.rst
+++ b/doc/build/changelog/changelog_08.rst
@@ -9,6 +9,19 @@
:start-line: 5
.. changelog::
+ :version: 0.8.5
+
+ .. change::
+ :tags: bug, declarative
+ :versions: 0.9.0b2
+ :tickets: 2888
+
+ Error message when a string arg sent to :func:`.relationship` which
+ doesn't resolve to a class or mapper has been corrected to work
+ the same way as when a non-string arg is received, which indicates
+ the name of the relationship which had the configurational error.
+
+.. changelog::
:version: 0.8.4
:released: December 8, 2013
diff --git a/lib/sqlalchemy/orm/properties.py b/lib/sqlalchemy/orm/properties.py
index f832091c0..da751404b 100644
--- a/lib/sqlalchemy/orm/properties.py
+++ b/lib/sqlalchemy/orm/properties.py
@@ -997,23 +997,23 @@ class RelationshipProperty(StrategizedProperty):
This is a lazy-initializing static attribute.
"""
- if isinstance(self.argument, type):
- mapper_ = mapper.class_mapper(self.argument,
- configure=False)
- elif isinstance(self.argument, mapper.Mapper):
- mapper_ = self.argument
- elif util.callable(self.argument):
-
- # accept a callable to suit various deferred-
- # configurational schemes
-
- mapper_ = mapper.class_mapper(self.argument(),
- configure=False)
+
+ if util.callable(self.argument) and \
+ not isinstance(self.argument, (type, mapperlib.Mapper)):
+ argument = self.argument()
+ else:
+ argument = self.argument
+
+ if isinstance(argument, type):
+ mapper_ = mapperlib.class_mapper(argument,
+ configure=False)
+ elif isinstance(self.argument, mapperlib.Mapper):
+ mapper_ = argument
+
else:
raise sa_exc.ArgumentError("relationship '%s' expects "
"a class or a mapper argument (received: %s)"
- % (self.key, type(self.argument)))
- assert isinstance(mapper_, mapper.Mapper), mapper_
+ % (self.key, type(argument)))
return mapper_
@util.memoized_property
diff --git a/test/ext/declarative/test_basic.py b/test/ext/declarative/test_basic.py
index 4b5736c9f..1596b78d3 100644
--- a/test/ext/declarative/test_basic.py
+++ b/test/ext/declarative/test_basic.py
@@ -123,6 +123,38 @@ class DeclarativeTest(DeclarativeTestBase):
assert class_mapper(Bar).get_property('some_data').columns[0] \
is t.c.data
+ def test_relationship_level_msg_for_invalid_callable(self):
+ class A(Base):
+ __tablename__ = 'a'
+ id = Column(Integer, primary_key=True)
+ class B(Base):
+ __tablename__ = 'b'
+ id = Column(Integer, primary_key=True)
+ a_id = Column(Integer, ForeignKey('a.id'))
+ a = relationship('a')
+ assert_raises_message(
+ sa.exc.ArgumentError,
+ "relationship 'a' expects a class or a mapper "
+ "argument .received: .*Table",
+ configure_mappers
+ )
+
+ def test_relationship_level_msg_for_invalid_object(self):
+ class A(Base):
+ __tablename__ = 'a'
+ id = Column(Integer, primary_key=True)
+ class B(Base):
+ __tablename__ = 'b'
+ id = Column(Integer, primary_key=True)
+ a_id = Column(Integer, ForeignKey('a.id'))
+ a = relationship(A.__table__)
+ assert_raises_message(
+ sa.exc.ArgumentError,
+ "relationship 'a' expects a class or a mapper "
+ "argument .received: .*Table",
+ configure_mappers
+ )
+
def test_difficult_class(self):
"""test no getattr() errors with a customized class"""