You are viewing a plain text version of this content. The canonical link for it is here.
Posted to ojb-dev@db.apache.org by ar...@apache.org on 2006/07/15 16:20:27 UTC

svn commit: r422231 [2/4] - in /db/ojb/trunk/src/java/org/apache/ojb/broker: ./ accesslayer/ accesslayer/sql/ cache/ core/ locking/ metadata/ metadata/fieldaccess/

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/core/PersistenceBrokerImpl.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/core/PersistenceBrokerImpl.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/core/PersistenceBrokerImpl.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/core/PersistenceBrokerImpl.java Sat Jul 15 07:20:25 2006
@@ -1,6 +1,6 @@
 package org.apache.ojb.broker.core;
 
-/* Copyright 2003-2004 The Apache Software Foundation
+/* Copyright 2003-2006 The Apache Software Foundation
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -16,7 +16,6 @@
  */
 
 import java.lang.reflect.Constructor;
-import java.lang.reflect.Field;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.Collection;
@@ -29,6 +28,8 @@
 
 import org.apache.commons.collections.ListUtils;
 import org.apache.commons.lang.ObjectUtils;
+import org.apache.commons.lang.SystemUtils;
+import org.apache.commons.lang.exception.ExceptionUtils;
 import org.apache.ojb.broker.Identity;
 import org.apache.ojb.broker.IdentityFactory;
 import org.apache.ojb.broker.ManageableCollection;
@@ -41,6 +42,8 @@
 import org.apache.ojb.broker.TransactionAbortedException;
 import org.apache.ojb.broker.TransactionInProgressException;
 import org.apache.ojb.broker.TransactionNotInProgressException;
+import org.apache.ojb.broker.TransientObjectException;
+import org.apache.ojb.broker.lob.LobHelper;
 import org.apache.ojb.broker.accesslayer.ChainingIterator;
 import org.apache.ojb.broker.accesslayer.CollectionCreationContext;
 import org.apache.ojb.broker.accesslayer.ConnectionManagerIF;
