You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jackrabbit.apache.org by ju...@apache.org on 2010/08/03 14:03:12 UTC

svn commit: r981833 - in /jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core: ItemImpl.java ItemRefreshOperation.java ItemRemoveOperation.java ProtectedItemModifier.java

Author: jukka
Date: Tue Aug  3 12:03:12 2010
New Revision: 981833

URL: http://svn.apache.org/viewvc?rev=981833&view=rev
Log:
JCR-890: concurrent read-only access to a session

Turn more ItemImpl methods into SessionOperations

Added:
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRemoveOperation.java   (with props)
Modified:
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemImpl.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRefreshOperation.java
    jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ProtectedItemModifier.java

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemImpl.java?rev=981833&r1=981832&r2=981833&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemImpl.java (original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemImpl.java Tue Aug  3 12:03:12 2010
@@ -16,7 +16,6 @@
  */
 package org.apache.jackrabbit.core;
 
-
 import javax.jcr.AccessDeniedException;
 import javax.jcr.InvalidItemStateException;
 import javax.jcr.Item;
@@ -29,13 +28,8 @@ import javax.jcr.RepositoryException;
 import javax.jcr.Session;
 import javax.jcr.Value;
 import javax.jcr.ValueFactory;
-import javax.jcr.lock.LockException;
-import javax.jcr.nodetype.ConstraintViolationException;
-import javax.jcr.version.VersionException;
 
 import org.apache.jackrabbit.core.id.ItemId;
-import org.apache.jackrabbit.core.id.NodeId;
-import org.apache.jackrabbit.core.security.authorization.Permission;
 import org.apache.jackrabbit.core.session.SessionContext;
 import org.apache.jackrabbit.core.session.SessionOperation;
 import org.apache.jackrabbit.core.state.ItemState;
@@ -97,9 +91,10 @@ public abstract class ItemImpl implement
         this.data = data;
     }
 
-    protected void perform(SessionOperation operation)
+    protected <T> T perform(final SessionOperation<T> operation)
             throws RepositoryException {
-        sessionContext.getSessionState().perform(operation);
+        itemSanityCheck();
+        return sessionContext.getSessionState().perform(operation);
     }
 
     /**
@@ -210,49 +205,6 @@ public abstract class ItemImpl implement
     }
 
     /**
-     * Same as <code>{@link Item#remove()}</code> except for the
-     * <code>noChecks</code> parameter.
-     *
-     * @param noChecks
-     * @throws VersionException
-     * @throws LockException
-     * @throws RepositoryException
-     */
-    protected void internalRemove(boolean noChecks)
-            throws VersionException, LockException,
-            ConstraintViolationException, RepositoryException {
-
-        // check state of this instance
-        sanityCheck();
-
-        // check if this is the root node
-        if (getDepth() == 0) {
-            throw new RepositoryException("Cannot remove the root node");
-        }
-
-        NodeImpl parentNode = (NodeImpl) getParent();
-        if (!noChecks) {
-            // check if protected and not under retention/hold
-            int options = ItemValidator.CHECK_CONSTRAINTS | ItemValidator.CHECK_HOLD |
-                    ItemValidator.CHECK_RETENTION;
-            session.getValidator().checkRemove(this, options, Permission.NONE);
-
-            // parent node: make sure it is checked-out and not protected nor locked.
-            options = ItemValidator.CHECK_LOCK | ItemValidator.CHECK_CHECKED_OUT |
-                    ItemValidator.CHECK_CONSTRAINTS;
-            session.getValidator().checkModify(parentNode, options, Permission.NONE);
-        }
-
-        // delegate the removal of the child item to the parent node
-        if (isNode()) {
-            parentNode.removeChildNode((NodeId) getId());
-        } else {
-            Path.Element thisName = getPrimaryPath().getNameElement();
-            parentNode.removeChildProperty(thisName.getName());
-        }
-    }
-
-    /**
      * Same as <code>{@link Item#getName()}</code> except that
      * this method returns a <code>Name</code> instead of a
      * <code>String</code>.
@@ -372,18 +324,14 @@ public abstract class ItemImpl implement
     /**
      * {@inheritDoc}
      */
