Re: Problem: InsertQuery order changes during batch insert

From: Andrus Adamchik (andru..bjectstyle.org)
Date: Wed Nov 23 2005 - 06:33:19 EST

  • Next message: Andrus Adamchik: "Re: Which version? 1.2 or 1.13"

    Ingo,

    Let me explain how ordering of inserts/updates/deletes works. There
    is no correlation between the order of initial insertion of objects
    into the DataContext and the order in which statements appear in the
    SQL. Ordering is inferred by Cayenne during commit using graph
    sorting algorithms based on Ashwood library.

    This means that in most cases you don't have to think about ordering
    (or deferred constraints), and Cayenne will do the right thing.
    However there is one limitation - this algorithm can't handle cyclic
    dependencies. And this is exactly the case that you have.

    What are your options:

    1. Perform an operation in two commits - first create your objects
    and setup all relationships except for the one that is giving you
    trouble; then do a commit; then establish remaining relationship and
    commit again. Simple, but not so clean if you want the whole thing to
    be atomic. This solution worked for me before with simpler dependency
    cycles.

    2. Subclass org.objectstyle.cayenne.map.AshwoodEntitySorter,
    overriding "sortDbEntities" to provide your own order when these two
    entities are involved. Then configure DataNode to use your sorter -
    DataNode.setEntitySorter(..)

    Andrus

    On Nov 23, 2005, at 1:13 PM, Ingo Feulner wrote:
    > Hello together,
    >
    > we have the following problem here:
    >
    > We have two entities, PRODUCTS and PRODUCT_STATES.
    >
    > PRODUCTS has two relationships to PRODUCT_STATES: a to-one
    > "currentState"
    > and a to-many "historicalStates".
    > PRODUCT_STATES itself has a to-one relationship to PRODUCTS.
    >
    > There are foreign-key constraints on both entities, but the one from
    > PRODUCTS to PRODUCTS_STATES is deferred (we are using Oracle here).
    >
    > That means, as long as a row is inserted into PRODUCTS before the
    > corresponding row is inserted into PRODUCT_STATES in one
    > transaction all
    > is going well.
    >
    > Now the problem: If we run a bigger batch of insertions into these two
    > entities, there is always a point where the insertion order
    > changes, i.e.
    > PRODUCT_STATES is inserted before PRODUCTS, and that of course
    > produces a
    > constraint error by Oracle. (see log excerpt below)
    >
    > My question is now: Why does the order of inserts change and what
    > influences it? How can we influence the order easily?
    > It currently does not give me a good feeling, that it changes more
    > or less
    > randomly....
    >
    > Please give me a hint.. maybe there is a setting in the model
    > that's missing.
    >
    > best regards, Ingo.
    >
    >
    >
    > Here is an log excerpt:
    >
    > GOOD case:
    >
    > 22 Nov 2005 15:46:20,840 [Thread-6] INFO - --- transaction started.
    > 22 Nov 2005 15:46:20,840 [Thread-6] INFO - --- will run 20 queries.
    > 22 Nov 2005 15:46:20,840 [Thread-6] INFO - INSERT INTO
    > ENTW.PARTNER (....)
    > 22 Nov 2005 15:46:20,840 [Thread-6] DEBUG - batch count: -2
    > 22 Nov 2005 15:46:20,840 [Thread-6] INFO - === updated 1 row.
    > 22 Nov 2005 15:46:20,840 [Thread-6] INFO - INSERT INTO
    > ENTW.ADDRESSES (....)
    > 22 Nov 2005 15:46:20,856 [Thread-6] DEBUG - batch count: -2
    > 22 Nov 2005 15:46:20,856 [Thread-6] INFO - === updated 1 row.
    > 22 Nov 2005 15:46:20,856 [Thread-6] INFO - INSERT INTO
    > ENTW.PRODUCTS (...)
    > 22 Nov 2005 15:46:20,856 [Thread-6] DEBUG - batch count: -2
    > 22 Nov 2005 15:46:20,856 [Thread-6] INFO - === updated 1 row.
    > 22 Nov 2005 15:46:20,856 [Thread-6] INFO - INSERT INTO
    > ENTW.PRODUCT_STATES ( ....)
    > 22 Nov 2005 15:46:20,856 [Thread-6] INFO - === updated 1 row.
    >
    >
    > ERROR case (same code, same run, just a few entries later)
    >
    > 22 Nov 2005 15:46:20,950 [Thread-6] INFO - --- will run 20 queries.
    > 22 Nov 2005 15:46:20,950 [Thread-6] INFO - INSERT INTO
    > ENTW.PARTNER (...)
    > 22 Nov 2005 15:46:20,950 [Thread-6] DEBUG - batch count: -2
    > 22 Nov 2005 15:46:20,950 [Thread-6] INFO - === updated 1 row.
    > 22 Nov 2005 15:46:20,950 [Thread-6] INFO - INSERT INTO
    > ENTW.ADDRESSES (...)
    > 22 Nov 2005 15:46:20,950 [Thread-6] DEBUG - batch count: -2
    > 22 Nov 2005 15:46:20,965 [Thread-6] INFO - === updated 1 row.
    > 22 Nov 2005 15:46:20,965 [Thread-6] INFO - INSERT INTO
    > ENTW.PRODUCT_STATES(...)
    > 22 Nov 2005 15:46:20,997 [Thread-6] INFO - *** error.
    > java.sql.SQLException: ORA-02291: integrity constraint
    > (ENTW.PRST_PROD_FK)
    > violated - parent key not found
    >
    >



    This archive was generated by hypermail 2.0.0 : Wed Nov 23 2005 - 06:33:21 EST