[ZODB-Dev] [ZODB4] - Shouldn't the new object be added to Connection._created ?

Ury Marshak um@hottech-israel.com
Mon, 8 Jul 2002 19:23:19 +0200


----- Original Message ----- From: "Jim Fulton" <jim@zope.com>

I'm attaching a small piece of code that demonstrates the problem.
Originally I ran it from two different processes, then tried two threads,
and then combined it into one file. The error is the same. So hte slightly
contrieved example of having two connections is just to simplify an
example


> What works? It can't be referenced from the container any more,
> because the container was ghostified. The new object isn't in the cache,
> so I don't see hos the data could be getting unghostified, or how it could
> be ghostified in the first place. How is the transaction failing?
My code keeps the reference, cause I want to retry the transaction
(incrementing the key in the container).


> because ZEO stores asynchronously, conflicts may be detected later,
however,
> by the time they are detected, the new objects should be
> in the created list.

I put a breakpoint on Connection._invalidate_created , and there I got
self._created = []

In any case I'm not trying to pretend to know what the problem is (it
might be something small and stupid that I'm missing), it's just the
thoughts
that I got spending some time in the debugger, trying to solve this
(rather crucial for me)  problem. If there exists some introductory
document on the workings of persistence/transactions I'd be thankful
for a pointer


>
> When you get a conflict error, do you call get_transaction().abort()?
Tried that, didn't change a thing. Am I supposed to do that on a
ConflictError?

btw, it'a win2k machine (SP2),
python 2.2.1,
ZEO and ZODB4 just pulled from the CVS

code follows:
-------------------------------------
tt.py ---------------------------------
from ZODB import FileStorage, DB
import Persistence
from Persistence.BTrees.IOBTree import IOBTree

from ZODB import FileStorage
from Transaction.Exceptions import ConflictError
from ZEO import ClientStorage

treename = 'aaaa'

class C(Persistence.Persistent): pass

def gen_conflict(db):
    conn = db.open()
    dbroot = conn.root()
    container = dbroot[treename]
    c = C()
    container[1]=c
    get_transaction().commit()

def do_main():
    storage = ClientStorage.ClientStorage(('127.0.0.1',7980))
    #storage = FileStorage.FileStorage('tst.fs')
    db = DB( storage )
    conn = db.open()
    dbroot = conn.root()

    if 1 : #not dbroot.has_key(treename):
        dbroot[treename]=IOBTree()
        get_transaction().commit()

    container = dbroot[treename]

    # make our container out-of-sync
    gen_conflict(db)

    c = C()
    try:
        container[1]=c
        get_transaction().commit()
    except ConflictError:
        print c._p_state   # 3 == ghost?
        # c.something = 1  # if I uncomment this line it dies here
        container[2]=c
        get_transaction().commit()

    db.close()
    storage.close()

if __name__=='__main__':
    do_main()

------------------------------------- just in
case ---------------------------------
-------------------------------------
run_zeo.bat---------------------------------
del aaa.txt
del Data.fs*
set STUPID_LOG_FILE=aaa.txt
C:\Python22\Lib\site-packages\ZEO\start.py -d -p 7980