-    public void remove()
-            throws VersionException, LockException,
-            ConstraintViolationException, RepositoryException {
-        internalRemove(false);
+    public void remove() throws RepositoryException {
+        perform(new ItemRemoveOperation(this, true));
     }
 
     /**
      * {@inheritDoc}
      */
     public void save() throws RepositoryException {
-        // check state of this instance
-        sanityCheck();
         perform(new ItemSaveOperation(getItemState()));
     }
 
@@ -391,71 +339,66 @@ public abstract class ItemImpl implement
      * {@inheritDoc}
      */
     public void refresh(boolean keepChanges) throws RepositoryException {
-        // check state of this instance
-        sanityCheck();
-
-        if (keepChanges) {
-            // FIXME should reset Item#status field to STATUS_NORMAL
-            // of all descendant non-transient instances; maybe also
-            // have to reset stale ItemState instances
-        } else {
-            perform(new ItemRefreshOperation(getItemState()));
-        }
+        perform(new ItemRefreshOperation(getItemState(), keepChanges));
     }
 
     /**
      * {@inheritDoc}
      */
-    public Item getAncestor(int degree)
-            throws ItemNotFoundException, AccessDeniedException, RepositoryException {
-        // check state of this instance
-        sanityCheck();
-
-        if (degree == 0) {
-            return itemMgr.getRootNode();
-        }
+    public Item getAncestor(final int degree) throws RepositoryException {
+        return perform(new SessionOperation<Item>() {
+            public Item perform(SessionContext context)
+                    throws RepositoryException {
+                if (degree == 0) {
+                    return context.getItemManager().getRootNode();
+                }
 
-        try {
-            // Path.getAncestor requires relative degree, i.e. we need
-            // to convert absolute to relative ancestor degree
-            Path path = getPrimaryPath();
-            int relDegree = path.getAncestorCount() - degree;
-            if (relDegree < 0) {
-                throw new ItemNotFoundException();
-            }
-            // shortcut
-            if (relDegree == 0) {
-                return this;
+                try {
+                    // Path.getAncestor requires relative degree, i.e. we need
+                    // to convert absolute to relative ancestor degree
+                    Path path = getPrimaryPath();
+                    int relDegree = path.getAncestorCount() - degree;
+                    if (relDegree < 0) {
+                        throw new ItemNotFoundException();
+                    } else if (relDegree == 0) {
+                        return ItemImpl.this; // shortcut
+                    }
+                    Path ancestorPath = path.getAncestor(relDegree);
+                    return context.getItemManager().getNode(ancestorPath);
+                } catch (PathNotFoundException e) {
+                    throw new ItemNotFoundException("Ancestor not found", e);
+                }
             }
-            Path ancestorPath = path.getAncestor(relDegree);
-            return itemMgr.getNode(ancestorPath);
-        } catch (PathNotFoundException pnfe) {
-            throw new ItemNotFoundException();
-        }
+        });
     }
 
     /**
      * {@inheritDoc}
      */
     public String getPath() throws RepositoryException {
-        // check state of this instance
-        sanityCheck();
-        return session.getJCRPath(getPrimaryPath());
+        return perform(new SessionOperation<String>() {
+            public String perform(SessionContext context)
+                    throws RepositoryException {
+                return context.getSessionImpl().getJCRPath(getPrimaryPath());
+            }
+        });
     }
 
     /**
      * {@inheritDoc}
      */
     public int getDepth() throws RepositoryException {
-        // check state of this instance
-        sanityCheck();
-
-        final ItemState state = getItemState();
-        if (state.getParentId() == null) {
-            // shortcut
-            return 0;
-        }
-        return sessionContext.getHierarchyManager().getDepth(id);
+        return perform(new SessionOperation<Integer>() {
+            public Integer perform(SessionContext context)
+                    throws RepositoryException {
+                ItemState state = getItemState();
+                if (state.getParentId() == null) {
+                    return 0; // shortcut
+                } else {
+                    return context.getHierarchyManager().getDepth(id);
+                }
+            }
+        });
     }
 
     /**

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRefreshOperation.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRefreshOperation.java?rev=981833&r1=981832&r2=981833&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRefreshOperation.java (original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRefreshOperation.java Tue Aug  3 12:03:12 2010
@@ -38,11 +38,21 @@ public class ItemRefreshOperation implem
 
     private final ItemState state;
 
-    public ItemRefreshOperation(ItemState state) {
+    private final boolean keepChanges;
+
+    public ItemRefreshOperation(ItemState state, boolean keepChanges) {
         this.state = state;
+        this.keepChanges = keepChanges;
     }
 
     public Object perform(SessionContext context) throws RepositoryException {
+        if (keepChanges) {
+            // FIXME When keepChanges is true, should reset Item#status field
+            // to STATUS_NORMAL of all descendant non-transient instances;
+            // maybe also have to reset stale ItemState instances
+            return this;
+        }
+
         SessionItemStateManager stateMgr = context.getItemStateManager();
 
         // Optimisation for the root node

Added: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRemoveOperation.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRemoveOperation.java?rev=981833&view=auto
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRemoveOperation.java (added)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ItemRemoveOperation.java Tue Aug  3 12:03:12 2010
@@ -0,0 +1,88 @@
+/*
+ * 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;
+
+import static org.apache.jackrabbit.core.ItemValidator.CHECK_CHECKED_OUT;
+import static org.apache.jackrabbit.core.ItemValidator.CHECK_CONSTRAINTS;
+import static org.apache.jackrabbit.core.ItemValidator.CHECK_HOLD;
+import static org.apache.jackrabbit.core.ItemValidator.CHECK_LOCK;
+import static org.apache.jackrabbit.core.ItemValidator.CHECK_RETENTION;
+
+import javax.jcr.RepositoryException;
+
+import org.apache.jackrabbit.core.id.NodeId;
+import org.apache.jackrabbit.core.security.authorization.Permission;
+import org.apache.jackrabbit.core.session.SessionContext;
+import org.apache.jackrabbit.core.session.SessionOperation;
+import org.apache.jackrabbit.spi.Path;
+
+/**
+ * Session operation for removing a given item, optionally with constraint
+ * checks enabled.
+ */
+class ItemRemoveOperation implements SessionOperation<Object> {
+
+    /**
+     * The item to be removed.
+     */
+    private final ItemImpl item;
+
+    /**
+     * Flag to enabled constraint checks
+     */
+    private final boolean checks;
+
+    public ItemRemoveOperation(ItemImpl item, boolean checks) {
+        this.item = item;
+        this.checks = checks;
+    }
+
+    public Object perform(SessionContext context)
+            throws RepositoryException {
+        // check if this is the root node
+        if (item.getDepth() == 0) {
+            throw new RepositoryException("Cannot remove the root node");
+        }
+
+        NodeImpl parentNode = (NodeImpl) item.getParent();
+        if (checks) {
+            ItemValidator validator = context.getItemValidator();
+            validator.checkRemove(
+                    item,
+                    CHECK_CONSTRAINTS | CHECK_HOLD | CHECK_RETENTION,
+                    Permission.NONE);
+
+            // Make sure the parent node is checked-out and
+            // neither protected nor locked.
+            validator.checkModify(
+                    parentNode,
+                    CHECK_LOCK | CHECK_CHECKED_OUT | CHECK_CONSTRAINTS,
+                    Permission.NONE);
+        }
+
+        // delegate the removal of the child item to the parent node
+        if (item.isNode()) {
+            parentNode.removeChildNode((NodeId) item.getId());
+        } else {
+            Path.Element thisName = item.getPrimaryPath().getNameElement();
+            parentNode.removeChildProperty(thisName.getName());
+        }
+
+        return this;
+    }
+
+}
\ No newline at end of file

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

Modified: jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ProtectedItemModifier.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ProtectedItemModifier.java?rev=981833&r1=981832&r2=981833&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ProtectedItemModifier.java (original)
+++ jackrabbit/trunk/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/ProtectedItemModifier.java Tue Aug  3 12:03:12 2010
@@ -142,7 +142,7 @@ public abstract class ProtectedItemModif
         checkPermission(itemImpl, getPermission(itemImpl.isNode(), true));
         // validation: make sure Node is not locked or checked-in.
         n.checkSetProperty();
-        itemImpl.internalRemove(true);
+        itemImpl.perform(new ItemRemoveOperation(itemImpl, false));
     }
 
     protected void markModified(NodeImpl parentImpl) throws RepositoryException {