On Jan 11, 2008 8:41 PM, Michael Bayer <[EMAIL PROTECTED]> wrote:
> what that looks like to me is that you're attempting to query the
> database for object ID #1 using merge().
>
> when you merge(), its going to treat the object similarly to how it
> does using session.save_or_update().  that is, it looks for an
> "_instance_key" attribute to determine if the object represents a
> transient or persisted instance.
>
> So you could "hack" the way youre doing it like:
>
> obj2 = ModelObject(1, u'title2')
> obj2._instance_key = session.identity_key(instance=obj2)
> session.merge(obj2)
> session.commit()
>
> we have yet to define a completely public API for the above operation,
> i.e. "treat this object as though its persistent".  im not sure yet
> how we could define one that has a straightforward use case which
> wouldn't add confusion.

Sometimes this doesn't work:
--->8---
import sqlalchemy as sa, logging
from sqlalchemy.orm import mapper, sessionmaker, relation

logging.getLogger('sqlalchemy.engine').setLevel(logging.INFO)
logging.basicConfig()

class ModelObject(object):

    def __init__(self, id, title):
        self.id = id
        self.title = title

class ModelReferer(object):

    def __init__(self, id, object):
        self.id = id
        self.object = object

metadata = sa.MetaData()

objectsTable = sa.Table(
    'Objects', metadata,
    sa.Column('id', sa.Integer, primary_key=True),
    sa.Column('title', sa.String(255), nullable=False),
)

referersTable = sa.Table(
    'Referers', metadata,
    sa.Column('id', sa.Integer, primary_key=True),
    sa.Column('objectId', sa.Integer, sa.ForeignKey('Objects.id'),
              nullable=False),
)

objectsMapper = mapper(ModelObject, objectsTable)
referersMapper = mapper(ModelReferer, referersTable,
                        properties={'object': relation(ModelObject)})

engine = sa.create_engine('sqlite://')
metadata.create_all(engine, checkfirst=True)

session = sessionmaker(bind=engine)()

def replace(session, obj):
    identityKey = session.identity_key(instance=obj)
    oldObj = session.get(*identityKey[:2])
    if oldObj is None:
        session.save(obj)
        return obj
    else:
        obj._instance_key = identityKey
        return session.merge(obj)

obj1 = ModelObject(1, u'title1')
replace(session, obj1)
ref1 = ModelReferer(1, obj1)
replace(session, ref1)
session.commit()

session.clear()

# Another program. We have to insure that object with id=1 exists in DB and has
# certain properties.
obj2 = replace(session, ModelObject(1, u'title2'))
session.commit()

ref2 = ModelReferer(1, obj2)
replace(session, ref2)
session.commit()
--->8---

The last commit fails with:
sqlalchemy.exceptions.IntegrityError: (IntegrityError)
Referers.objectId may not be NULL u'UPDATE "Referers" SET "objectId"=?
WHERE "Referers".id = ?' [None, 1]

--~--~---------~--~----~------------~-------~--~----~
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 [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to