[sqlalchemy] Migration from django orm: override save method?

2009-06-15 Thread drakkan

Hi all,

I'm migrating from django orm to sqlalchemy, in django was very simple
to override save method to do own stuff before save the value to
database, for example:

class TestModel(models.Model):
field1=models.CharField(max_length=255)

def save():
self.field1=self.field1.upper()
super(TestModel,self).save()

so when I add or modify an object it is ever converted to uppercase.
In sa this simple model become:

class TestModel(Base)
__tablename__='testtable'
field1=Column(Unicode(255))

def __init__(field1):
self.field1=field1.upper()

this way if I call the init method field1 is converted to upper but if
i modify the field I have to manually convert to upper. There is some
way to override save method as in django orm?

regards
drakkan

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: @synonym_for lose the docstrings

2009-06-15 Thread Christophe de VIENNE
Hi,

I tried the patch, but got the following error :

/home/cdevienne/prog/sqlalchemy/lib/sqlalchemy/ext/declarative.pyc in
decorate(fn)
645 
646 def decorate(fn):
-- 647 return util.update_wrapper(_orm_synonym(name,
map_column=map_column, descriptor=fn), fn)
648 return decorate
649

/usr/lib/python2.5/functools.pyc in update_wrapper(wrapper, wrapped,
assigned, updated)
 31 
 32 for attr in assigned:
--- 33 setattr(wrapper, attr, getattr(wrapped, attr))
 34 for attr in updated:
 35 getattr(wrapper, attr).update(getattr(wrapped, attr, {}))

AttributeError: 'property' object has no attribute '__module__'

I think the problem is, in that case, that the decorator is applied on
property, not a function.

I also tried to do the following :

  def decorate(fn):
  w = _orm_synonym(name, map_column=map_column, descriptor=fn)
  w.__doc__ = fn.__doc__
  return w
  return decorate

But in my documentation, I get A combination of InsturmentedAttribute and a
regular descriptor., which is the docstring of a Proxy class defined in
proxied_attribute_factory, in attributes.py.

From what I could understand, at one moment the
attributes.register_descriptor function replace my property on the class,
and it is seems to be at that moment that the docstring is lost. I might be
completely wrong though, it is just a guess.

Thanks,

Chrisotphe

2009/6/12 Michael Bayer mike...@zzzcomputing.com


 try this patch:

 Index: lib/sqlalchemy/ext/declarative.py
 ===
 --- lib/sqlalchemy/ext/declarative.py   (revision 6051)
 +++ lib/sqlalchemy/ext/declarative.py   (working copy)
 @@ -639,8 +639,9 @@
   prop = synonym('col', descriptor=property(_read_prop, _write_prop))

 
 +
 def decorate(fn):
 -return _orm_synonym(name, map_column=map_column, descriptor=fn)
 +return util.update_wrapper(_orm_synonym(name,
 map_column=map_column, descriptor=fn), fn)
 return decorate

  def comparable_using(comparator_factory):
 @@ -661,7 +662,7 @@

 
 def decorate(fn):
 -return comparable_property(comparator_factory, fn)
 +return
 util.update_wrapper(comparable_property(comparator_factory, fn), fn)
 return decorate

  def _declarative_constructor(self, **kwargs):



 Angri wrote:
 
  I think that patch which you would like to provide could add
  functools.wraps decorator to the decorator defined in synonym_for().
  See http://docs.python.org/library/functools.html#functools.wraps
 
  --
  Anton Gritsay
  http://angri.ru
 
  On 12 ÉÀÎ, 22:20, Christophe de VIENNE cdevie...@gmail.com wrote:
  Hi,
 
  I noticed that when I use the @synonym_for decorator, my function
  docstring
  get lost.
 
  I got lost in SA code around the attributes.register_descriptor
  function,
  which is one of the steps I guess the doc is not copied (along with the
  decorator function itself), and cannot propose a patch.
 
  I workaround the issue by doing the plain synonym declaration and using
  the
  sphinx specific docstrings for class attributes, but it would be really
  great if it could just work.
 
  And thanks for the awesome tool SqlAlchemy is : it is a constant source
  of
  amazement to me.
 
  Regards,
 
  Christophe
  
 


 


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] INSERT from session.add omits field value