@@ -107,6 +110,15 @@
 {
     private Logger logger = LoggerFactory.getLogger(PersistenceBrokerImpl.class);
 
+    /**
+     * A stack trace of this broker user.
+     * Used when broker leak detection is enabled.
+     */
+    protected String brokerStackTrace;
+    /**
+     * Returns <em>true</em> if broker leak detection is enabled.
+     */
+    protected boolean brokerLeakDetection;
     protected PersistenceConfiguration persistenceConfiguration;
     protected BrokerHelper brokerHelper;
     protected MtoNBroker mtoNBroker;
@@ -151,6 +163,8 @@
     private SqlGenerator sqlGenerator;
     private IdentityFactory identityFactory;
     private RelationshipPrefetcherFactory relationshipPrefetcherFactory;
+    private LobHelper lobHelper;
+    private PBKey pbKey;
 
     /**
      * List of objects being stored now, allows to avoid infinite
@@ -162,12 +176,12 @@
     with user implemented equals/hashCode methods of persistence capable objects
     (e.g. objects are equals but PK fields not)
     */
-    private List nowStoring = new IdentityArrayList();
+    private IdentityArrayList nowStoring = new IdentityArrayList();
 
     /**
      * Lists for object registration during delete operations.
      * We reuse these list to avoid excessive object creation.
-     * @see #clearRegistrationLists
+     * @see #refreshRegistrationLists
      */
     /*
     arminw: list was cleared before delete method end. Internal we only
@@ -177,7 +191,13 @@
     with user implemented equals/hashCode methods of persistence capable objects
     (e.g. objects are equals but PK fields not)
     */
-    private List markedForDelete = new IdentityArrayList();
+    private IdentityArrayList markedForDelete = new IdentityArrayList();
+
+    /**
+     * Used for performance optimization of method
+     * {@link #refreshRelationships(Object, org.apache.ojb.broker.Identity, org.apache.ojb.broker.metadata.ClassDescriptor)}
+     */
+    private IdentityArrayList skipRefreshRelationship = new IdentityArrayList();
 
     /**
      * The set of identities of all deleted objects during current transaction
@@ -254,6 +274,12 @@
         proxyFactory      = (ProxyFactory)subContainer.getSingletonInstance(ProxyFactory.class);
         queryFactory      = (QueryFactoryNew)subContainer.getSingletonInstance(QueryFactoryNew.class);
         relationshipPrefetcherFactory = new RelationshipPrefetcherFactory(this);
+        lobHelper   = (LobHelper)subContainer.getSingletonInstance(LobHelper.class);
+    }
+
+    public LobHelper serviceLobHelper()
+    {
+        return lobHelper;
     }
 
     public BatchManager serviceBatchManager()
@@ -324,7 +350,17 @@
     {
         return proxyFactory;
     }
-    
+
+    public boolean isBrokerLeakDetection()
+    {
+        return brokerLeakDetection;
+    }
+
+    public void setBrokerLeakDetection(boolean brokerLeakDetection)
+    {
+        this.brokerLeakDetection = brokerLeakDetection;
+    }
+
     public boolean isClosed()
     {
         return this.isClosed;
@@ -332,11 +368,19 @@
 
     public void setClosed(boolean closed)
     {
+        // When lookup the PB instance from pool method setClosed(false)
+        // was called before returning instance from pool, in this case
+        // OJB have to refresh the instance.
         if (!closed)
         {
             refresh();
+            if(brokerLeakDetection)
+            {
+                brokerStackTrace = ExceptionUtils.getFullStackTrace(
+                        new Exception("PersistenceBroker caller stack"));
+            }
         }
-        isClosed = closed;
+        this.isClosed = closed;
     }
 
     /**
@@ -360,7 +404,7 @@
 
     /**
      * Returns the maximum number of sql columns.
-     * 
+     *
      * @return The sql limit
      */
     public int getSqlInLimit()
@@ -394,7 +438,7 @@
      */
     public void destroy()
     {
-        logger.info("Destroy and cleanup this PB instance. " + this);
+        if(logger.isEnabledFor(Logger.INFO)) logger.info("Destroy and cleanup this PB instance. " + this);
         removeAllListeners();
         if (connectionManager != null)
         {
@@ -435,8 +479,8 @@
 
     /**
      * Creates a proxy instance.
-     * 
-     * @param baseClassForProxy  The base class that the Proxy should extend. For dynamic Proxies, the method of 
+     *
+     * @param baseClassForProxy  The base class that the Proxy should extend. For dynamic Proxies, the method of
      * 							 generation is dependent on the ProxyFactory implementation.
      * @param realSubjectsIdentity The identity of the subject
      * @return An instance of the proxy subclass
@@ -456,11 +500,11 @@
                 return constructor.newInstance(new Object[]{ handler });
             }
             else
-            {                
+            {
                 return getProxyFactory().createProxy(baseClassForProxy,handler);
             }
 
-            
+
         }
         catch (Exception ex)
         {
@@ -489,7 +533,7 @@
         try
         {
             fireBrokerEvent(BEFORE_CLOSE_EVENT);
-            clearRegistrationLists();
+            refreshRegistrationLists();
             referencesBroker.removePrefetchingListeners();
             if (connectionManager != null)
             {
@@ -509,6 +553,7 @@
         }
         finally
         {
+            if(skipRefreshRelationship.size() > 0) skipRefreshRelationship.clear();
             // reset flag indicating use in managed environment
             setManaged(false);
             serviceSessionCache().evictAll(SessionCache.LEVEL_SESSION);
@@ -530,7 +575,7 @@
         {
             fireBrokerEvent(BEFORE_ROLLBACK_EVENT);
             setInTransaction(false);
-            clearRegistrationLists();
+            refreshRegistrationLists();
             referencesBroker.removePrefetchingListeners();
             /*
             arminw:
@@ -579,7 +624,7 @@
         }
         fireBrokerEvent(BEFORE_COMMIT_EVENT);
         setInTransaction(false);
-        clearRegistrationLists();
+        refreshRegistrationLists();
         referencesBroker.removePrefetchingListeners();
         /*
         arminw:
@@ -654,15 +699,15 @@
         // only delete if object is not null
         if (obj != null)
         {
+            // replace specified object with the real one
             obj = getProxyFactory().getRealObject(obj);
-            /**
-             * MBAIRD
-             * 1. if we are marked for delete already, avoid recursing on this object
-             *
-             * arminw:
-             * use object instead Identity object in markedForDelete List,
-             * because using objects we get a better performance. I can't find
-             * side-effects in doing so.
+
+            /*
+            MBAIRD
+            1. if we are marked for delete already, avoid recursing on this object
+            arminw:
+            use object identity based list, because using objects we get a
+            better performance. I can't find side-effects in doing so.
              */
             if (markedForDelete.contains(obj))
             {
@@ -670,10 +715,14 @@
             }
 
             ClassDescriptor cld = getClassDescriptor(obj.getClass());
+            Identity oid = serviceIdentity().buildIdentity(cld, obj);
+
             //BRJ: check for valid pk
-            if (!serviceBrokerHelper().assertValidPkForDelete(cld, obj))
+            //if (!serviceBrokerHelper().assertValidPkForDelete(cld, obj))
+            // TODO: arminw: this simple check should do the same - verify
+            if (oid.isTransient())
             {
-                String msg = "Cannot delete object without valid PKs. " + obj;
+                String msg = "Cannot delete object without valid PKs: " + obj;
                 logger.error(msg);
                 return;
             }
@@ -683,40 +732,14 @@
              * 2. register object in markedForDelete map.
              */
             markedForDelete.add(obj);
-            Identity oid = serviceIdentity().buildIdentity(cld, obj);
 
             // Invoke events on PersistenceBrokerAware instances and listeners
             BEFORE_DELETE_EVENT.setTarget(obj);
             fireBrokerEvent(BEFORE_DELETE_EVENT);
             BEFORE_DELETE_EVENT.setTarget(null);
 
-            // 1. delete dependend collections
-            if (!ignoreReferences  && cld.getCollectionDescriptors().size() > 0)
-            {
-                deleteCollections(obj, cld.getCollectionDescriptors());
-            }
-            // 2. delete object from directly mapped table
-            try
-            {
-                dbAccess.executeDelete(cld, obj); // use obj not oid to delete, BRJ
-            }
-            catch(OptimisticLockException e)
-            {
-                // ensure that the outdated object be removed from cache
-                sessionCache.evict(oid, SessionCache.LEVEL_DEEP);
-                throw e;
-            }
-
-            // 3. Add OID to the set of deleted objects
-            deletedDuringTransaction.add(oid);
-
-            // 4. delete dependend upon objects last to avoid FK violations
-            if (cld.getObjectReferenceDescriptors().size() > 0)
-            {
-                deleteReferences(obj, cld.getObjectReferenceDescriptors(), ignoreReferences);
-            }
-            // remove obj from the object cache:
-            sessionCache.evict(oid, SessionCache.LEVEL_DEEP);
+            // now perform deletion
+            performDeletion(cld, obj, oid, ignoreReferences);
 
             // Invoke events on PersistenceBrokerAware instances and listeners
             AFTER_DELETE_EVENT.setTarget(obj);
@@ -726,6 +749,41 @@
     }
 
     /**
+     * This method perform the delete of the specified object
+     * based on the {@link org.apache.ojb.broker.metadata.ClassDescriptor}.
+     */
+    private void performDeletion(final ClassDescriptor cld, final Object obj, final Identity oid, final boolean ignoreReferences) throws PersistenceBrokerException
+    {
+        // 1. delete dependend collections
+        if (!ignoreReferences  && cld.getCollectionDescriptors().size() > 0)
+        {
+            deleteCollections(obj, cld.getCollectionDescriptors());
+        }
+        // 2. delete object from directly mapped table
+        try
+        {
+            dbAccess.executeDelete(cld, obj); // use obj not oid to delete, BRJ
+        }
+        catch(OptimisticLockException e)
+        {
+            // ensure that the outdated object be removed from cache
+            sessionCache.evict(oid, SessionCache.LEVEL_DEEP);
+            throw e;
+        }
+
+        // 3. Add OID to the set of deleted objects
+        deletedDuringTransaction.add(oid);
+
+        // 4. delete dependend upon objects last to avoid FK violations
+        if (cld.getObjectReferenceDescriptors().size() > 0)
+        {
+            deleteReferences(cld, obj, oid, ignoreReferences);
+        }
+        // remove obj from the object cache:
+        sessionCache.evict(oid, SessionCache.LEVEL_DEEP);
+    }
+
+    /**
      * Extent aware Delete by Query
      * @param query
      * @param cld
@@ -749,29 +807,40 @@
             if (query instanceof QueryByIdentity)
             {
                 Identity oid = getIdentity((QueryByIdentity) query);
-                query = referencesBroker.getPKQuery(oid);
-            }
-
-            if (cld.isMappedToTable())
-            {
-                dbAccess.executeDelete(query, cld);
+                try
+                {
+                    query = referencesBroker.getPKQuery(oid);
+                }
+                catch(TransientObjectException e)
+                {
+                    query = null;
+                    logger.error("Can't delete transient objects from datastore", e);
+                }
             }
 
-            // if class is an extent, we have to delete all extent classes too
-            String lastUsedTable = cld.getFullTableName();
-            if (cld.isExtent())
+            if(query != null)
             {
-                Iterator extents = getDescriptorRepository().getAllConcreteSubclassDescriptors(cld).iterator();
+                if (cld.isMappedToTable())
+                {
+                    dbAccess.executeDelete(query, cld);
+                }
 
-                while (extents.hasNext())
+                // if class is an extent, we have to delete all extent classes too
+                String lastUsedTable = cld.getFullTableName();
+                if (cld.isExtent())
                 {
-                    ClassDescriptor extCld = (ClassDescriptor) extents.next();
+                    Iterator extents = getDescriptorRepository().getAllConcreteSubclassDescriptors(cld).iterator();
 
-                    // read same table only once
-                    if (!extCld.getFullTableName().equals(lastUsedTable))
+                    while (extents.hasNext())
                     {
-                        lastUsedTable = extCld.getFullTableName();
-                        dbAccess.executeDelete(query, extCld);
+                        ClassDescriptor extCld = (ClassDescriptor) extents.next();
+
+                        // read same table only once
+                        if (!extCld.getFullTableName().equals(lastUsedTable))
+                        {
+                            lastUsedTable = extCld.getFullTableName();
+                            this.dbAccess.executeDelete(query, extCld);
+                        }
                     }
                 }
             }
@@ -793,29 +862,44 @@
      * will be deleted if auto-delete is true <b>AND</b>
      * the member field containing the object reference is NOT null.
      *
+     * @param cld The {@link org.apache.ojb.broker.metadata.ClassDescriptor} of the object
+     * or of a super class.
      * @param obj Object which we will delete references for
-     * @param listRds list of ObjectRederenceDescriptors
+     * @param oid The {@link Identity} of the object.
      * @param ignoreReferences With this flag the automatic deletion/unlinking
      * of references can be suppressed (independent of the used auto-delete setting in metadata),
      * except {@link org.apache.ojb.broker.metadata.SuperReferenceDescriptor}
      * these kind of reference (descriptor) will always be performed.
      * @throws PersistenceBrokerException if some goes wrong - please see the error message for details
      */
-    private void deleteReferences(Object obj, List listRds, boolean ignoreReferences) throws PersistenceBrokerException
+    private void deleteReferences(ClassDescriptor cld, Object obj, Identity oid, boolean ignoreReferences) throws PersistenceBrokerException
     {
+        List listRds = cld.getObjectReferenceDescriptors();
         // get all members of obj that are references and delete them
         for (Iterator i = listRds.iterator(); i.hasNext();)
         {
             ObjectReferenceDescriptor rds = (ObjectReferenceDescriptor)i.next();
-
-            if ((!ignoreReferences && (rds.getCascadingDelete() == ObjectReferenceDescriptor.CASCADE_OBJECT))
+            if ((!ignoreReferences && rds.getCascadingDelete() == ObjectReferenceDescriptor.CASCADE_OBJECT)
                     || rds.isSuperReferenceDescriptor())
             {
                 Object referencedObject = rds.getPersistentField().get(obj);
-
                 if (referencedObject != null)
                 {
-                    doDelete(referencedObject, ignoreReferences);
+                    if(rds.isSuperReferenceDescriptor())
+                    {
+                        ClassDescriptor base = cld.getSuperClassDescriptor();
+                        /*
+                        arminw: If "table-per-subclass" inheritance is used we have to
+                        guarantee that all super-class table entries are deleted too.
+                        Thus we have to perform the recursive deletion of all super-class
+                        table entries.
+                        */
+                        performDeletion(base, referencedObject, oid, ignoreReferences);
+                    }
+                    else
+                    {
+                        doDelete(referencedObject, ignoreReferences);
+                    }
                 }
             }
         }
@@ -878,12 +962,14 @@
         if(obj == null) return;
 
         ClassDescriptor cld = getClassDescriptor(obj.getClass());
+        Identity oid = serviceIdentity().buildIdentity(cld, obj);
         /*
         if one of the PK fields was null, we assume the objects
         was new and needs insert
         */
-        boolean insert = serviceBrokerHelper().hasNullPKField(cld, obj);
-        Identity oid = serviceIdentity().buildIdentity(cld, obj);
+        // boolean insert = serviceBrokerHelper().hasNullPKField(cld, obj);
+        // TODO: arminw: this should do the same - verify
+        boolean insert = oid.isTransient();
         /*
         if PK values are set, lookup cache or db to see whether object
         needs insert or update
@@ -1039,7 +1125,7 @@
     {
         // get all members of obj that are references and store them
         Collection listRds = cld.getObjectReferenceDescriptors();
-
+        // skip if nothing to do
         if ((listRds != null) && (listRds.size() > 0))
         {
             for (Iterator i = listRds.iterator(); i.hasNext();)
@@ -1047,7 +1133,7 @@
                 ObjectReferenceDescriptor rds = (ObjectReferenceDescriptor) i.next();
                 /*
                 arminw: the special references (eg. super-references used for table per subclass
-                inheritance) must be performed in any case. The "normal" 1:1 references can be 
+                inheritance) must be performed in any case. The "normal" 1:1 references can be
                 ignored when flag "ignoreReferences" is set
                 */
                 if((!ignoreReferences && rds.getCascadingStore() != ObjectReferenceDescriptor.CASCADE_NONE)
@@ -1096,15 +1182,15 @@
                 Object obj = iter.next();
                 ClassDescriptor cld = getClassDescriptor(obj.getClass());
                 if (serviceBrokerHelper().assertValidPkForDelete(cld, obj))
-                {    
+                {
                     delete(obj);
-                }    
+                }
             }
             tc.clearDeletedObjects();
             tc.clearNewObjects();
         }
     }
-    
+
     /**
      * Store/Link collections of objects poiting to <b>obj</b>.
      * More info please see comments in source.
@@ -1142,7 +1228,7 @@
                 if (referencedObjects instanceof TrackingCollection)
                 {
                     afterStore((TrackingCollection) referencedObjects, cod);
-                }                
+                }
             }
         }
     }
@@ -1250,8 +1336,17 @@
             while(it.hasNext())
             {
                 refObj = it.next();
-                // set FK in refObj if it is materialized
-                if(getProxyFactory().isMaterialized(refObj))
+                /*
+                TODO: Check this!
+                arminw:
+                When it's necessary to 'link' (set the FK) the 1:n reference objects?
+                1. set FK in refObj if it is materialized
+                2. if the referenced object is a proxy AND the main object needs insert
+                we have to materialize the real object, because the user may move a collection
+                of proxy objects from object A to new object B. In this case we have to replace the
+                FK in the proxy object with new key of object B.
+                */
+                if(insert || getProxyFactory().isMaterialized(refObj))
                 {
                     ClassDescriptor refCld = getClassDescriptor(getProxyFactory().getRealClass(refObj));
                     // get the real object before linking
@@ -1464,7 +1559,7 @@
 
     /**
      * Creates the hierarchy of enclosing objects between the target class and the given persistent outer class
-     * 
+     *
      * @param targetClass                 The target inner class (is not instantiated)
      * @param directPersistentOuterClass  The nearest persistent enclosing class
      * @param directPersistentOuterObject The instance of the nearest persistent enclosing class to use
@@ -1486,7 +1581,7 @@
             {
                 // recursively create the direct enclosing object of the direct enclosing class
                 Object oneLevelAboveOuterObj = createDirectEnclosingObject(directEnclosingClass, directPersistentOuterClass, directPersistentOuterObject);
-    
+
                 try
                 {
                     return  ClassHelper.newInstance(directEnclosingClass,
@@ -1527,13 +1622,14 @@
     /**
      * Retrieve all References (also Collection-attributes) of a given instance.
      * Loading is forced, even if the collection- and reference-descriptors differ.
-     * @param pInstance the persistent instance to work with
+     * @param obj the persistent instance to work with
+     * @param force Force the loading of references
      */
     private void retrieveAllReferences(Object obj, boolean force) throws PersistenceBrokerException
     {
         if (logger.isDebugEnabled())
         {
-            logger.debug("Manually retrieving all references for object " + serviceIdentity().buildIdentity(obj));
+        	logger.debug("Manually retrieving all references for object " + serviceIdentity().buildIdentity(obj));
         }
         ClassDescriptor cld = getClassDescriptor(obj.getClass());
         try
@@ -1620,8 +1716,7 @@
 
     public void refreshRelationships(Object obj, ClassDescriptor cld)
     {
-        Identity oid = serviceIdentity().buildIdentity(cld, obj);
-        refreshRelationships(obj, oid, cld);
+        refreshRelationships(obj, serviceIdentity().buildIdentity(obj), cld);
     }
 
     /**
@@ -1635,6 +1730,8 @@
      */
     public void refreshRelationships(Object obj, Identity oid, ClassDescriptor cld)
     {
+        if(skipRefreshRelationship.contains(cld)) return;
+
         Iterator iter;
         CollectionDescriptor cds;
         ObjectReferenceDescriptor rds;
@@ -1651,6 +1748,7 @@
         }
         try
         {
+            boolean needsRelationshipRefresh = false;
             serviceSessionCache().enableMaterializationCache();
             if(tmp == null)
             {
@@ -1664,6 +1762,7 @@
                 if (cds.isRefresh())
                 {
                     referencesBroker.retrieveCollection(obj, cld, cds, false);
+                    needsRelationshipRefresh = true;
                 }
             }
             iter = cld.getObjectReferenceDescriptors().iterator();
@@ -1673,9 +1772,14 @@
                 if (rds.isRefresh())
                 {
                     referencesBroker.retrieveReference(obj, cld, rds, false);
+                    needsRelationshipRefresh = true;
                 }
             }
             serviceSessionCache().disableMaterializationCache();
+            if(!needsRelationshipRefresh)
+            {
+                skipRefreshRelationship.add(cld);
+            }
         }
         catch(RuntimeException e)
         {
@@ -1705,7 +1809,7 @@
 
     /**
      * Retrieves the collection described by the given creation context.
-     * 
+     *
      * @param context The creation context
      * @return The collection
      */
@@ -1753,8 +1857,8 @@
         }
         return newObj;
     }
-    
-    
+
+
     /**
      * Retrieve an full materialized (dependent on the metadata settings)
      * object by it's identity from the database, as well as caching the
@@ -1776,7 +1880,7 @@
         }
 
         ClassDescriptor cld = getClassDescriptor(c);
-        Object newObj = getPlainDBObject(cld,oid);        
+        Object newObj = getPlainDBObject(cld,oid);
 
         // loading references is useful only when the Object could be found in db:
         if (newObj != null)
@@ -1838,7 +1942,7 @@
             }
         }
     }
-    
+
     /**
      * returns an Iterator that iterates Objects of class c if calling the .next()
      * method. The Elements returned come from a SELECT ... WHERE Statement
@@ -1867,7 +1971,6 @@
         {
             result = new PagingIterator(result, query.getStartAtIndex(), query.getEndAtIndex());
         }
-
         return result;
     }
 
@@ -1928,6 +2031,11 @@
             {
                 refreshInstance(obj, id, cld);
             }
+            else
+            {
+                // refresh LOB-fields
+                serviceLobHelper().internalAutoRefresh(obj, cld);
+            }
             // now refresh all references
             refreshRelationships(obj, id, cld);
         }
@@ -1977,7 +2085,19 @@
         if (query instanceof QueryByIdentity)
         {
             Identity oid = getIdentity((QueryByIdentity) query);
-            result = getObjectByIdentity(oid);
+            // only non-transient objects can be found in DB
+            if(oid.isTransient())
+            {
+                if(logger.isEnabledFor(Logger.INFO)) logger.info(
+                        "The object to query was detected as transient, will only lookup the cache for object instance. Identity="
+                        + oid + ", the query object was " + query);
+                // transient objects can only be found in session cache
+                result = serviceSessionCache().lookup(oid, SessionCache.LEVEL_SESSION);
+            }
+            else
+            {
+                result = getObjectByIdentity(oid);
+            }
         }
         else
         {
@@ -2234,14 +2354,19 @@
      *
      * @param obj
      * @param cld
-     * @param oid   
+     * @param oid
      * @param insert
      * @param ignoreReferences
      */
     private void storeToDb(Object obj, ClassDescriptor cld, Identity oid, boolean insert, boolean ignoreReferences)
     {
         // 1. link and store 1:1 references
-        storeReferences(obj, cld, insert, ignoreReferences);
+        // we can skip handling for 1:1 references if
+        // it's enabled and the class has no super-reference
+        if(!(ignoreReferences && cld.getSuperReference() == null))
+        {
+            storeReferences(obj, cld, insert, ignoreReferences);
+        }
 
         Object[] pkValues = oid.getPrimaryKeyValues();
         if (!serviceBrokerHelper().assertValidPksForStore(cld.getPkFields(), pkValues))
@@ -2281,6 +2406,11 @@
         if (insert)
         {
             dbAccess.executeInsert(cld, obj);
+            if(oid.isTransient())
+            {
+                // Create a new Identity based on the current set of primary key values.
+                oid = serviceIdentity().buildIdentity(cld, obj);
+            }
         }
         // else use UPDATE
         else
@@ -2296,12 +2426,10 @@
                 throw e;
             }
         }
-        // Create a new Identity based on the current set of primary key values.
-        Identity newOid = serviceIdentity().buildIdentity(cld, obj);
         // cache object for symmetry with getObjectByXXX()
         // Add the object to the cache.
-        serviceSessionCache().cache(newOid, obj, SessionCache.TYPE_WRITE, SessionCache.LEVEL_DEEP);
-        // 3. store 1:n and m:n associations
+        serviceSessionCache().cache(oid, obj, SessionCache.TYPE_WRITE, SessionCache.LEVEL_DEEP);
+        // 3. store 1:n and m:n associations except if we have to skip
         if(!ignoreReferences) storeCollections(obj, cld, insert);
     }
 
