On Wednesday 10 April 2002 01:56 pm, you wrote:
> If you do not pass a Connection to the methods it will use its own
> transaction.  Otherwise I think assuming the connection you pass to a
> method will be used is a good assumption.

transaction is needed for identity & sequence idgens cause they can only do 
their stuff on the connection where id is being used. For ID broker it is not 
needed at all and the only reason it get's the connection is because it 
implements the same interface. It should NOT use the connection for the 
reasons I explained before.

>
> I have also been getting some bug reports that I was thinking might be
> due to having two transactions in progress within the same thread.  Are
> you pretty certain that this should not be an issue?

I do not see how it could. I am quite sure it is not. You may be confusing it 
with the problem of using same Connection in two threads which is definitely 
a problem since it is not threadsafe

>
> The case that actually made me want to allow the extended transaction
> was a case where the ID_TABLE is having rows added dynamically, if the
> row does not already exist.  In this case the IDBroker internal
> transaction queried for the row, if not found, one would be created
> (within the main transaction).  Then the query would be retried.  Since
> the main transaction was not committed yet, the row still was not
> available.  I guess I can abandon the idea of creating the row within
> the transaction, and if the main transaction fails, the row would still
> exist.  Possibly cleaning up separately (might just have to leave it).

i do not like that idea, but if you implement it please make it strictly 
optional.
It is a config issue and should not be done at runtime. Do you want a Peer to 
create a table if it does not exist? I guess not...

fedor.