2009-06-15 Thread Les

I'm learning SA.  I wrote a, purposely simple, version of the tutorial
(4.8).  It, mostly, works. However, objects which have been
instantiated and can print themselves with all their fields filled
(lines begining  Person), lose the contents of their first field
when INSERTed at commit.

I'm hoping someone will point out  where I've done something or failed
to do something that's causing the error..

Thanks

Les
++

Console:
 python main.py
 dbName: sqlalTest.db
 Creating database: sqlalTest.db
2009-06-14 22:53:53,401 INFO sqlalchemy.engine.base.Engine.0x..10
SELECT name FROM  (SELECT * FROM sqlite_master UNION ALL   SELECT *
FROM sqlite_temp_master) WHERE type='table' ORDER BY name
2009-06-14 22:53:53,401 INFO sqlalchemy.engine.base.Engine.0x..10 {}
 Engine: Engine(sqlite:///sqlalTest.db), []
 Session: class 'sqlalchemy.orm.session.Sess', 
 sqlalchemy.orm.session.Sess object at 0x176a350
Entering createTables
 self.dbSession: sqlalchemy.orm.session.Sess object at 0x176a350
2009-06-14 22:53:53,402 INFO sqlalchemy.engine.base.Engine.0x..10
PRAGMA table_info(People)
2009-06-14 22:53:53,402 INFO sqlalchemy.engine.base.Engine.0x..10 {}
2009-06-14 22:53:53,403 INFO sqlalchemy.engine.base.Engine.0x..10
CREATE TABLE People (
id INTEGER NOT NULL,
firstName VARCHAR(30),
lastName VARCHAR(30),
dateCreated TIMESTAMP,
PRIMARY KEY (id)
)


2009-06-14 22:53:53,403 INFO sqlalchemy.engine.base.Engine.0x..10 {}
2009-06-14 22:53:53,440 INFO sqlalchemy.engine.base.Engine.0x..10
COMMIT
Entering initTables
 self.dbSession: sqlalchemy.orm.session.Sess object at 0x176a350
 Person: Person('Ferd','Berfle', '2009-06-14')
 Person: Person('Fannie','Farkle', '2009-06-14')
 Person: Person('Tiny','Tim', '2009-06-14')
2009-06-14 22:53:53,443 INFO sqlalchemy.engine.base.Engine.0x..10
BEGIN
2009-06-14 22:53:53,445 INFO sqlalchemy.engine.base.Engine.0x..10
INSERT INTO People (firstName, lastName, dateCreated) VALUES
(?, ?, ?)
2009-06-14 22:53:53,445 INFO sqlalchemy.engine.base.Engine.0x..10
[None, 'Berfle', '2009-06-14 00:00:00']
2009-06-14 22:53:53,446 INFO sqlalchemy.engine.base.Engine.0x..10
INSERT INTO People (firstName, lastName, dateCreated) VALUES
(?, ?, ?)
2009-06-14 22:53:53,446 INFO sqlalchemy.engine.base.Engine.0x..10
[None, 'Farkle', '2009-06-14 00:00:00']
2009-06-14 22:53:53,447 INFO sqlalchemy.engine.base.Engine.0x..10
INSERT INTO People (firstName, lastName, dateCreated) VALUES
(?, ?, ?)
2009-06-14 22:53:53,447 INFO sqlalchemy.engine.base.Engine.0x..10
[None, 'Tim', '2009-06-14 00:00:00']
2009-06-14 22:53:53,449 INFO sqlalchemy.engine.base.Engine.0x..10
COMMIT
+
SOURCE:
import datetime,os
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy import Table, Column, Integer, String, DateTime,
MetaData, \
  ForeignKey, create_engine
from sqlalchemy.orm import sessionmaker

Base = declarative_base()

class Database(object):
  global Person
  def __init__(self, dbName, config):
print( dbName: %s) % dbName
if os.path.exists(dbName) == False:
  print( Creating database: %s) % dbName
  dbUrl = 'sqlite:///' + dbName
  self.dbEngine = create_engine(dbUrl, echo=True)
  print( Engine: %s, %s) % (self.dbEngine,
self.dbEngine.table_names())
  Session = sessionmaker()
  Session.configure(bind=self.dbEngine) # Instance of Session
class w/dbEngine
  self.dbSession = Session()
  print( Session: %s, %s) % (Session, self.dbSession)

  self.createTables()
  self.initTables(config)

#
# # # Business object definitions
#

#
# # # Person object
#
  class Person(Base):
__tablename__ = 'People'

id  = Column(Integer, primary_key=True)
firstName   = Column(String(30))
lastName= Column(String(30))
dateCreated = Column(DateTime, default=datetime.date.today)

def __init__(self, firstName, lastName):
  self.firstname = firstName
  self.lastName = lastName
  self.dateCreated = datetime.date.today()

def lastNameFirst(self):
  return self.lastName + ', ' + self.firstName

def __repr__(self):
  return Person('%s','%s', '%s') % (self.firstname,
self.lastName, self.dateCreated)
#
# # # End Business object definitions
#


#
# # # Create tables
#
  def createTables(self):
print Entering createTables
print( self.dbSession: %s) % self.dbSession
Base.metadata.create_all(self.dbEngine)


#
# # # Load data from config and do basic table init
#
  def initTables(self,config):
  print Entering initTables
  print( self.dbSession: %s) % self.dbSession
  people = config.getItem('People')
  for p in people:
person = Person(p[0],p[1])
print( Person: %s) % person.__repr__()
self.dbSession.add(person)
  self.dbSession.commit()

#
# # # Create another session
#
  def createSession(self):
s = Session()
return s


[sqlalchemy] Re: INSERT from session.add omits field value

2009-06-15 Thread Michael Bayer

Les wrote:

   class Person(Base):
 __tablename__ = 'People'

 id  = Column(Integer, primary_key=True)
 firstName   = Column(String(30))
 lastName= Column(String(30))
 dateCreated = Column(DateTime, default=datetime.date.today)

 def __init__(self, firstName, lastName):

# typo  #

   self.firstname = firstName

###  #

   self.lastName = lastName
   self.dateCreated = datetime.date.today()


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: Migration from django orm: override save method?

2009-06-15 Thread Didip Kerabat
Quick note about __init__ method. SA select(..) or query(...) does not call
__init__(), so your to upper logic won't be executed then. If you want it to
be called every object construction you need to do this:

from sqlalchemy import orm

@orm.reconstructor
def some_function():
   self.field1=field1.upper()

# Call that method inside __init__ as well
def __init__(self):
   some_function()

Sorry for not answering the problem.

- Didip -

On Mon, Jun 15, 2009 at 1:43 AM, drakkan drakkan1...@gmail.com wrote:


 Hi all,

 I'm migrating from django orm to sqlalchemy, in django was very simple
 to override save method to do own stuff before save the value to
 database, for example:

 class TestModel(models.Model):
field1=models.CharField(max_length=255)

 def save():
self.field1=self.field1.upper()
super(TestModel,self).save()

 so when I add or modify an object it is ever converted to uppercase.
 In sa this simple model become:

 class TestModel(Base)
__tablename__='testtable'
field1=Column(Unicode(255))

 def __init__(field1):
self.field1=field1.upper()

 this way if I call the init method field1 is converted to upper but if
 i modify the field I have to manually convert to upper. There is some
 way to override save method as in django orm?

 regards
 drakkan

 


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: Migration from django orm: override save method?

2009-06-15 Thread Laurent Rahuel

Hi,

You should take a look at MapperExtension. Then you'll be able to add 
method which would be called depending on the orm actions.
For example, you'll be able to add your own custom before_insert or 
after_insert or after_delete methods.

Regards,

Laurent


Le 15/06/2009 17:36, Didip Kerabat a écrit :
 Quick note about __init__ method. SA select(..) or query(...) does not 
 call __init__(), so your to upper logic won't be executed then. If you 
 want it to be called every object construction you need to do this:

 from sqlalchemy import orm

 @orm.reconstructor
 def some_function():
self.field1=field1.upper()

 # Call that method inside __init__ as well
 def __init__(self):
some_function()

 Sorry for not answering the problem.

 - Didip -

 On Mon, Jun 15, 2009 at 1:43 AM, drakkan drakkan1...@gmail.com 
 mailto:drakkan1...@gmail.com wrote:


 Hi all,

 I'm migrating from django orm to sqlalchemy, in django was very simple
 to override save method to do own stuff before save the value to
 database, for example:

 class TestModel(models.Model):
field1=models.CharField(max_length=255)

 def save():
self.field1=self.field1.upper()
super(TestModel,self).save()

 so when I add or modify an object it is ever converted to uppercase.
 In sa this simple model become:

 class TestModel(Base)
__tablename__='testtable'
field1=Column(Unicode(255))

 def __init__(field1):
self.field1=field1.upper()

 this way if I call the init method field1 is converted to upper but if
 i modify the field I have to manually convert to upper. There is some
 way to override save method as in django orm?

 regards
 drakkan




 

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: Migration from django orm: override save method?

2009-06-15 Thread drakkan

Thanks,

I did it using synonym

class TestModel(Base)
__tablename__='testtable'
_field1=Column('field1',Unicode(255))

def _set_field1(self, field1):
self._field1 = self.field1.upper()

def _get_field1(self):
return self._fiedl1

field1 = synonym('_field1', descriptor=property
(_get_field1,_set_field1))

thanks
drakkan

On 15 Giu, 17:52, Laurent Rahuel laurent.rah...@gmail.com wrote:
 Hi,

 You should take a look at MapperExtension. Then you'll be able to add
 method which would be called depending on the orm actions.
 For example, you'll be able to add your own custom before_insert or
 after_insert or after_delete methods.

 Regards,

 Laurent

 Le 15/06/2009 17:36, Didip Kerabat a écrit :

  Quick note about __init__ method. SA select(..) or query(...) does not
  call __init__(), so your to upper logic won't be executed then. If you
  want it to be called every object construction you need to do this:

  from sqlalchemy import orm

  @orm.reconstructor
  def some_function():
     self.field1=field1.upper()

  # Call that method inside __init__ as well
  def __init__(self):
     some_function()

  Sorry for not answering the problem.

  - Didip -

  On Mon, Jun 15, 2009 at 1:43 AM, drakkan drakkan1...@gmail.com
  mailto:drakkan1...@gmail.com wrote:

      Hi all,

      I'm migrating from django orm to sqlalchemy, in django was very simple
      to override save method to do own stuff before save the value to
      database, for example:

      class TestModel(models.Model):
         field1=models.CharField(max_length=255)

      def save():
         self.field1=self.field1.upper()
         super(TestModel,self).save()

      so when I add or modify an object it is ever converted to uppercase.
      In sa this simple model become:

      class TestModel(Base)
         __tablename__='testtable'
         field1=Column(Unicode(255))

      def __init__(field1):
         self.field1=field1.upper()

      this way if I call the init method field1 is converted to upper but if
      i modify the field I have to manually convert to upper. There is some
      way to override save method as in django orm?

      regards
      drakkan
--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Problem getting primary key on object creation

2009-06-15 Thread JanW

I am trying to access an objects primary key either in the constructor
(preferred) or right after the object is created. And I would like to
use a scoped session for this. Below is some dummy code to illustrate
what I'm trying to do.

I defined the get_person function to first query the database to see
if the object already exists. If not it creates a new object.

As is, the code will print 2 lines with in both cases 'None' as id.

My question is, is there a way to make SA flush this object to the
database as soon as possible? Making the session autoflush=True does
not help.

It does work if I enable the Session.object_session(self).flush() line
in the constructor or in the get_person function, but this doesn't
seem like a clean way to do it, especially not in the constructor. Is
this the correct way to do it or does SA provide another, cleaner way?
I would have expected autoflush to do this.

(I can't do session.flush() since in reality session is not in the
scope of either Person.__init__() or get_person(), they are both
defined in my module's __init__.py while session is initialized in the
script that imports the module.)

Many thanks,

Jan.

### demo code:
##
from sqlalchemy import *
from sqlalchemy.orm import *

# Define SQLite databases
person_engine  = create_engine('sqlite:///person_db.sqlite')

# Define database structure
metadata=MetaData()
metadata.bind = person_engine

person_table = Table(
'person', metadata,
Column('id', Integer, primary_key=True),
Column('name', Text),
)

person_table.create()

Session = scoped_session(sessionmaker())
#Session = scoped_session(sessionmaker(autoflush=True))
session = Session()

class Person(object):
def __init__(self, name):
self.name = name
#Session.object_session(self).flush()
print In constructor: id=%s%self.id

person_mapper = Session.mapper(Person, person_table)

def get_person(name):
result = Person.query().filter_by(name=name).first()
if not result:
result = Person(name)
#Session.object_session(result).flush()
print New person made: id=%s, name=%s%(result.id,
result.name)
return result

p = get_person(Ed Jones)

session.commit()
session.close()

--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: Problem getting primary key on object creation

2009-06-15 Thread Mike Conley
Since the id will only be available after a database insert; some flavor of
session.flush() is needed. I like to keep object constructors limited to
actual object construction; so putting it in get_person() after
instantiating the person seems best approach.

-- 
Mike Conley



On Mon, Jun 15, 2009 at 4:27 PM, JanW jan.wu...@gmail.com wrote:


 I am trying to access an objects primary key either in the constructor
 (preferred) or right after the object is created. And I would like to
 use a scoped session for this. Below is some dummy code to illustrate
 what I'm trying to do.

 I defined the get_person function to first query the database to see
 if the object already exists. If not it creates a new object.

 As is, the code will print 2 lines with in both cases 'None' as id.

 My question is, is there a way to make SA flush this object to the
 database as soon as possible? Making the session autoflush=True does
 not help.

 It does work if I enable the Session.object_session(self).flush() line
 in the constructor or in the get_person function, but this doesn't
 seem like a clean way to do it, especially not in the constructor. Is
 this the correct way to do it or does SA provide another, cleaner way?
 I would have expected autoflush to do this.

 (I can't do session.flush() since in reality session is not in the
 scope of either Person.__init__() or get_person(), they are both
 defined in my module's __init__.py while session is initialized in the
 script that imports the module.)

 Many thanks,

 Jan.

 ### demo code:
 ##
 from sqlalchemy import *
 from sqlalchemy.orm import *

 # Define SQLite databases
 person_engine  = create_engine('sqlite:///person_db.sqlite')

 # Define database structure
 metadata=MetaData()
 metadata.bind = person_engine

 person_table = Table(
'person', metadata,
Column('id', Integer, primary_key=True),
Column('name', Text),
 )

 person_table.create()

 Session = scoped_session(sessionmaker())
 #Session = scoped_session(sessionmaker(autoflush=True))
 session = Session()

 class Person(object):
def __init__(self, name):
self.name = name
 #Session.object_session(self).flush()
print In constructor: id=%s%self.id

 person_mapper = Session.mapper(Person, person_table)

 def get_person(name):
result = Person.query().filter_by(name=name).first()
if not result:
result = Person(name)
 #Session.object_session(result).flush()
print New person made: id=%s, name=%s%(result.id,
 result.name)
return result

 p = get_person(Ed Jones)

 session.commit()
 session.close()

 


--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] Re: Merging and PGArray

