jackrabbit-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From dpfis...@apache.org
Subject svn commit: r790892 - /jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/
Date Fri, 03 Jul 2009 13:00:25 GMT
Author: dpfister
Date: Fri Jul  3 13:00:25 2009
New Revision: 790892

URL: http://svn.apache.org/viewvc?rev=790892&view=rev
Log:
JCR-2183 - Provide overridables for lock checking
- Add public LockInfo class
- Make AbstractLockInfo package private
- Rename internal LockInfo classes to avoid confusion
- Add overridable in LockManagerImpl with default implementation

Added:
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java
  (with props)
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockImpl.java
      - copied, changed from r790814, jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALock.java
Removed:
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALock.java
Modified:
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/AbstractLockInfo.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockImpl.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManager.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/SessionLockManager.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XAEnvironment.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockManager.java

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/AbstractLockInfo.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/AbstractLockInfo.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/AbstractLockInfo.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/AbstractLockInfo.java
Fri Jul  3 13:00:25 2009
@@ -24,12 +24,13 @@
 /**
  * Common information about a lock.
  */
-public abstract class AbstractLockInfo {
+abstract class AbstractLockInfo implements LockInfo {
 
     /**
      * Constant for the undefined or infinite timeout.
      */
     static final long TIMEOUT_INFINITE = Long.MAX_VALUE;
+    
     /**
      * Constant for the expired timeout.
      */
@@ -56,14 +57,14 @@
     protected final String lockOwner;
 
     /**
-     * Session currently holding lock
+     * Flag indicating whether this lock is live
      */
-    protected SessionImpl lockHolder;
+    private boolean live;
 
     /**
-     * Flag indicating whether this lock is live
+     * Session currently holding lock
      */
-    protected boolean live;
+    private SessionImpl lockHolder;
 
     /**
      * Create a new instance of this class.
@@ -111,6 +112,27 @@
     public NodeId getId() {
         return lockToken.getId();
     }
+    
+    /**
+     * {@inheritDoc}
+     */
+    public boolean isLockHolder(Session session) {
+    	return lockHolder == session;
+    }
+    
+    /**
+     * {@inheritDoc}
+     */
+    public String getLockOwner() {
+    	return lockOwner;
+    }
+    
+    /**
+     * {@inheritDoc}
+     */
+    public boolean isDeep() {
+    	return deep;
+    }
 
     /**
      * Return the session currently holding the lock
@@ -129,21 +151,25 @@
     public void setLockHolder(SessionImpl lockHolder) {
         this.lockHolder = lockHolder;
     }
-
+    
     /**
-     * Return the lock token as seen by the session passed as parameter. If
-     * this session is currently holding the lock, it will get the lock token
-     * itself, otherwise a <code>null</code> string.
-     *
-     * @param session The session asking for the lock token.
-     * @return lock token.
+     * {@inheritDoc}
      */
     public String getLockToken(Session session) {
-        if (session.equals(lockHolder)) {
+    	if (isLockHolder(session)) {
             return lockToken.toString();
         }
         return null;
     }
+    
+    /**
+     * Return the lock token.
+     * 
+     * @return lock token
+     */
+    public String getLockToken() {
+    	return lockToken.toString();
+    }
 
     /**
      * Return a flag indicating whether the lock is live

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockImpl.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockImpl.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockImpl.java
Fri Jul  3 13:00:25 2009
@@ -33,7 +33,7 @@
     /**
      * Lock info containing latest information
      */
-    protected final AbstractLockInfo info;
+    protected final LockInfo info;
 
     /**
      * Node holding lock
@@ -46,7 +46,7 @@
      * @param info lock information
      * @param node node holding lock
      */
-    public LockImpl(AbstractLockInfo info, Node node) {
+    public LockImpl(LockInfo info, Node node) {
         this.info = info;
         this.node = node;
     }
@@ -57,14 +57,14 @@
      * {@inheritDoc}
      */
     public String getLockOwner() {
-        return info.lockOwner;
+        return info.getLockOwner();
     }
 
     /**
      * {@inheritDoc}
      */
     public boolean isDeep() {
-        return info.deep;
+        return info.isDeep();
     }
 
     /**
@@ -138,7 +138,7 @@
      */
     public boolean isLockOwningSession() {
         try {
-            return node.getSession().equals(info.getLockHolder());
+        	return info.isLockHolder(node.getSession());
         } catch (RepositoryException e) {
             return false;
         }

Added: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java?rev=790892&view=auto
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java
(added)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java
Fri Jul  3 13:00:25 2009
@@ -0,0 +1,87 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.jackrabbit.core.lock;
+
+import org.apache.jackrabbit.core.NodeId;
+
+import javax.jcr.Session;
+
+/**
+ * Lock information interface.
+ */
+public interface LockInfo {
+
+    /**
+     * Return the ID of the lock holding node
+     * @return the id
+     */
+    public NodeId getId();
+    
+    /**
+     * Return the lock owner.
+     * 
+     * @return lock owner
+     */
+    public String getLockOwner();
+    
+    /**
+     * Return a flag indicating whether the lock is deep.
+     * 
+     * @return <code>true</code> if the lock is deep;
+     *         <code>false</code> otherwise
+     */
+    public boolean isDeep();
+    
+    /**
+     * Return a flag indicating whether the session given is lock holder. 
+     *
+     * @param session session to compare with
+     */
+    public boolean isLockHolder(Session session);
+
+    /**
+     * Return the lock token as seen by the session passed as parameter. If
+     * this session is currently holding the lock, it will get the lock token
+     * itself, otherwise a <code>null</code> string.
+     *
+     * @param session The session asking for the lock token.
+     * @return lock token.
+     */
+    public String getLockToken(Session session);
+
+    /**
+     * Return a flag indicating whether the lock is live
+     *
+     * @return <code>true</code> if the lock is live; otherwise <code>false</code>
+     */
+    public boolean isLive();
+
+    /**
+     * Return a flag indicating whether the lock is session-scoped
+     *
+     * @return <code>true</code> if the lock is session-scoped;
+     *         otherwise <code>false</code>
+     */
+    public boolean isSessionScoped();
+
+    /**
+     * Return the number of seconds remaining until the lock expires.
+     *
+     * @return number of seconds remaining until the lock expires.
+     */
+    public long getSecondsRemaining();
+}

Propchange: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockInfo.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManager.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManager.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManager.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManager.java
Fri Jul  3 13:00:25 2009
@@ -102,20 +102,6 @@
     boolean holdsLock(NodeImpl node) throws RepositoryException;
 
     /**
-     * Returns <code>true</code> if the specified session holds a lock on the
-     * given node; otherwise returns <code>false</code>.
-     * <p/>
-     * Note that <code>isLockHolder(session, node)==true</code> implies
-     * <code>holdsLock(node)==true</code>.
-     * @param session session
-     * @param node node
-     * @return if the specified session holds a lock on the given node;
-     *         otherwise returns <code>false</code>
-     * @throws javax.jcr.RepositoryException If an exception occurs.
-     */
-    boolean isLockHolder(Session session, NodeImpl node) throws RepositoryException;
-
-    /**
      * Returns <code>true</code> if this node is locked either as a result
      * of a lock held by this node or by a deep lock on a node above this
      * node; otherwise returns <code>false</code>
@@ -154,6 +140,19 @@
             throws LockException, RepositoryException;
 
     /**
+     * Returns <code>true</code> if the specified session is allowed to unlock
+     * the node; otherwise returns <code>false</code>.
+     * @param session session
+     * @param node node
+     * @return <code>true</code> if the session is allowed access to the node;
+     *         <code>false</code> otherwise
+     * @throws LockException if write access to the specified path is not allowed
+     * @throws RepositoryException if some other error occurs
+     */
+    void checkUnlock(Session session, NodeImpl node) 
+    		throws LockException, RepositoryException;
+    
+    /**
      * Invoked by a session to inform that a lock token has been added.
      * 
      * @param session session that has a added lock token
@@ -161,7 +160,7 @@
      * @throws LockException
      * @throws RepositoryException
      */
-    void lockTokenAdded(SessionImpl session, String lt) throws LockException, RepositoryException;
+    void addLockToken(SessionImpl session, String lt) throws LockException, RepositoryException;
 
     /**
      * Invoked by a session to inform that a lock token has been removed.
@@ -171,5 +170,5 @@
      * @throws LockException
      * @throws RepositoryException
      */
-    void lockTokenRemoved(SessionImpl session, String lt) throws LockException, RepositoryException;
+    void removeLockToken(SessionImpl session, String lt) throws LockException, RepositoryException;
 }

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java
Fri Jul  3 13:00:25 2009
@@ -222,7 +222,7 @@
                 sysSession.getItemManager().getItem(lockToken.getId());
             Path path = getPath(sysSession, lockToken.getId());
 
-            LockInfo info = new LockInfo(lockToken, false,
+            InternalLockInfo info = new InternalLockInfo(lockToken, false,
                     node.getProperty(NameConstants.JCR_LOCKISDEEP).getBoolean(),
                     node.getProperty(NameConstants.JCR_LOCKOWNER).getString());
             info.setLive(true);
@@ -242,12 +242,12 @@
             return;
         }
 
-        final ArrayList<LockInfo> list = new ArrayList<LockInfo>();
+        final ArrayList<AbstractLockInfo> list = new ArrayList<AbstractLockInfo>();
 
         lockMap.traverse(new PathMap.ElementVisitor() {
             public void elementVisited(PathMap.Element element) {
-                LockInfo info = (LockInfo) element.get();
-                if (!info.sessionScoped) {
+            	AbstractLockInfo info = (AbstractLockInfo) element.get();
+                if (!info.isSessionScoped()) {
                     list.add(info);
                 }
             }
@@ -260,8 +260,8 @@
             writer = new BufferedWriter(
                     new OutputStreamWriter(locksFile.getOutputStream()));
             for (int i = 0; i < list.size(); i++) {
-                AbstractLockInfo info = list.get(i);
-                writer.write(info.lockToken.toString());
+            	AbstractLockInfo info = list.get(i);
+                writer.write(info.getLockToken());
                 writer.newLine();
             }
         } catch (FileSystemException fse) {
@@ -302,7 +302,7 @@
 
         SessionImpl session = (SessionImpl) node.getSession();
         String lockOwner = (ownerInfo != null) ? ownerInfo : session.getUserID();
-        LockInfo info = new LockInfo(new LockToken(node.getNodeId()),
+        InternalLockInfo info = new InternalLockInfo(new LockToken(node.getNodeId()),
                 isSessionScoped, isDeep, lockOwner, timeoutHint);
 
         ClusterOperation operation = null;
@@ -324,7 +324,7 @@
             if (other != null) {
                 if (element.hasPath(path)) {
                     throw new LockException("Node already locked: " + node);
-                } else if (other.deep) {
+                } else if (other.isDeep()) {
                     throw new LockException(
                             "Parent node has a deep lock: " + node);
                 }
@@ -339,11 +339,11 @@
             info.setLive(true);
             session.addListener(info);
             if (!info.isSessionScoped()) {
-                getSessionLockManager(session).lockTokenAdded(info.lockToken.toString());
+                getSessionLockManager(session).lockTokenAdded(info.getLockToken());
             }
             lockMap.put(path, info);
 
-            if (!info.sessionScoped) {
+            if (!info.isSessionScoped()) {
                 save();
                 successful = true;
             }
@@ -386,16 +386,14 @@
             if (info == null) {
                 throw new LockException("Node not locked: " + node);
             }
-            if (session != info.getLockHolder()) {
-                throw new LockException("Node not locked by session: " + node);
-            }
+            checkUnlock(info, session);
 
             getSessionLockManager(session).lockTokenRemoved(info.getLockToken(session));
 
             element.set(null);
             info.setLive(false);
 
-            if (!info.sessionScoped) {
+            if (!info.isSessionScoped()) {
                 save();
                 successful = true;
             }
@@ -421,7 +419,7 @@
         lockMap.traverse(new PathMap.ElementVisitor() {
             public void elementVisited(PathMap.Element element) {
                 LockInfo info = (LockInfo) element.get();
-                if (info.isLive() && info.getLockHolder().equals(session)) {
+                if (info.isLive() && info.isLockHolder(session)) {
                     infos.add(info);
                 }
             }
@@ -449,7 +447,7 @@
             PathMap.Element element = lockMap.map(path, false);
             AbstractLockInfo info = (AbstractLockInfo) element.get();
             if (info != null) {
-                if (element.hasPath(path) || info.deep) {
+                if (element.hasPath(path) || info.isDeep()) {
                     return info;
                 }
             }
@@ -561,28 +559,6 @@
     /**
      * {@inheritDoc}
      */
-    public boolean isLockHolder(Session session, NodeImpl node)
-            throws RepositoryException {
-        acquire();
-
-        try {
-            SessionImpl nodeSession = (SessionImpl) node.getSession();
-            PathMap.Element element = lockMap.map(getPath(nodeSession, node.getId()), true);
-            if (element == null) {
-                return false;
-            }
-            AbstractLockInfo info = (AbstractLockInfo) element.get();
-            return info != null && info.getLockHolder() == session;
-        } catch (ItemNotFoundException e) {
-            return false;
-        } finally {
-            release();
-        }
-    }
-
-    /**
-     * {@inheritDoc}
-     */
     public boolean isLocked(NodeImpl node) throws RepositoryException {
         acquire();
 
@@ -624,20 +600,77 @@
             throws LockException, RepositoryException {
 
         PathMap.Element element = lockMap.map(path, false);
-        AbstractLockInfo info = (AbstractLockInfo) element.get();
+        LockInfo info = (LockInfo) element.get();
         if (info != null) {
-            if (element.hasPath(path) || info.deep) {
-                if (session != info.getLockHolder()) {
-                    throw new LockException("Node locked.");
-                }
+            if (element.hasPath(path) || info.isDeep()) {
+            	checkLock(info, session);
             }
         }
     }
 
     /**
+     * Check whether a lock info allows access to a session. May be overridden
+     * by subclasses to allow access to nodes for sessions other than the
+     * lock holder itself.
+     * <p/>
+     * Default implementation allows access to the lock holder only.
+     * 
+     * @param info info to check
+     * @param session session
+     * @throws LockException if write access to the specified path is not allowed
+     * @throws RepositoryException if some other error occurs
+     */
+    protected void checkLock(LockInfo info, Session session) 
+    		throws LockException, RepositoryException {
+    	
+    	if (!info.isLockHolder(session)) {
+            throw new LockException("Node locked.");
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void checkUnlock(Session session, NodeImpl node)
+    		throws LockException, RepositoryException {
+
+	    // check whether node is locked by this session
+	    PathMap.Element element = lockMap.map(
+	    		getPath((SessionImpl) session, node.getId()), true);
+	    if (element == null) {
+	        throw new LockException("Node not locked: " + node);
+	    }
+	    AbstractLockInfo info = (AbstractLockInfo) element.get();
+	    if (info == null) {
+	        throw new LockException("Node not locked: " + node);
+	    }
+	    checkUnlock(info, session);
+    }
+
+    /**
+     * Check whether a session is allowed to unlock a node. May be overridden
+     * by subclasses to allow this to sessions other than the lock holder
+     * itself.
+     * <p/>
+     * Default implementation allows unlocking to the lock holder only.
+     * 
+     * @param info info to check
+     * @param session session
+     * @throws LockException if unlocking is denied
+     * @throws RepositoryException if some other error occurs
+     */
+    protected void checkUnlock(LockInfo info, Session session)
+    		throws LockException, RepositoryException {
+    	
+	    if (!info.isLockHolder(session)) {
+	        throw new LockException("Node not locked by session: " + info.getId());
+	    }
+    }
+    
+    /**
      * {@inheritDoc}
      */
-    public void lockTokenAdded(SessionImpl session, String lt) throws LockException, RepositoryException
{
+    public void addLockToken(SessionImpl session, String lt) throws LockException, RepositoryException
{
         try {
             LockToken lockToken = LockToken.parse(lt);
 
@@ -647,10 +680,12 @@
             if (element != null) {
                 AbstractLockInfo info = (AbstractLockInfo) element.get();
                 if (info != null) {
-                    if (info.getLockHolder() == null) {
+                	if (info.isLockHolder(session)) {
+                		// nothing to do
+                	} else if (info.getLockHolder() == null) {
                         info.setLockHolder(session);
-                        if (info instanceof LockInfo) {
-                            session.addListener((LockInfo) info);
+                        if (info instanceof InternalLockInfo) {
+                            session.addListener((InternalLockInfo) info);
                         }
                     } else {
                         String msg = "Cannot add lock token: lock already held by other session.";
@@ -671,7 +706,9 @@
     /**
      * {@inheritDoc}
      */
-    public void lockTokenRemoved(SessionImpl session, String lt) throws LockException, RepositoryException
{
+    public void removeLockToken(SessionImpl session, String lt) 
+    		throws LockException, RepositoryException {
+    	
         try {
             LockToken lockToken = LockToken.parse(lt);
 
@@ -681,8 +718,10 @@
             if (element != null) {
                 AbstractLockInfo info = (AbstractLockInfo) element.get();
                 if (info != null) {
-                    if (session == info.getLockHolder()) {
+                	if (info.isLockHolder(session)) {
                         info.setLockHolder(null);
+                	} else if (info.getLockHolder() == null) {
+                		// nothing to do
                     } else {
                         String msg = "Cannot remove lock token: lock held by other session.";
                         log.warn(msg);
@@ -1023,13 +1062,13 @@
      * its position.
      */
     private void refresh(PathMap.Element element) {
-        final ArrayList<LockInfo> infos = new ArrayList<LockInfo>();
+        final ArrayList<AbstractLockInfo> infos = new ArrayList<AbstractLockInfo>();
         boolean needsSave = false;
 
         // save away non-empty children
         element.traverse(new PathMap.ElementVisitor() {
             public void elementVisited(PathMap.Element element) {
-                LockInfo info = (LockInfo) element.get();
+            	AbstractLockInfo info = (AbstractLockInfo) element.get();
                 infos.add(info);
             }
         }, false);
@@ -1040,14 +1079,14 @@
         // now re-insert at appropriate location or throw away if node
         // does no longer exist
         for (int i = 0; i < infos.size(); i++) {
-            LockInfo info = infos.get(i);
+        	AbstractLockInfo info = infos.get(i);
             try {
                 NodeImpl node = (NodeImpl) sysSession.getItemManager().
                         getItem(info.getId());
                 lockMap.put(node.getPrimaryPath(), info);
             } catch (RepositoryException e) {
                 info.setLive(false);
-                if (!info.sessionScoped) {
+                if (!info.isSessionScoped()) {
                     needsSave = true;
                 }
             }
@@ -1128,7 +1167,7 @@
      * Contains information about a lock and gets placed inside the child
      * information of a {@link org.apache.jackrabbit.spi.commons.name.PathMap}.
      */
-    class LockInfo extends AbstractLockInfo implements SessionListener {
+    class InternalLockInfo extends AbstractLockInfo implements SessionListener {
 
         /**
          * Create a new instance of this class.
@@ -1138,8 +1177,8 @@
          * @param deep          whether lock is deep
          * @param lockOwner     owner of lock
          */
-        public LockInfo(LockToken lockToken, boolean sessionScoped,
-                        boolean deep, String lockOwner) {
+        public InternalLockInfo(LockToken lockToken, boolean sessionScoped,
+                                boolean deep, String lockOwner) {
             this(lockToken, sessionScoped, deep, lockOwner, TIMEOUT_INFINITE);
         }
 
@@ -1152,11 +1191,11 @@
          * @param lockOwner     owner of lock
          * @param timeoutHint
          */
-        public LockInfo(LockToken lockToken, boolean sessionScoped,
-                        boolean deep, String lockOwner, long timeoutHint) {
+        public InternalLockInfo(LockToken lockToken, boolean sessionScoped,
+                                boolean deep, String lockOwner, long timeoutHint) {
             super(lockToken, sessionScoped, deep, lockOwner, timeoutHint);
         }
-
+        
         /**
          * {@inheritDoc}
          * <p/>
@@ -1167,8 +1206,8 @@
          *     from the session and set the lockHolder field to <code>null</code>.
          */
         public void loggingOut(SessionImpl session) {
-            if (live) {
-                if (sessionScoped) {
+            if (isLive()) {
+                if (isSessionScoped()) {
                     // if no session currently holds lock, reassign
                     SessionImpl lockHolder = getLockHolder();
                     if (lockHolder == null) {
@@ -1188,15 +1227,13 @@
                             NodeImpl node = (NodeImpl) systemSession.getItemManager().getItem(getId());
                             node.unlock();
                         } catch (RepositoryException re) {
-                            log.warn("Unable to remove session-scoped lock on node '" + lockToken
+ "': " + e.getMessage());
+                            log.warn("Unable to remove session-scoped lock on node '" + getLockToken()
+ "': " + e.getMessage());
                             log.debug("Root cause: ", e);
                         }
                     }
-                } else {
-                    if (session == lockHolder) {
-                        session.removeLockToken(lockToken.toString());
-                        lockHolder = null;
-                    }
+                } else if (isLockHolder(session)) {
+                    session.removeLockToken(getLockToken());
+                    setLockHolder(null);
                 }
             }
         }
@@ -1230,7 +1267,7 @@
             Path path = getPath(sysSession, nodeId);
 
             // create lock token
-            LockInfo info = new LockInfo(new LockToken(nodeId), false, isDeep, lockOwner);
+            InternalLockInfo info = new InternalLockInfo(new LockToken(nodeId), false, isDeep,
lockOwner);
             info.setLive(true);
             lockMap.put(path, info);
 

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/SessionLockManager.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/SessionLockManager.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/SessionLockManager.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/SessionLockManager.java
Fri Jul  3 13:00:25 2009
@@ -72,7 +72,7 @@
      */
     public void addLockToken(String lockToken) throws LockException, RepositoryException
{
         if (!lockTokens.contains(lockToken)) {
-            systemLockMgr.lockTokenAdded(session, lockToken);
+            systemLockMgr.addLockToken(session, lockToken);
         } else {
             log.debug("Lock token already present with session -> no effect.");
         }
@@ -83,7 +83,7 @@
      */
     public void removeLockToken(String lockToken) throws LockException, RepositoryException
{
         if (lockTokens.contains(lockToken)) {
-            systemLockMgr.lockTokenRemoved(session, lockToken);
+            systemLockMgr.removeLockToken(session, lockToken);
         } else {
             throw new LockException("Lock token " + lockToken + " not present with session.");
         }
@@ -179,9 +179,7 @@
             if (!systemLockMgr.holdsLock(node)) {
                 throw new LockException("Node not locked: " + node);
             }
-            if (!systemLockMgr.isLockHolder(session, node)) {
-                throw new LockException("Node not locked by session: " + node);
-            }
+            systemLockMgr.checkUnlock(session, node);
             systemLockMgr.unlock(node);
         }
     }

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XAEnvironment.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XAEnvironment.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XAEnvironment.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XAEnvironment.java
Fri Jul  3 13:00:25 2009
@@ -56,17 +56,19 @@
     /**
      * Map of locked nodes, indexed by their (internal) id.
      */
-    private final Map lockedNodesMap = new HashMap();
+    private final Map<NodeId, XALockInfo> lockedNodesMap = 
+    		new HashMap<NodeId, XALockInfo>();
 
     /**
      * Map of unlocked nodes, indexed by their (internal) id.
      */
-    private final Map unlockedNodesMap = new HashMap();
+    private final Map<NodeId, XALockInfo> unlockedNodesMap = 
+    		new HashMap<NodeId, XALockInfo>();
 
     /**
      * List of lock/unlock operations.
      */
-    private final List operations = new ArrayList();
+    private final List<XALockInfo> operations = new ArrayList<XALockInfo>();
 
     /**
      * Operation index.
@@ -129,7 +131,7 @@
         NodeId id = node.getNodeId();
 
         // check negative set first
-        LockInfo info = (LockInfo) unlockedNodesMap.get(id);
+        XALockInfo info = unlockedNodesMap.get(id);
         if (info != null) {
             // if settings are compatible, this is effectively a no-op
             if (info.deep == isDeep && info.sessionScoped == isSessionScoped) {
@@ -146,7 +148,7 @@
 
         // create a new lock info for this node
         String lockOwner = (ownerInfo != null) ? ownerInfo : node.getSession().getUserID();
-        info = new LockInfo(node, new LockToken(id), isSessionScoped, isDeep, lockOwner);
+        info = new XALockInfo(node, new LockToken(id), isSessionScoped, isDeep, lockOwner);
         SessionImpl session = (SessionImpl) node.getSession();
         info.setLockHolder(session);
         info.setLive(true);
@@ -168,7 +170,7 @@
         NodeId id = node.getNodeId();
 
         // check positive set first
-        AbstractLockInfo info = (LockInfo) lockedNodesMap.get(id);
+        AbstractLockInfo info = lockedNodesMap.get(id);
         if (info != null) {
             lockedNodesMap.remove(id);
             operations.remove(info);
@@ -177,12 +179,12 @@
             info = getLockInfo(node);
             if (info == null || !info.getId().equals(id)) {
                 throw new LockException("Node not locked.");
-            } else if (info.getLockHolder() != node.getSession()) {
+            } else if (!info.isLockHolder(node.getSession())) {
                 throw new LockException("Node not locked by this session.");
             }
-            info = new LockInfo(node, info);
-            unlockedNodesMap.put(id, info);
-            operations.add(info);
+            XALockInfo xaInfo = new XALockInfo(node, info);
+            unlockedNodesMap.put(id, xaInfo);
+            operations.add(xaInfo);
         }
 
     }
@@ -194,8 +196,7 @@
      * @throws RepositoryException if an error occurs
      */
     public boolean isLocked(NodeImpl node) throws RepositoryException {
-        AbstractLockInfo info = getLockInfo(node);
-        return info != null;
+        return getLockInfo(node) != null;
     }
 
     /**
@@ -218,7 +219,7 @@
         if (!lockedNodesMap.isEmpty()) {
             NodeImpl current = node;
             for (;;) {
-                LockInfo info = (LockInfo) lockedNodesMap.get(current.getId());
+                XALockInfo info = lockedNodesMap.get(current.getId());
                 if (info != null) {
                     if (info.getId().equals(id) || info.deep) {
                         return info;
@@ -244,9 +245,10 @@
      */
     public AbstractLockInfo[] getLockInfos(SessionImpl session)
             throws RepositoryException {
-        ArrayList result = new ArrayList();
+    	
+        ArrayList<AbstractLockInfo> result = new ArrayList<AbstractLockInfo>();
 
-        // get lock infos from global lock manager first
+        // get lock informations from global lock manager first
         AbstractLockInfo[] infos = lockMgr.getLockInfos(session);
         for (int i = 0; i < infos.length; i++) {
             AbstractLockInfo info = infos[i];
@@ -256,7 +258,7 @@
             }
         }
 
-        // add 'uncommitted' lock infos
+        // add 'uncommitted' lock informations
         result.addAll(lockedNodesMap.values());
 
         return (AbstractLockInfo[]) result.toArray(new AbstractLockInfo[result.size()]);
@@ -274,7 +276,9 @@
             NodeImpl node = (NodeImpl) session.getItemManager().getItem(lockToken.getId());
             AbstractLockInfo info = getLockInfo(node);
             if (info != null) {
-                if (info.getLockHolder() == null) {
+            	if (info.isLockHolder(session)) {
+            		// nothing to do
+            	} else if (info.getLockHolder() == null) {
                     info.setLockHolder(session);
                 } else {
                     String msg = "Cannot add lock token: lock already held by other session.";
@@ -304,8 +308,10 @@
             NodeImpl node = (NodeImpl) session.getItemManager().getItem(lockToken.getId());
             AbstractLockInfo info = getLockInfo(node);
             if (info != null) {
-                if (session == info.getLockHolder()) {
+            	if (info.isLockHolder(session)) {
                     info.setLockHolder(null);
+            	} else if (info.getLockHolder() == null) {
+            		// nothing to do
                 } else {
                     String msg = "Cannot remove lock token: lock held by other session.";
                     log.warn(msg);
@@ -338,7 +344,7 @@
             try {
                 while (opIndex < operations.size()) {
                     try {
-                        LockInfo info = (LockInfo) operations.get(opIndex);
+                        XALockInfo info = operations.get(opIndex);
                         info.update();
                     } catch (RepositoryException e) {
                         throw new TransactionException("Unable to update.", e);
@@ -349,7 +355,7 @@
                 if (opIndex < operations.size()) {
                     while (opIndex > 0) {
                         try {
-                            LockInfo info = (LockInfo) operations.get(opIndex - 1);
+                            XALockInfo info = operations.get(opIndex - 1);
                             info.undo();
                         } catch (RepositoryException e) {
                             log.error("Unable to undo lock operation.", e);
@@ -392,7 +398,7 @@
             if (!operations.isEmpty()) {
                 while (opIndex > 0) {
                     try {
-                        LockInfo info = (LockInfo) operations.get(opIndex - 1);
+                        XALockInfo info = operations.get(opIndex - 1);
                         info.undo();
                     } catch (RepositoryException e) {
                         log.error("Unable to undo lock operation.", e);
@@ -411,8 +417,8 @@
      * XA environment.
      */
     public boolean differentXAEnv(AbstractLockInfo info) {
-        if (info instanceof LockInfo) {
-            LockInfo lockInfo = (LockInfo) info;
+        if (info instanceof XALockInfo) {
+            XALockInfo lockInfo = (XALockInfo) info;
             return lockInfo.getXAEnv() != this;
         }
         return true;
@@ -421,7 +427,7 @@
     /**
      * Information about a lock used inside transactions.
      */
-    class LockInfo extends AbstractLockInfo {
+    class XALockInfo extends AbstractLockInfo {
 
         /**
          * Node being locked/unlocked.
@@ -440,8 +446,8 @@
          * @param deep          whether lock is deep
          * @param lockOwner     owner of lock
          */
-        public LockInfo(NodeImpl node, LockToken lockToken,
-                        boolean sessionScoped, boolean deep, String lockOwner) {
+        public XALockInfo(NodeImpl node, LockToken lockToken,
+        				  boolean sessionScoped, boolean deep, String lockOwner) {
 
             this(node, lockToken, sessionScoped, deep, lockOwner, TIMEOUT_INFINITE);
         }
@@ -453,9 +459,9 @@
          * @param deep          whether lock is deep
          * @param lockOwner     owner of lock
          */
-        public LockInfo(NodeImpl node, LockToken lockToken,
-                        boolean sessionScoped, boolean deep, String lockOwner,
-                        long timeoutHint) {
+        public XALockInfo(NodeImpl node, LockToken lockToken,
+                          boolean sessionScoped, boolean deep, String lockOwner,
+                          long timeoutHint) {
 
             super(lockToken, sessionScoped, deep, lockOwner, timeoutHint);
             this.node = node;
@@ -465,7 +471,7 @@
          * Create a new instance of this class. Used to signal an
          * unlock operation on some existing lock information.
          */
-        public LockInfo(NodeImpl node, AbstractLockInfo info) {
+        public XALockInfo(NodeImpl node, AbstractLockInfo info) {
             super(info.lockToken, info.sessionScoped, info.deep, info.lockOwner, info.getSecondsRemaining());
 
             this.node = node;

Copied: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockImpl.java
(from r790814, jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALock.java)
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockImpl.java?p2=jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockImpl.java&p1=jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALock.java&r1=790814&r2=790892&rev=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALock.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockImpl.java
Fri Jul  3 13:00:25 2009
@@ -24,21 +24,27 @@
 /**
  * Extension to standard lock implementation that works in XA environment.
  */
-class XALock extends LockImpl {
+class XALockImpl extends LockImpl {
 
     /**
      * XA lock manager.
      */
     private final XALockManager lockMgr;
+    
+    /**
+     * Abstract lock info.
+     */
+    private final AbstractLockInfo info;
 
     /**
      * Create a new instance of this class.
      * @param info lock information
      * @param node node holding lock
      */
-    public XALock(XALockManager lockMgr, AbstractLockInfo info, Node node) {
+    public XALockImpl(XALockManager lockMgr, AbstractLockInfo info, Node node) {
         super(info, node);
 
+        this.info = info;
         this.lockMgr = lockMgr;
     }
 

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockManager.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockManager.java?rev=790892&r1=790891&r2=790892&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockManager.java
(original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/XALockManager.java
Fri Jul  3 13:00:25 2009
@@ -80,7 +80,7 @@
             info = lockMgr.internalLock(node, isDeep, isSessionScoped, timoutHint, ownerInfo);
         }
         lockMgr.writeLockProperties(node, info.lockOwner, info.deep);
-        return new XALock(this, info, node);
+        return new XALockImpl(this, info, node);
     }
 
     /**
@@ -98,7 +98,7 @@
         }
         SessionImpl session = (SessionImpl) node.getSession();
         NodeImpl holder = (NodeImpl) session.getItemManager().getItem(info.getId());
-        return new XALock(this, info, holder);
+        return new XALockImpl(this, info, holder);
     }
 
     /**
@@ -112,12 +112,12 @@
             infos = lockMgr.getLockInfos(session);
         }
 
-        XALock[] locks = new XALock[infos.length];
+        XALockImpl[] locks = new XALockImpl[infos.length];
 
         for (int i = 0; i < infos.length; i++) {
             AbstractLockInfo info = infos[i];
             NodeImpl holder = (NodeImpl) session.getItemManager().getItem(info.getId());
-            locks[i] = new XALock(this, info, holder);
+            locks[i] = new XALockImpl(this, info, holder);
         }
         return locks;
     }
@@ -150,75 +150,83 @@
     /**
      * {@inheritDoc}
      */
-    public boolean isLockHolder(Session session, NodeImpl node)
-            throws RepositoryException {
+    public boolean isLocked(NodeImpl node) throws RepositoryException {
         AbstractLockInfo info;
         if (isInXA()) {
             info = xaEnv.getLockInfo(node);
         } else {
             info = lockMgr.getLockInfo(node.getNodeId());
         }
-        return info != null && info.getId().equals(node.getId())
-                && info.getLockHolder() == session;
+        return info != null;
     }
 
     /**
      * {@inheritDoc}
      */
-    public boolean isLocked(NodeImpl node) throws RepositoryException {
+    public void checkLock(NodeImpl node) throws LockException, RepositoryException {
         AbstractLockInfo info;
         if (isInXA()) {
             info = xaEnv.getLockInfo(node);
+            if (info != null && !info.isLockHolder(node.getSession())) {
+                throw new LockException("Node locked.");
+            }
         } else {
-            info = lockMgr.getLockInfo(node.getNodeId());
+        	lockMgr.checkLock(node);
         }
-        return info != null;
     }
 
     /**
      * {@inheritDoc}
      */
-    public void checkLock(NodeImpl node) throws LockException, RepositoryException {
-        AbstractLockInfo info;
+    public void checkLock(Path path, Session session)
+            throws LockException, RepositoryException {
+
         if (isInXA()) {
-            info = xaEnv.getLockInfo(node);
+	        SessionImpl sessionImpl = (SessionImpl) session;
+	        checkLock(sessionImpl.getItemManager().getNode(path));
         } else {
-            info = lockMgr.getLockInfo(node.getNodeId());
-        }
-        if (info != null && info.getLockHolder() != node.getSession()) {
-            throw new LockException("Node locked.");
+        	lockMgr.checkLock(path, session);
         }
     }
-
+    
     /**
      * {@inheritDoc}
      */
-    public void checkLock(Path path, Session session)
-            throws LockException, RepositoryException {
+    public void checkUnlock(Session session, NodeImpl node)
+    		throws LockException, RepositoryException {
 
-        SessionImpl sessionImpl = (SessionImpl) session;
-        checkLock(sessionImpl.getItemManager().getNode(path));
+        if (isInXA()) {
+            AbstractLockInfo info = xaEnv.getLockInfo(node);
+            if (info == null || !info.getId().equals(node.getId())) {
+    	        throw new LockException("Node not locked: " + node);
+            }
+    	    if (!info.isLockHolder(session)) {
+    	        throw new LockException("Node not locked by session: " + node);
+    	    }
+        } else {
+        	lockMgr.checkUnlock(session, node);
+        }
     }
 
     /**
      * {@inheritDoc}
      */
-    public void lockTokenAdded(SessionImpl session, String lt) throws RepositoryException
{
+    public void addLockToken(SessionImpl session, String lt) throws RepositoryException {
         if (isInXA()) {
             xaEnv.addLockToken(session, lt);
         } else {
-            lockMgr.lockTokenAdded(session, lt);
+            lockMgr.addLockToken(session, lt);
         }
     }
 
     /**
      * {@inheritDoc}
      */
-    public void lockTokenRemoved(SessionImpl session, String lt) throws RepositoryException
{
+    public void removeLockToken(SessionImpl session, String lt) throws RepositoryException
{
         if (isInXA()) {
             xaEnv.removeLockToken(session, lt);
         } else {
-            lockMgr.lockTokenRemoved(session, lt);
+            lockMgr.removeLockToken(session, lt);
         }
     }
 
@@ -293,7 +301,7 @@
         if (isInXA()) {
             return xaEnv.differentXAEnv(info);
         } else {
-            return info instanceof XAEnvironment.LockInfo;
+            return info instanceof XAEnvironment.XALockInfo;
         }
     }
 



Mime
View raw message