>
> But I am still concerned that having multiple transactions open within a
> single thread might lead to problems.
>
> john mcnally
>
> Fedor Karpelevitch wrote:
> > I beleive you are wrong. It was that way for a reason.
> > The reason is that if ID aquisition is performed as a part of (large)
> > transaction it will lock ID_TABLE for the duration of that transaction.
> > So it was perfectly correct for IDBroker to get the IDs in a separate
> > (small) transaction so that ID_TABLE is locked for the minimal time
> > possible. I think this change should be rolled back...
> >
> > your ever-watching fedor.
> >
> > On Tuesday 09 April 2002 08:23 am, you wrote:
> > > jmcnally    02/04/09 08:23:01
> > >
> > >   Modified:    src/java/org/apache/torque/oid IDBroker.java
> > >   Log:
> > >   no longer ignoring the connection passed into the getIdAsXXX methods
> > > as it might be part of a transaction.
> > >
> > >   Revision  Changes    Path
> > >   1.12      +106 -47
> > > jakarta-turbine-torque/src/java/org/apache/torque/oid/IDBroker.java
> > >
> > >   Index: IDBroker.java
> > >   ===================================================================
> > >   RCS file:
> > > /home/cvs/jakarta-turbine-torque/src/java/org/apache/torque/oid/IDBroke
> > >r.ja va,v retrieving revision 1.11
> > >   retrieving revision 1.12
> > >   diff -u -r1.11 -r1.12
> > >   --- IDBroker.java   6 Feb 2002 15:18:56 -0000       1.11
> > >   +++ IDBroker.java   9 Apr 2002 15:23:01 -0000       1.12
> > >   @@ -113,7 +113,7 @@
> > >     *
> > >     * @author <a href="mailto:[EMAIL PROTECTED]";>Frank Y. Kim</a>
> > >     * @author <a href="mailto:[EMAIL PROTECTED]";>John D. McNally</a>
> > >   - * @version $Id: IDBroker.java,v 1.11 2002/02/06 15:18:56 mpoeschl
> > > Exp $ + * @version $Id: IDBroker.java,v 1.12 2002/04/09 15:23:01
> > > jmcnally Exp $ */
> > >    public class IDBroker
> > >        implements Runnable, IdGenerator
> > >   @@ -288,7 +288,7 @@
> > >        public int getIdAsInt(Connection connection, Object tableName)
> > >            throws Exception
> > >        {
> > >   -        return getIdAsBigDecimal(null, tableName).intValue();
> > >   +        return getIdAsBigDecimal(connection, tableName).intValue();
> > >        }
> > >
> > >
> > >   @@ -305,7 +305,7 @@
> > >        public long getIdAsLong(Connection connection, Object tableName)
> > >            throws Exception
> > >        {
> > >   -        return getIdAsBigDecimal(null, tableName).longValue();
> > >   +        return getIdAsBigDecimal(connection, tableName).longValue();
> > >        }
> > >
> > >        /**
> > >   @@ -322,7 +322,7 @@
> > >                                            Object tableName)
> > >            throws Exception
> > >        {
> > >   -        BigDecimal[] id = getNextIds((String)tableName, 1);
> > >   +        BigDecimal[] id = getNextIds((String)tableName, 1,
> > > connection); return id[0];
> > >        }
> > >
> > >   @@ -339,13 +339,12 @@
> > >        public String getIdAsString(Connection connection, Object
> > > tableName) throws Exception
> > >        {
> > >   -        return getIdAsBigDecimal(null, tableName).toString();
> > >   +        return getIdAsBigDecimal(connection, tableName).toString();
> > >        }
> > >
> > >
> > >        /**
> > >   -     * A flag to determine the timing of the id generation
> > >   -     *
> > >   +     * A flag to determine the timing of the id generation     *
> > >         * @return a <code>boolean</code> value
> > >         */
> > >        public boolean isPriorToInsert()
> > >   @@ -386,6 +385,22 @@
> > >                                                    int
> > > numOfIdsToReturn) throws Exception
> > >        {
> > >   +        return getNextIds(tableName, numOfIdsToReturn, null);
> > >   +    }
> > >   +
> > >   +    /**
> > >   +     * This method returns x number of ids for the given table.
> > >   +     *
> > >   +     * @param tableName The name of the table for which we want an
> > > id. +     * @param numOfIdsToReturn The desired number of ids.
> > >   +     * @return A BigDecimal.
> > >   +     * @exception Exception Database error.
> > >   +     */
> > >   +    public synchronized BigDecimal[] getNextIds(String tableName,
> > >   +                                                int
> > > numOfIdsToReturn, +                                               
> > > Connection connection) +        throws Exception
> > >   +    {
> > >            if (tableName == null)
> > >            {
> > >                throw new Exception ("getNextIds(): tableName == null");
> > >   @@ -413,7 +428,7 @@
> > >                {
> > >                    category.info ("Forced id retrieval - " +
> > > availableIds.size()); }
> > >   -            storeIDs(tableName, true);
> > >   +            storeIDs(tableName, true, connection);
> > >                availableIds = (List)ids.get(tableName);
> > >            }
> > >
> > >   @@ -515,7 +530,7 @@
> > >                    category.info("IDBroker thread checking for more
> > > keys on table: " + tableName);
> > >                    List availableIds = (List)ids.get(tableName);
> > >   -                int quantity = getQuantity(tableName).intValue();
> > >   +                int quantity = getQuantity(tableName,
> > > null).intValue(); if ( quantity > availableIds.size() )
> > >                    {
> > >                        try
> > >   @@ -523,7 +538,7 @@
> > >                            // Second parameter is false because we
> > > don't // want the quantity to be adjusted for thread // calls.
> > >   -                        storeIDs(tableName, false);
> > >   +                        storeIDs(tableName, false, null);
> > >                            category.info("Retrieved more ids for table:
> > > " + tableName);
> > >                        }
> > >   @@ -585,7 +600,7 @@
> > >                             tableName);
> > >                    // Increase quantity, so that hopefully this does
> > > not // happen again.
> > >   -                float rate = getQuantity(tableName).floatValue()
> > >   +                float rate = getQuantity(tableName,
> > > null).floatValue() / (float)timeLapse;
> > >                    quantityStore.put(tableName,
> > >                        new
> > > BigDecimal(Math.ceil(sleepPeriod*rate*safetyMargin))); @@ -604,7 +619,8
> > > @@ * @exception Exception, a generic exception.
> > >         */
> > >        private void storeIDs(String tableName,
> > >   -                          boolean adjustQuantity)
> > >   +                          boolean adjustQuantity,
> > >   +                          Connection connection)
> > >            throws Exception
> > >        {
> > >            BigDecimal nextId = null;
> > >   @@ -624,33 +640,29 @@
> > >                DBConnection dbCon = null;
> > >                try
> > >                {
> > >   -                String databaseName = dbMap.getName();
> > >   -
> > >   -                // Get a connection to the db by starting a
> > >   -                // transaction.
> > >   -                if (transactionsSupported)
> > >   +                if (connection == null)
> > >                    {
> > >   -                    dbCon = BasePeer.beginTransaction(databaseName);
> > >   -                }
> > >   -                else
> > >   -                {
> > >   -                    dbCon = Torque.getConnection(databaseName);
> > >   +                    String databaseName = dbMap.getName();
> > >   +                    // Get a connection to the db by starting a
> > >   +                    // transaction.
> > >   +                    if (transactionsSupported)
> > >   +                    {
> > >   +                        dbCon =
> > > BasePeer.beginTransaction(databaseName); +                    }
> > >   +                    else
> > >   +                    {
> > >   +                        dbCon = Torque.getConnection(databaseName);
> > >   +                    }
> > >   +                    connection = dbCon.getConnection();
> > >                    }
> > >   -                Connection connection = dbCon.getConnection();
> > >   -
> > >   +
> > >                    // Write the current value of quantity of keys to
> > > grab // to the database, primarily to obtain a write lock // on the
> > > table/row, but this value will also be used // as the starting value
> > > when an IDBroker is // instantiated.
> > >   -                quantity = getQuantity(tableName);
> > >   -                Criteria criteria = new Criteria(2)
> > >   -                    .add( QUANTITY, quantity );
> > >   -                Criteria selectCriteria = new Criteria(2)
> > >   -                    .add( TABLE_NAME, tableName );
> > >   -                criteria.setDbName(dbMap.getName());
> > >   -                selectCriteria.setDbName(dbMap.getName());
> > >   -                BasePeer.doUpdate( selectCriteria, criteria, dbCon
> > > ); +                quantity = getQuantity(tableName, connection); +   
> > >             updateQuantity(connection, tableName, quantity);
> > >
> > >                    // Read the next starting ID from the ID_TABLE.
> > >                    BigDecimal[] results = selectRow(connection,
> > > tableName); @@ -659,16 +671,16 @@
> > >                    // Update the row based on the quantity in the
> > >                    // ID_TABLE.
> > >                    BigDecimal newNextId = nextId.add(quantity);
> > >   -                updateRow(connection, tableName,
> > > newNextId.toString() ); +                updateNextId(connection,
> > > tableName, newNextId.toString() );
> > >
> > >   -                if (transactionsSupported)
> > >   +                if (transactionsSupported && dbCon != null)
> > >                    {
> > >                        BasePeer.commitTransaction(dbCon);
> > >                    }
> > >                }
> > >                catch (Exception e)
> > >                {
> > >   -                if (transactionsSupported)
> > >   +                if (transactionsSupported && dbCon != null)
> > >                    {
> > >                        BasePeer.rollBackTransaction(dbCon);
> > >                    }
> > >   @@ -676,7 +688,7 @@
> > >                }
> > >                finally
> > >                {
> > >   -                if (!transactionsSupported)
> > >   +                if (!transactionsSupported && dbCon != null)
> > >                    {
> > >                        // Return the connection to the pool.
> > >                        Torque.releaseConnection(dbCon);
> > >   @@ -713,7 +725,7 @@
> > >         * @param tableName The name of the table we want to query.
> > >         * @return An int with the number of ids cached in memory.
> > >         */
> > >   -    private BigDecimal getQuantity(String tableName)
> > >   +    private BigDecimal getQuantity(String tableName, Connection
> > > connection) {
> > >            BigDecimal quantity = null;
> > >
> > >   @@ -732,11 +744,13 @@
> > >                DBConnection dbCon = null;
> > >                try
> > >                {
> > >   -                String databaseName =
> > > tableMap.getDatabaseMap().getName(); -
> > >   -                // Get a connection to the db
> > >   -                dbCon = Torque.getConnection(databaseName);
> > >   -                Connection connection = dbCon.getConnection();
> > >   +                if (connection == null)
> > >   +                {
> > >   +                    String databaseName =
> > > tableMap.getDatabaseMap().getName(); +                    // Get a
> > > connection to the db
> > >   +                    dbCon = Torque.getConnection(databaseName);
> > >   +                    connection = dbCon.getConnection();
> > >   +                }
> > >
> > >                    // Read the row from the ID_TABLE.
> > >                    BigDecimal[] results = selectRow(connection,
> > > tableName); @@ -754,7 +768,10 @@
> > >                    // Return the connection to the pool.
> > >                    try
> > >                    {
> > >   -                    Torque.releaseConnection(dbCon);
> > >   +                    if (dbCon != null)
> > >   +                    {
> > >   +                        Torque.releaseConnection(dbCon);
> > >   +                    }
> > >                    }
> > >                    catch (Exception e)
> > >                    {
> > >   @@ -824,9 +841,9 @@
> > >         * @param id An int with the value to set for the id.
> > >         * @exception Exception Database error.
> > >         */
> > >   -    private void updateRow(Connection con,
> > >   -                           String tableName,
> > >   -                           String id)
> > >   +    private void updateNextId(Connection con,
> > >   +                              String tableName,
> > >   +                              String id)
> > >            throws Exception
> > >        {
> > >
> > >   @@ -842,7 +859,49 @@
> > >
> > >            Statement statement = null;
> > >
> > >   -        category.debug("updateRow: " + stmt.toString());
> > >   +        category.debug("updateNextId: " + stmt.toString());
> > >   +
> > >   +        try
> > >   +        {
> > >   +            statement = con.createStatement();
> > >   +            statement.executeUpdate( stmt.toString() );
> > >   +        }
> > >   +        finally
> > >   +        {
> > >   +            if (statement != null) statement.close();
> > >   +        }
> > >   +    }
> > >   +
> > >   +
> > >   +    /**
> > >   +     * Helper method to update a row in the ID_TABLE.
> > >   +     *
> > >   +     * @param con A Connection.
> > >   +     * @param tableName The properly escaped name of the table to
> > > identify the +     * row.
> > >   +     * @param id An int with the value to set for the id.
> > >   +     * @exception Exception Database error.
> > >   +     */
> > >   +    private void updateQuantity(Connection con,
> > >   +                                String tableName,
> > >   +                                BigDecimal quantity)
> > >   +        throws Exception
> > >   +    {
> > >   +
> > >   +
> > >   +        StringBuffer stmt =
> > >   +            new StringBuffer(quantity.toString().length() +
> > > tableName.length() +                             + 50);
> > >   +            stmt.append( "UPDATE " + ID_TABLE )
> > >   +            .append( " SET QUANTITY = " )
> > >   +            .append( quantity )
> > >   +            .append( " WHERE TABLE_NAME = '" )
> > >   +            .append( tableName )
> > >   +            .append( '\'' );
> > >   +
> > >   +        Statement statement = null;
> > >   +
> > >   +        category.debug("updateQuantity: " + stmt.toString());
> > >
> > >            try
> > >            {
> >
> > --
> > To unsubscribe, e-mail:  
> > <mailto:[EMAIL PROTECTED]> For additional
> > commands, e-mail: <mailto:[EMAIL PROTECTED]>

--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to