2009-06-15 Thread Michael Bayer

this is committed in the latest trunk and will be in 0.5.5.


Michael Bayer wrote:

 Ok we'll have to ensure this doesn't break anything, that line doesn't
 seem to be covered in the current unit tests

 Roel van Os wrote:
 Hi Michael,

 On 12-06-2009 16:22, Michael Bayer wrote:
 this is likely a bug.  try out the patch below (against the latest 0.5
 release):


 After applying the patch it works perfectly. Thanks a lot!

 Regards,
 Roel

 Index: lib/sqlalchemy/orm/state.py
 ===
 --- lib/sqlalchemy/orm/state.py (revision 6049)
 +++ lib/sqlalchemy/orm/state.py (working copy)
 @@ -111,8 +111,8 @@
   return None
   elif hasattr(impl, 'get_collection'):
   return impl.get_collection(self, dict_, x,
 passive=passive)
 -elif isinstance(x, list):
 -return x
 +#elif isinstance(x, list):
 +#return x
   else:
   return [x]




 Roel van Os wrote:

 Hi all,

 In my program I'm using PGArray to store a list of strings in the
 database (defined as text[] in the schema).

 When I use Session.merge to create a copy of an object in the current
 session, the list is converted to a single string (the first from the
 list) in the copy. I've placed an example below. dont_load True or
 False
 doesn't make a difference.

 I've tested with SQLAlchemy 0.5.4 and 0.4.6.

 Any idea what the problem might be and what I can do about it?

 Thanks,
 Roel van Os

 Example code:

 #!/usr/bin/env python
 from sqlalchemy import *
 from sqlalchemy.sql import *
 from sqlalchemy.orm import *
 from sqlalchemy.ext.declarative import declarative_base
 from sqlalchemy.databases.postgres import PGArray

 Base = declarative_base()

 class TestClass(Base):
   __tablename__ = 'testclass'

   id  = Column(Integer, primary_key=True)
   test_array  = Column(PGArray(Text))

 dburl = 'postgres://:x...@/'
 engine = create_engine(dburl, convert_unicode=True, echo=False,
 pool_recycle=60)
 Session = sessionmaker(bind=engine)
 Base.metadata.create_all(engine)

 # Create a test object
 s1 = Session()
 o1 = TestClass(test_array=['1', '2', '3'])
 s1.save(o1)
 s1.commit()
 o1_id = o1.id
 s1.close()

 # Load the test object
 s2 = Session()
 o2 = s2.query(TestClass).get(o1_id)
 print o2.test_array
 assert len(o2.test_array) == 3

 # Merge the object into another session
 s3 = Session()
 o3 = s3.merge(o2, dont_load=True)

 # Should print the same as above, but prints 1
 print o3.test_array
 assert len(o3.test_array) == 3





 



 



 