@@ -2449,7 +2577,7 @@
     {
         query.setFetchSize(1);
         query.preprocess(this);
-        
+
         if (query instanceof QueryBySQL)
         {
             if(logger.isDebugEnabled()) logger.debug("Creating SQL-RsIterator for class ["+cld.getClassNameOfObject()+"]");
@@ -2470,12 +2598,12 @@
         ChainingIterator chainingIter = new ChainingIterator();
         Collection cldInfos = serviceBrokerHelper().getExtentsDescriptors(cld);
         Iterator extents = cldInfos.iterator();
-        
+
         while (extents.hasNext())
         {
             BrokerHelper.CldInfo cldInfo = (BrokerHelper.CldInfo) extents.next();
             Query theQuery = serviceBrokerHelper().setConcreteClassCriteria(this, (QueryByCriteria)query, cldInfo);
-            
+
             if(logger.isDebugEnabled()) logger.debug("Adding RsIterator of class ["+ cldInfo.cld.getClassNameOfObject()+"] to ChainingIterator");
 
             // add the iterator to the chaining iterator.
@@ -2520,13 +2648,40 @@
         return persistenceConfiguration.getModel();
     }
 
+    protected void finalize()
+    {
+        try
+        {
+            super.finalize();
+            // if not closed ==> broker leak detected
+            if (!isClosed)
+            {
+                String msg = "Garbage collection: Unclosed PersistenceBroker instance detected, check code for PB leaks.";
+                if(brokerLeakDetection)
+                {
+                    logger.error(msg + " Broker caller stack is: "
+                            + SystemUtils.LINE_SEPARATOR + brokerStackTrace);
+                }
+                else
+                {
+                    logger.warn(msg);
+                }
+                close();
+            }
+        }
+        catch(Throwable ignore)
+        {
+            // ignore
+        }
+    }
+
     /**
      * clean up the maps for reuse by the next transaction.
      */
-    private void clearRegistrationLists()
+    private void refreshRegistrationLists()
     {
-        nowStoring.clear();
-        deletedDuringTransaction.clear();
+        if(nowStoring.size() > 0) nowStoring = new IdentityArrayList();
+        if(deletedDuringTransaction.size() > 0) deletedDuringTransaction.clear();
         /*
         arminw:
         for better performance I don't register MtoNBroker as listner,
@@ -2550,7 +2705,7 @@
     {
 		mtoNBroker.storeMtoNImplementor(m2n);
     }
-    
+
     /**
      * Get the Identity out of the Query.
      * @param aQuery
@@ -2559,21 +2714,21 @@
     private Identity getIdentity(QueryByIdentity aQuery)
     {
         Object obj = aQuery.getIdentityObject();
-        Identity oid = null;
-        
+        Identity oid ;
         if (obj instanceof Identity)
         {
             oid = (Identity) obj;
         }
         else
         {
-            // TODO: This workaround doesn't allow 'null' for PK fields
-            if (!serviceBrokerHelper().hasNullPKField(getClassDescriptor(obj.getClass()), obj))
-            {
-                oid = serviceIdentity().buildIdentity(obj);
-            }
+//            if (!serviceBrokerHelper().hasNullPKField(getClassDescriptor(obj.getClass()), obj))
+//            {
+//                oid = serviceIdentity().buildIdentity(obj);
+//            }
+            // TODO: Check this! The above check is no longer needed, because "new objects" will automatic
+            // have transient Identity objects
+            oid = serviceIdentity().buildIdentity(obj);
         }
-        
         return oid;
     }
 

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/core/QueryReferenceBroker.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/core/QueryReferenceBroker.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/core/QueryReferenceBroker.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/core/QueryReferenceBroker.java Sat Jul 15 07:20:25 2006
@@ -27,6 +27,7 @@
 import org.apache.ojb.broker.ManageableCollection;
 import org.apache.ojb.broker.PBLifeCycleEvent;
 import org.apache.ojb.broker.PersistenceBrokerException;
+import org.apache.ojb.broker.TransientObjectException;
 import org.apache.ojb.broker.accesslayer.CollectionCreationContext;
 import org.apache.ojb.broker.accesslayer.OJBIterator;
 import org.apache.ojb.broker.accesslayer.PagingIterator;
@@ -50,6 +51,7 @@
 import org.apache.ojb.broker.util.BrokerHelper;
 import org.apache.ojb.broker.util.logging.Logger;
 import org.apache.ojb.broker.util.logging.LoggerFactory;
+import org.apache.commons.lang.SystemUtils;
 
 /**
  * Encapsulates 1:1 and 1:n references and collection references stuff.
@@ -85,7 +87,7 @@
             throws ClassNotPersistenceCapableException, PersistenceBrokerException
     {
         ManageableCollection collection = pb.getConfiguration().getCollectionFactory().createCollection(context);
-        Query                query      = context.getQuery();
+        Query query = context.getQuery();
 
         if (query == null)
         {
@@ -152,11 +154,12 @@
                     else
                     {
                         //warn the user
-                        log.warn("Candidate object ["+candidate
-                                    +"] class ["+candidate.getClass().getName()
-                                    +"] is not a subtype of ["+itemClass.getName()
-                                    +"] or any type of proxy. NOT INCLUDED in result collection");
-                    }
+                        if(log.isEnabledFor(Logger.WARN)) log.warn(SystemUtils.LINE_SEPARATOR
+                                + "Candidate object ["+candidate + "]"
+                                +" of "+candidate.getClass() + SystemUtils.LINE_SEPARATOR
+                                +"is not a subtype of "+itemClass +" or any type of proxy - e.g. this can be the result of a"
+                                + SystemUtils.LINE_SEPARATOR +"'declared' extent in "+itemClass + "."
+                                + " This can cause side-effects and will NOT INCLUDED in the current generated collection result");                    }
                     if (prefetchProxies && (handler != null)
                             && (cld.getProxyPrefetchingLimit() > 0)
                             && addRetrievalTask(candidate, this))
@@ -166,6 +169,7 @@
                     }
                 }
             }
+
             if (isRetrievalTasksCreated)
             {
                 // turn off auto prefetching for related proxies
@@ -200,6 +204,7 @@
             // catch runtime exc. to guarantee clearing of
             // materialization cache on failure
             pb.serviceSessionCache().clearMaterializationCache();
+            log.error(e);
             throw e;
         }
         finally
@@ -273,7 +278,7 @@
         }
         catch (Throwable e)
         {
-            e.printStackTrace();
+            log.error(e);
             throw new PersistenceBrokerException("Can't query for collection",e);
         }
     }
@@ -325,7 +330,8 @@
                 }
 
                 ObjectReferenceDescriptor ord = (ObjectReferenceDescriptor) key;
-                if (ord.isSuperReferenceDescriptor() || ord.isLazy() || (ord.getItemProxyClass() != null))
+//                if (ord.isSuperReferenceDescriptor() || ord.isLazy() || (ord.getItemProxyClass() != null))
+                if (ord.isLazy() || (ord.getItemProxyClass() != null))
                 {
                     continue;
                 }
@@ -369,12 +375,12 @@
                 else if ( pb.serviceSessionCache().lookup(id) != null )
                 {
                     refObj = pb.getObjectByIdentity(id);
-                    if (rds.isSuperReferenceDescriptor()) 
+                    if (rds.isSuperReferenceDescriptor())
                     {
                         // walk the super-references
                         ClassDescriptor superCld = cld.getRepository().getDescriptorFor(rds.getItemClass());
                         retrieveReferences(refObj, superCld, false);
-                        retrieveCollections(refObj, superCld, false);                        
+                        retrieveCollections(refObj, superCld, false);
                     }
                 }
                 else if ((m_retrievalTasks != null)
@@ -422,6 +428,52 @@
     }
 
     /**
+     * Retrieve a single Reference.
+     * This implementation retrieves a referenced object from the data backend
+     * if <b>cascade-retrieve</b> is true or if <b>forced</b> is true.
+     *
+     * @param obj - object that will have it's field set with a referenced object.
+     * @param cld - the ClassDescriptor describring obj
+     * @param rds - the ObjectReferenceDescriptor of the reference attribute to be loaded
+     * @param forced - if set to true, the reference is loaded even if the rds differs.
+     */
+    public void retrieveProxyReference(Object obj, ClassDescriptor cld, ObjectReferenceDescriptor rds, boolean forced)
+    {
+        PersistentField refField;
+        Object refObj = null;
+
+            pb.serviceSessionCache().enableMaterializationCache();
+            try
+            {
+                Identity id = getReferencedObjectIdentity(obj, rds, cld);
+                if (id != null){
+                    refObj = pb.createProxy(rds.getItemClass(), id);
+                }
+                refField = rds.getPersistentField();
+                refField.set(obj, refObj);
+
+                if ((refObj != null) && prefetchProxies
+                        && (m_retrievalTasks != null)
+                        && (rds.getProxyPrefetchingLimit() > 0))
+                {
+                    IndirectionHandler handler = pb.getProxyFactory().getIndirectionHandler(refObj);
+
+                    if ((handler != null) && addRetrievalTask(obj, rds))
+                    {
+                        new PBMaterializationListener(obj, m_retrievalTasks, rds, rds.getProxyPrefetchingLimit(), pb.getProxyFactory());
+                    }
+                }
+                pb.serviceSessionCache().disableMaterializationCache();
+            }
+            catch(RuntimeException e)
+            {
+                pb.serviceSessionCache().clearMaterializationCache();
+                throw e;
+            }
+
+    }
+
+    /**
      * Retrieve all References
      *
      * @param newObj the instance to be loaded or refreshed
@@ -459,6 +511,43 @@
         }
     }
 
+    /**
+     * Retrieve all References
+     *
+     * @param newObj the instance to be loaded or refreshed
+     * @param cld the ClassDescriptor of the instance
+     * @param forced if set to true loading is forced even if cld differs.
+     */
+    public void retrieveProxyReferences(Object newObj, ClassDescriptor cld, boolean forced) throws PersistenceBrokerException
+    {
+        Iterator i = cld.getObjectReferenceDescriptors().iterator();
+
+        // turn off auto prefetching for related proxies
+        final Class saveClassToPrefetch = classToPrefetch;
+        classToPrefetch = null;
+
+        pb.serviceSessionCache().enableMaterializationCache();
+        try
+        {
+            while (i.hasNext())
+            {
+                ObjectReferenceDescriptor rds = (ObjectReferenceDescriptor) i.next();
+                retrieveProxyReference(newObj, cld, rds, forced);
+            }
+
+            pb.serviceSessionCache().disableMaterializationCache();
+        }
+        catch(RuntimeException e)
+        {
+            pb.serviceSessionCache().clearMaterializationCache();
+            throw e;
+        }
+        finally
+        {
+            classToPrefetch = saveClassToPrefetch;
+        }
+    }
+
    /**
      * retrieves an Object reference's Identity.
      * <br>
@@ -491,7 +580,7 @@
         else
         {
             // ensure that top-level extents are used for Identities
-            return new Identity(rds.getItemClass(), pb.getTopLevelClass(rds.getItemClass()), fkValues);
+            return pb.serviceIdentity().buildIdentity(rds.getItemClass(), pb.getTopLevelClass(rds.getItemClass()), fkValues);
         }
         return null;
     }
@@ -559,8 +648,15 @@
             }
             catch (Exception e)
             {
-                log.error("Error instantiating obj: " + e.getMessage(), e);
-                throw new PersistenceBrokerException(e);
+                log.error("Error while instantiate object " + id + ", msg: "+ e.getMessage(), e);
+                if(e instanceof PersistenceBrokerException)
+                {
+                    throw (PersistenceBrokerException) e;
+                }
+                else
+                {
+                    throw new PersistenceBrokerException(e);
+                }
             }
         }
         else
@@ -582,6 +678,27 @@
      */
     public void retrieveCollection(Object obj, ClassDescriptor cld, CollectionDescriptor cds, boolean forced)
     {
+        doRetrieveCollection(obj, cds, forced);
+    }
+
+    /**
+     * Retrieve a single Proxied Collection on behalf of <b>obj</b>.
+     * The Collection is retrieved only if <b>cascade.retrieve is true</b>
+     * or if <b>forced</b> is set to true.     *
+     *
+     * @param obj - the object to be updated
+     * @param cld - the ClassDescriptor describing obj
+     * @param cds - the CollectionDescriptor describing the collection attribute to be loaded
+     * @param forced - if set to true a proxy will be placed, even if cds differs.
+     *
+     */
+    public void retrieveProxyCollection(Object obj, ClassDescriptor cld, CollectionDescriptor cds, boolean forced)
+    {
+        doRetrieveCollection(obj, cds, forced);
+    }
+
+    private void doRetrieveCollection(Object obj, CollectionDescriptor cds, boolean forced)
+    {
         if (forced || cds.getCascadeRetrieve())
         {
             if ((m_retrievalTasks != null) && !cds.isLazy()
@@ -768,9 +885,16 @@
      *
      * @param oid the Identity of the Object to retrieve
      * @return The resulting query
+     * @throws TransientObjectException If the specified {@link org.apache.ojb.broker.Identity}
+     * is <em>transient</em> this exception will be thrown, because it's not possible to build
+     * a valid query.
      */
-    public Query getPKQuery(Identity oid)
+    public Query getPKQuery(Identity oid) throws TransientObjectException
     {
+        if(oid.isTransient())
+        {
+            throw new TransientObjectException("Not allowed to build PK Query for a transient object");
+        }
         Object[] values = oid.getPrimaryKeyValues();
         ClassDescriptor cld = pb.getClassDescriptor(oid.getObjectsTopLevelClass());
         FieldDescriptor[] fields = cld.getPkFields();
@@ -794,6 +918,24 @@
      */
     public void retrieveCollections(Object newObj, ClassDescriptor cld, boolean forced) throws PersistenceBrokerException
     {
+        doRetrieveCollections(newObj, cld, forced, false);
+    }
+
+    /**
+     * Retrieve all Collection attributes of a given instance, and make all of the Proxy Collections
+     *
+     * @param newObj the instance to be loaded or refreshed
+     * @param cld the ClassDescriptor of the instance
+     * @param forced if set to true, loading is forced even if cld differs
+     *
+     */
+    public void retrieveProxyCollections(Object newObj, ClassDescriptor cld, boolean forced) throws PersistenceBrokerException
+    {
+        doRetrieveCollections(newObj, cld, forced, true);
+    }
+
+    private void doRetrieveCollections(Object newObj, ClassDescriptor cld, boolean forced, boolean forceProxyCollection) throws PersistenceBrokerException
+    {
         Iterator i = cld.getCollectionDescriptors().iterator();
 
         // turn off auto prefetching for related proxies
@@ -806,7 +948,14 @@
             while (i.hasNext())
             {
                 CollectionDescriptor cds = (CollectionDescriptor) i.next();
-                retrieveCollection(newObj, cld, cds, forced);
+                if(forceProxyCollection)
+                {
+                    retrieveProxyCollection(newObj, cld, cds, forced);
+                }
+                else
+                {
+                    retrieveCollection(newObj, cld, cds, forced);
+                }
             }
             pb.serviceSessionCache().disableMaterializationCache();
         }
@@ -858,7 +1007,7 @@
 
 
         PBMaterializationListener(Object owner,
-                HashMap retrievalTasks, Object key, int limit, ProxyFactory proxyFactory)
+                                  HashMap retrievalTasks, Object key, int limit, ProxyFactory proxyFactory)
         {
             super(owner, retrievalTasks, key, limit, proxyFactory);
         }
@@ -918,7 +1067,7 @@
        protected ProxyFactory _proxyFactory;
 
         PBPrefetchingListener(Object owner, HashMap retrievalTasks,
-                Object key, int limit, ProxyFactory proxyFactory)
+                              Object key, int limit, ProxyFactory proxyFactory)
         {
             _retrievalTasks = retrievalTasks;
             _key = key;
@@ -997,7 +1146,7 @@
         CollectionProxy _listenedCollection;
 
         PBCollectionProxyListener(Object owner,
-                HashMap retrievalTasks, CollectionDescriptor key, int limit, ProxyFactory proxyFactory)
+                                  HashMap retrievalTasks, CollectionDescriptor key, int limit, ProxyFactory proxyFactory)
         {
             super(owner, retrievalTasks, key, limit, proxyFactory);
         }

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/core/ValueContainer.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/core/ValueContainer.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/core/ValueContainer.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/core/ValueContainer.java Sat Jul 15 07:20:25 2006
@@ -103,7 +103,7 @@
     public String toString()
     {
         return "[" + ClassUtils.getShortClassName(this.getClass()) + ": jdbcType="
-                + jdbcType.getTypeAsString()
+                + jdbcType
                 + ", value=" + value + "]";
     }
 }

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/locking/IsolationLevels.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/locking/IsolationLevels.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/locking/IsolationLevels.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/locking/IsolationLevels.java Sat Jul 15 07:20:25 2006
@@ -176,7 +176,7 @@
     /**
      * Literal constant representing that no isolation level is used.
      */
-    public final static String LITERAL_IL_NO_LOCKING = "no-lock";
+    public final static String LITERAL_IL_NO_LOCKING = "none";
 
     /**
      * Literal constant representing the uncommited read isolation level.

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolation.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolation.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolation.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolation.java Sat Jul 15 07:20:25 2006
@@ -15,12 +15,13 @@
  * limitations under the License.
  */
 
+import java.io.Serializable;
 
 /**
  * This interface defines method that a Locking Strategy must implement
  * according to the isolation level it represents.
  */
-abstract class LockIsolation
+abstract class LockIsolation implements Serializable
 {
     /**
      * Returns the isolation level identity.

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolationManager.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolationManager.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolationManager.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockIsolationManager.java Sat Jul 15 07:20:25 2006
@@ -15,14 +15,14 @@
  * limitations under the License.
  */
 
-
+import java.io.Serializable;
 
 /**
  * Factory class used to obtain the proper {@link LockIsolation} level.
  *
  * @version $Id$
  */
-class LockIsolationManager
+class LockIsolationManager implements Serializable
 {
     private LockIsolation readUncommitedStrategy;
     private LockIsolation readCommitedStrategy;

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManager.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManager.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManager.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManager.java Sat Jul 15 07:20:25 2006
@@ -1,6 +1,6 @@
 package org.apache.ojb.broker.locking;
 
-/* Copyright 2002-2004 The Apache Software Foundation
+/* Copyright 2002-2005 The Apache Software Foundation
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -53,15 +53,16 @@
     /**
      * The maximal time to wait for acquire a lock.
      *
-     * @return The time to wait for aquire a lock.
+     * @return The time to wait for aquire a lock in milliseconds.
      */
     public long getBlockTimeout();
 
     /**
-     * Set the maximal time to wait for acquire a lock in milliseconds.
+     * Set the maximal time to wait for acquire a lock.
+     * <br/>
      * All so called <em>non-blocking</em> implementation will ignore this setting.
      *
-     * @param timeout The time to wait for acquire a lock.
+     * @param timeout The time to wait for acquire a lock in milliseconds.
      */
     public void setBlockTimeout(long timeout);
 

Modified: db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManagerCommonsImpl.java
URL: http://svn.apache.org/viewvc/db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManagerCommonsImpl.java?rev=422231&r1=422230&r2=422231&view=diff
==============================================================================
--- db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManagerCommonsImpl.java (original)
+++ db/ojb/trunk/src/java/org/apache/ojb/broker/locking/LockManagerCommonsImpl.java Sat Jul 15 07:20:25 2006
@@ -1,13 +1,5 @@
 package org.apache.ojb.broker.locking;
 
-import org.apache.commons.lang.SystemUtils;
-import org.apache.commons.transaction.locking.GenericLock;
-import org.apache.commons.transaction.locking.GenericLockManager;
-import org.apache.commons.transaction.locking.LockException;
-import org.apache.commons.transaction.util.LoggerFacade;
-import org.apache.ojb.broker.util.logging.Logger;
-import org.apache.ojb.broker.util.logging.LoggerFactory;
-
 /* Copyright 2002-2004 The Apache Software Foundation
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -23,6 +15,14 @@
  * limitations under the License.
  */
 
+import org.apache.commons.lang.SystemUtils;
+import org.apache.commons.transaction.locking.GenericLock;
+import org.apache.commons.transaction.locking.GenericLockManager;
+import org.apache.commons.transaction.locking.LockException;
+import org.apache.commons.transaction.util.LoggerFacade;
+import org.apache.ojb.broker.util.logging.Logger;
+import org.apache.ojb.broker.util.logging.LoggerFactory;
+
 /**
  * A {@link LockManager} implementation based on apache's commons-transaction
  * locking part.
@@ -30,7 +30,6 @@
  * The timeout of locks is currently (OJB 1.0.2) not supported, maybe
  * in further versions.
  *
- * @author <a href="mailto:arminw@apache.org">Armin Waibel</a>
  * @version $Id$
  */
 public class LockManagerCommonsImpl implements LockManager
@@ -49,12 +48,11 @@
 
     public LockManagerCommonsImpl()
     {
-        LoggerFacade logFacade = new LoggerFacadeImpl();
         // default lock timeout
         this.lockTimeout = DEFAULT_LOCK_TIMEOUT;
         // default time to wait for a lock
         this.blockTimeout = DEFAULT_BLOCK_TIMEOUT;
-        lm = new OJBLockManager(logFacade, blockTimeout, GenericLockManager.DEFAULT_CHECK_THRESHHOLD);
+        lm = new OJBLockManager(new LoggerFacadeImpl(), blockTimeout, GenericLockManager.DEFAULT_CHECK_THRESHHOLD);
     }
 
     public long getLockTimeout()



---------------------------------------------------------------------
To unsubscribe, e-mail: ojb-dev-unsubscribe@db.apache.org
For additional commands, e-mail: ojb-dev-help@db.apache.org