Thanks for the detailed explanation and the workarounds, works nicely.

2013/1/8 Michael Bayer <mike...@zzzcomputing.com>

> assuming you can try 0.8 which provides inspect(), this will show what is
> happening:
>
> from sqlalchemy import inspect
> print "--------------------"
>
> p.children[2] = c2
> print p.children
> print inspect(c2).attrs.parent.history
> print inspect(c3).attrs.parent.history
> print "--------------------"
>
> p.children[1] = c3
> print p.children
> print inspect(c2).attrs.parent.history
> print inspect(c3).attrs.parent.history
> print "--------------------"
>
>
> we see:
>
> --------------------
> [Mary, John, John]
> History(added=(), unchanged=[Thomas], deleted=())
> History(added=[None], unchanged=(), deleted=[Thomas])
> --------------------
> [Mary, Kenny, John]
> History(added=[None], unchanged=(), deleted=[Thomas])
> History(added=(), unchanged=[Thomas], deleted=())
> --------------------
>
>
> basically, "somecollection[n] = someobject" will also fire a backref
> event.   The object already at somecollection[n] fires a replace event,
> which sends a "remove" to the backref at somecollection[n].
>
> The confusion arises because "p.children[2] = c2" means that c2 is now
> present in the list twice, which is not a condition the collection
> mechanics support.   The assignment back of "c3" leads the system to
> believe that "c2" is being removed from the collection, hence the backref
> sets "c2.parent" to None, yet c2 is in the list twice so it isn't actually
> being removed.   It's the backref event being fired off inappropriately
> that's the core of the issue.   Tracking this count like the ticket states
> would add an expensive id() + dictionary storage for all objects in all
> collections everywhere, for a pretty infrequent use case, hitting us both
> in memory and time spent.   It's a bad situation.   i can see having this
> as perhaps an option on relationship(), track_dupes=True, we'd have to
> recommend it in conjunction with ordering_list.
>
> Some ways to work around include, assigning a slice, so that both items
> are removed first:
>
> p.children[1:2] = [c2, c1]
>
> or just doing the second set event again:
>
> p.children[1], p.children[2] = p.children[2], p.children[1]
> p.children[1] = p.children[1]
>
> I'll add these workarounds to the ticket.
>
>
>
>
> On Jan 7, 2013, at 9:09 PM, Alexey Vihorev wrote:
>
> Tried to replace this with this,  but results are the same****
> ** **
>
> temp1 = p.children[1]****
>
> temp2 = p.children[2]****
>
> ** **
>
> p.children[2] = temp1****
>
> p.children[1] = temp2****
> ** **
> *From:* sqlalchemy@googlegroups.com [mailto:sqlalchemy@googlegroups.com] *On
> Behalf Of *Michael Bayer
> *Sent:* Tuesday, January 08, 2013 2:23 AM
> *To:* sqlalchemy@googlegroups.com
> *Subject:* Re: [sqlalchemy] Strange behaviour while trying to swap
> related records, or am I doing it wrong?****
> ** **
> ** **
> On Jan 7, 2013, at 7:05 PM, Alexey Vihorev wrote:****
>
>  ****
> p.children[1], p.children[2] = p.children[2], p.children[1]****
> *print*(p.children) *#prints [Mary, Kenny, John]*****
>  ****
>
> ** **
> yeah, without looking too deeply I'm fairly certain this is this trac
> ticket:****
> ** **
> http://www.sqlalchemy.org/trac/ticket/1103****
> ** **
> ** **
> basically would add a good chunk of complexity and overhead to the list
> instrumentation.   this is a "blue sky" ticket for that reason.   For now
> you'd need to just assign to an intermediary variable and do one assignment
> at a time.****
> ** **
> ** **
> ** **
> --
> 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.****
>
> --
> 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.
>
>
>  --
> 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.
>



-- 
Алексей Вихорев

-- 
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.

Reply via email to