--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---



[sqlalchemy] slight behavior change for relation() in 0.5.5

2009-06-15 Thread Michael Bayer

I've committed this change to the trunk and it does have a behavior
change, here's the changelog:

- The foreign_keys argument of relation() will now propagate
  automatically to the backref in the same way that
  primaryjoin and secondaryjoin do.   For the extremely
  rare use case where the backref of a relation() has
  intentionally different foreign_keys configured, both sides
  now need to be configured explicity (if they do in fact require
  this setting, see the next note...).

- ...the only known (and really, really rare) use case where a
  different foreign_keys setting was used on the forwards/backwards
  side, a composite foreign key that partially points to its own
  columns, has been enhanced such that the fk-itself aspect of the
  relation won't be used to determine relation direction.




Affect wrote:

 Thank you, Bobby and Michael. This seems to work now.

 I'm still waiting for your book, Michael. Hope it comes soon!

 A.


 On Jun 12, 5:29 pm, Michael Bayer mike...@zzzcomputing.com wrote:
 the foreign keys argument as yet is not propagated to the backref (the
 primaryjoin is), I should look into fixing that, but for now use
 backref=backref('owner', primaryjoin=pj, foreign_keys=[the foreign
 keys]).



 Affect wrote:

  Hello:

  When I use the foreign_keys argument to the relation function in the
  mapper of SA, I get the following error:

  ArgumentError: Could not determine relation direction for primaryjoin
  condition 'drm_owners.owner_id = drm_contract_royalties.contract_id',
  on relation Royalty.owner. Specify the 'foreign_keys' argument to
  indicate which columns on the relation are foreign.

  This error only shows when the 'backref' argument is specified and not
  otherwise! Is this a bug in alchemy or am I missing something?

  Here's the mapper conf:
  ===
  mapper(Royalty, royalties_table)
  mapper(Owner, owners_table,
          properties = {
              'works': relation(Work, backref='owner'),
              'royalty': relation(Royalty,

  primaryjoin=owners_table.c.owner_id==royalties_table.c.contract_id,
                  foreign_keys=[royalties_table.c.contract_id],
                  backref='owner')
              })

  So, if I remove the 'backref' argument from the call to 'relation',
  the relation works, but of course I lose the backref 'owner'.

  Thanks!
 



--~--~-~--~~~---~--~~
You received this message because you are subscribed to the Google Groups 
sqlalchemy group.
To post to this group, send email to sqlalchemy@googlegroups.com
To unsubscribe from this group, send email to 
sqlalchemy+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~--~~~~--~~--~--~---