Thanks for your prompt response.

Assuming I fully compose the primary keys, I am still struggling with
merge():

The model is exactly as I've pasted in my original post, except that
I've changed the mapper to cascade delete and delete-orphan, since I
read it would solve my issue...

So the new mapper is:

=======
orderdetail_mapper = mapper(OrderDetail, order_detail_table,
        properties=dict(parentorder=relation(Order,
                            cascade='all,delete-orphan',single_parent=True,
                            backref='orderdetails')))
=======

Start over with a fresh database. Now, I add two "line details" like
my original post.


================
ord = Order()
ord.id = '55'
ord.customer = 'Kent'

ln1 = OrderDetail()
ln1.line = 1
ln1.orderid = '55'
ln1.product = 'DESK'

ln2 = OrderDetail()
ln2.line = 2
ln2.orderid = '55'
ln2.product = 'WHITESECTIONAL'

ord.orderdetails = [ln1,ln2]

session.add(ord)
session.flush()
session.commit()
==================


This behaves as I expected.

Now, onto merge.  Say that ln1 has been deleted and ln3 added:


====
ord = Order()
ord.id = '55'
ord.customer = 'Kent'

ln2 = OrderDetail()
ln2.line = 2
ln2.orderid = '55'
ln2.product = 'WHITESECTIONAL'

ln3 = OrderDetail()  # new line
ln3.line = 3
ln3.orderid = '55'
ln3.product = 'CHAIR'

ord.orderdetails = [ln2,ln3]

dbord = session.merge(ord)
session.commit()
======


I expected merge to INSERT ln3 (which it attempts to do) and DELETE
ln1, which it doesn't do, but fails with this exception:

AssertionError: Dependency rule tried to blank-out primary key column
'orderdetails.orderid' on instance '<OrderDetail at 0x2cc5850>'


Is my use-case for merge() still not really what it was designed for?
Can you explain what is going on or what I am doing wrong?


Third question: I extrapolate that merge() expects *all* fields are
populated?  In other words, if merge() encounters a field whose value
is None, will it update that field to null in the database (as opposed
to leaving the value untouched in the database)?  Does None mean
"leave it alone" or "update to null"?




full output pasted here:
===========
2010-01-14 02:45:16,296 INFO sqlalchemy.engine.base.Engine.0x...4e50
BEGIN
2010-01-14 02:45:16,296 INFO sqlalchemy.engine.base.Engine.0x...4e50
SELECT orders.id AS orders_id, orders.customer AS orders_customer
FROM orders
WHERE orders.id = :param_1
2010-01-14 02:45:16,296 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'param_1': '55'}
2010-01-14 02:45:16,298 INFO sqlalchemy.engine.base.Engine.0x...4e50
SELECT orderdetails.orderid AS orderdetails_orderid, orderdetails.line
AS orderdetails_line, orderdetails.product AS orderdetails_product,
orderdetails.qtyordered AS orderdetails_qtyordered
FROM orderdetails
WHERE orderdetails.orderid = :param_1 AND orderdetails.line = :param_2
2010-01-14 02:45:16,298 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'param_1': '55', 'param_2': 2}
2010-01-14 02:45:16,302 INFO sqlalchemy.engine.base.Engine.0x...4e50
SELECT orderdetails.orderid AS orderdetails_orderid, orderdetails.line
AS orderdetails_line, orderdetails.product AS orderdetails_product,
orderdetails.qtyordered AS orderdetails_qtyordered
FROM orderdetails
WHERE orderdetails.orderid = :param_1 AND orderdetails.line = :param_2
2010-01-14 02:45:16,302 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'param_1': '55', 'param_2': 3}
2010-01-14 02:45:16,305 INFO sqlalchemy.engine.base.Engine.0x...4e50
SELECT orderdetails.qtyordered AS orderdetails_qtyordered
FROM orderdetails
WHERE orderdetails.orderid = :param_1 AND orderdetails.line = :param_2
2010-01-14 02:45:16,305 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'param_1': '55', 'param_2': 3}
/home/rarch/tg2env/lib/python2.6/site-packages/SQLAlchemy-0.5.2-
py2.6.egg/sqlalchemy/engine/default.py:241: SAWarning: Unicode type
received non-unicode bind param value 'CHAIR'
  param[key.encode(encoding)] = processors[key](compiled_params[key])
2010-01-14 02:45:16,306 INFO sqlalchemy.engine.base.Engine.0x...4e50
INSERT INTO orderdetails (orderid, line, product, qtyordered) VALUES
(:orderid, :line, :product, :qtyordered)
2010-01-14 02:45:16,307 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'orderid': '55', 'line': 3, 'product': 'CHAIR', 'qtyordered': None}
2010-01-14 02:45:16,308 INFO sqlalchemy.engine.base.Engine.0x...4e50
SELECT orderdetails.orderid AS orderdetails_orderid, orderdetails.line
AS orderdetails_line, orderdetails.product AS orderdetails_product,
orderdetails.qtyordered AS orderdetails_qtyordered
FROM orderdetails
WHERE :param_1 = orderdetails.orderid
2010-01-14 02:45:16,308 INFO sqlalchemy.engine.base.Engine.0x...4e50
{'param_1': '55'}
>>>
>>>
>>>
>>> session.commit()
2010-01-14 02:45:30,143 INFO sqlalchemy.engine.base.Engine.0x...4e50
ROLLBACK
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/session.py", line 673, in
commit
    self.transaction.commit()
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/session.py", line 378, in
commit
    self._prepare_impl()
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/session.py", line 362, in
_prepare_impl
    self.session.flush()
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/session.py", line 1347, in
flush
    self._flush(objects)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/session.py", line 1417, in
_flush
    flush_context.execute()
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 244, in
execute
    UOWExecutor().execute(self, tasks)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 707, in
execute
    self.execute_save_steps(trans, task)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 724, in
execute_save_steps
    self.execute_dependencies(trans, task)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 733, in
execute_dependencies
    self.execute_dependency(trans, dep, False)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 719, in
execute_dependency
    dep.execute(trans, isdelete)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/unitofwork.py", line 686, in
execute
    delete=delete)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/dependency.py", line 353, in
process_dependencies
    self._synchronize(state, child, None, False, uowcommit)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/dependency.py", line 395, in
_synchronize
    sync.clear(state, self.parent, self.prop.synchronize_pairs)
  File "/home/rarch/tg2env/lib/python2.6/site-packages/
SQLAlchemy-0.5.2-py2.6.egg/sqlalchemy/orm/sync.py", line 28, in clear
    raise AssertionError("Dependency rule tried to blank-out primary
key column '%s' on instance '%s'" % (r, mapperutil.state_str(dest)))
AssertionError: Dependency rule tried to blank-out primary key column
'orderdetails.orderid' on instance '<OrderDetail at 0x2cc5850>'










-- 
You received this message because you are subscribed to the Google Groups 
"sqlalchemy" group.
To post to this group, send email to [email protected].
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