You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jackrabbit.apache.org by an...@apache.org on 2011/04/14 18:48:43 UTC

svn commit: r1092393 - in /jackrabbit/trunk: jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/ jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ jackrabbit-jcr2dav/ jackrabbit-jcr2spi/src/test/java/org/apach...

Author: angela
Date: Thu Apr 14 16:48:42 2011
New Revision: 1092393

URL: http://svn.apache.org/viewvc?rev=1092393&view=rev
Log:
JCR-2454 : spi2dav: JSR 283 NodeType Management

Added:
    jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java   (with props)
Modified:
    jackrabbit/trunk/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java
    jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java
    jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java
    jackrabbit/trunk/jackrabbit-jcr2dav/pom.xml
    jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/TestAll.java
    jackrabbit/trunk/jackrabbit-spi2dav/pom.xml
    jackrabbit/trunk/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java

Modified: jackrabbit/trunk/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java (original)
+++ jackrabbit/trunk/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java Thu Apr 14 16:48:42 2011
@@ -73,6 +73,11 @@ public interface JcrRemotingConstants {
     public static final String XML_DESCRIPTORKEY = "descriptorkey";
     public static final String XML_DESCRIPTORVALUE = "descriptorvalue";
 
+    // xml elements used for node type registration
+    public static final String XML_CND = "cnd";
+    public static final String XML_ALLOWUPDATE = "allowupdate";
+    public static final String XML_NODETYPENAME = "nodetypename";
+
     /**
      * The 'removeexisting' element is not defined by RFC 3253. If it is present
      * in the UPDATE request body, uuid conflicts should be solved by removing
@@ -126,6 +131,7 @@ public interface JcrRemotingConstants {
     public static final String JCR_LENGTHS_LN = "lengths";
 
     public static final String JCR_NAMESPACES_LN = "namespaces";
+    public static final String JCR_NODETYPES_CND_LN = "nodetypes-cnd";
 
     // property local names used for resource representing a version history
     public static final String JCR_VERSIONABLEUUID_LN = "versionableuuid";

Modified: jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java (original)
+++ jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java Thu Apr 14 16:48:42 2011
@@ -84,6 +84,7 @@ public interface ItemResourceConstants e
 
     // property names used for resource representing a workspace
     public static final DavPropertyName JCR_NAMESPACES = DavPropertyName.create(JCR_NAMESPACES_LN, NAMESPACE);
+    public static final DavPropertyName JCR_NODETYPES_CND = DavPropertyName.create(JCR_NODETYPES_CND_LN, NAMESPACE);
 
     // property names used for resource representing a version history
     public static final DavPropertyName JCR_VERSIONABLEUUID = DavPropertyName.create(JCR_VERSIONABLEUUID_LN, NAMESPACE);

Modified: jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java (original)
+++ jackrabbit/trunk/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java Thu Apr 14 16:48:42 2011
@@ -16,51 +16,59 @@
  */
 package org.apache.jackrabbit.webdav.jcr;
 
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.apache.jackrabbit.webdav.version.WorkspaceResource;
-import org.apache.jackrabbit.webdav.version.DeltaVResource;
-import org.apache.jackrabbit.webdav.version.UpdateInfo;
-import org.apache.jackrabbit.webdav.version.VersionControlledResource;
-import org.apache.jackrabbit.webdav.version.MergeInfo;
-import org.apache.jackrabbit.webdav.version.LabelInfo;
-import org.apache.jackrabbit.webdav.version.VersionHistoryResource;
-import org.apache.jackrabbit.webdav.DavResource;
+import org.apache.jackrabbit.commons.cnd.CompactNodeTypeDefReader;
+import org.apache.jackrabbit.commons.cnd.DefinitionBuilderFactory;
+import org.apache.jackrabbit.commons.cnd.ParseException;
+import org.apache.jackrabbit.commons.cnd.TemplateBuilderFactory;
 import org.apache.jackrabbit.webdav.DavException;
+import org.apache.jackrabbit.webdav.DavMethods;
+import org.apache.jackrabbit.webdav.DavResource;
+import org.apache.jackrabbit.webdav.DavResourceFactory;
 import org.apache.jackrabbit.webdav.DavResourceIterator;
+import org.apache.jackrabbit.webdav.DavResourceIteratorImpl;
 import org.apache.jackrabbit.webdav.DavResourceLocator;
-import org.apache.jackrabbit.webdav.MultiStatusResponse;
 import org.apache.jackrabbit.webdav.DavServletResponse;
-import org.apache.jackrabbit.webdav.DavResourceIteratorImpl;
-import org.apache.jackrabbit.webdav.DavResourceFactory;
 import org.apache.jackrabbit.webdav.MultiStatus;
-import org.apache.jackrabbit.webdav.DavMethods;
-import org.apache.jackrabbit.webdav.xml.DomUtil;
-import org.apache.jackrabbit.webdav.search.SearchResource;
+import org.apache.jackrabbit.webdav.MultiStatusResponse;
+import org.apache.jackrabbit.webdav.io.InputContext;
+import org.apache.jackrabbit.webdav.io.OutputContext;
 import org.apache.jackrabbit.webdav.jcr.property.NamespacesProperty;
 import org.apache.jackrabbit.webdav.jcr.version.report.JcrPrivilegeReport;
 import org.apache.jackrabbit.webdav.property.DavProperty;
 import org.apache.jackrabbit.webdav.property.PropEntry;
-import org.apache.jackrabbit.webdav.io.InputContext;
-import org.apache.jackrabbit.webdav.io.OutputContext;
+import org.apache.jackrabbit.webdav.search.SearchResource;
+import org.apache.jackrabbit.webdav.version.DeltaVResource;
+import org.apache.jackrabbit.webdav.version.LabelInfo;
+import org.apache.jackrabbit.webdav.version.MergeInfo;
+import org.apache.jackrabbit.webdav.version.UpdateInfo;
+import org.apache.jackrabbit.webdav.version.VersionControlledResource;
+import org.apache.jackrabbit.webdav.version.VersionHistoryResource;
+import org.apache.jackrabbit.webdav.version.WorkspaceResource;
+import org.apache.jackrabbit.webdav.xml.DomUtil;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 import org.w3c.dom.Element;
 
+import javax.jcr.Item;
 import javax.jcr.NamespaceRegistry;
+import javax.jcr.Repository;
 import javax.jcr.RepositoryException;
-import javax.jcr.Workspace;
-import javax.jcr.Item;
 import javax.jcr.Session;
-import javax.jcr.Repository;
-import javax.jcr.version.Version;
+import javax.jcr.Workspace;
+import javax.jcr.nodetype.NodeTypeManager;
+import javax.jcr.nodetype.NodeTypeTemplate;
 import javax.jcr.observation.EventListener;
-import java.util.List;
-import java.util.Date;
-import java.util.Map;
-import java.util.HashMap;
-import java.util.Collections;
+import javax.jcr.version.Version;
 import java.io.IOException;
-import java.io.PrintWriter;
 import java.io.OutputStreamWriter;
+import java.io.PrintWriter;
+import java.io.StringReader;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
 
 /**
  * <code>WorkspaceResourceImpl</code>...
@@ -240,8 +248,10 @@ public class WorkspaceResourceImpl exten
     }
 
     /**
-     * Allows to alter the registered namespaces ({@link ItemResourceConstants#JCR_NAMESPACES}) and
-     * forwards any other property to the super class.<p/>
+     * Allows to alter the registered namespaces ({@link ItemResourceConstants#JCR_NAMESPACES})
+     * or register node types ({@link ItemResourceConstants#JCR_NODETYPES_CND)
+     * where the passed value is a cnd string containing the definition
+     * and forwards any other property to the super class.<p/>
      * Note that again no property status is set. Any failure while setting
      * a property results in an exception (violating RFC 2518).
      *
@@ -275,8 +285,63 @@ public class WorkspaceResourceImpl exten
             } catch (RepositoryException e) {
                 throw new JcrDavException(e);
             }
+        } else if (ItemResourceConstants.JCR_NODETYPES_CND.equals(property.getName())) {
+            try {
+                Object value = property.getValue();
+                List<?> cmds;
+                if (value instanceof List) {
+                    cmds = (List) value;
+                } else  if (value instanceof Element) {
+                    cmds = Collections.singletonList(value);
+                } else {
+                    log.warn("Unexpected structure of dcr:nodetypes-cnd property.");
+                    throw new DavException(DavServletResponse.SC_INTERNAL_SERVER_ERROR);
+                }
+
+                String registerCnd = null;
+                boolean allowUpdate = false;
+                List<String> unregisterNames = new ArrayList<String>();
+
+                for (Object listEntry : cmds) {
+                    if (listEntry instanceof Element) {
+                        Element e = (Element) listEntry;
+                        String localName = e.getLocalName();
+                        if (ItemResourceConstants.XML_CND.equals(localName)) {
+                            registerCnd = DomUtil.getText(e);
+                        } else if (ItemResourceConstants.XML_ALLOWUPDATE.equals(localName)) {
+                            String allow = DomUtil.getTextTrim(e);
+                            allowUpdate = Boolean.parseBoolean(allow);
+                        } else if (ItemResourceConstants.XML_NODETYPENAME.equals(localName)) {
+                            unregisterNames.add(DomUtil.getTextTrim(e));
+                        }
+                    }
+                }
+
+                // TODO: for simplicity it's currently it's either registration or unregistration as nt-modifications are immediately persisted.
+                Session s = getRepositorySession();
+                NodeTypeManager ntMgr = s.getWorkspace().getNodeTypeManager();
+                if (registerCnd != null) {
+                    StringReader reader = new StringReader(registerCnd);
+                    DefinitionBuilderFactory<NodeTypeTemplate, NamespaceRegistry> factory =
+                            new TemplateBuilderFactory(ntMgr, s.getValueFactory(), s.getWorkspace().getNamespaceRegistry());
+
+                    CompactNodeTypeDefReader<NodeTypeTemplate, NamespaceRegistry> cndReader =
+                            new CompactNodeTypeDefReader<NodeTypeTemplate, NamespaceRegistry>(reader, "davex", factory);
+
+                    List<NodeTypeTemplate> ntts = cndReader.getNodeTypeDefinitions();
+                    ntMgr.registerNodeTypes(ntts.toArray(new NodeTypeTemplate[ntts.size()]), allowUpdate);
+                } else if (!unregisterNames.isEmpty()) {
+                    ntMgr.unregisterNodeTypes(unregisterNames.toArray(new String[unregisterNames.size()]));
+                }
+                
+            } catch (ParseException e) {
+                throw new DavException(DavServletResponse.SC_BAD_REQUEST, e);
+            }
+            catch (RepositoryException e) {
+                throw new JcrDavException(e);
+            }
         } else {
-            // only jcr:namespace can be modified
+            // only jcr:namespace or node types can be modified
             throw new DavException(DavServletResponse.SC_CONFLICT);
         }
     }
@@ -294,7 +359,8 @@ public class WorkspaceResourceImpl exten
            PropEntry propEntry = changeList.get(0);
             // only modification of prop is allowed. removal is not possible
             if (propEntry instanceof DavProperty
-                && ItemResourceConstants.JCR_NAMESPACES.equals(((DavProperty<?>)propEntry).getName())) {
+                    && (ItemResourceConstants.JCR_NAMESPACES.equals(((DavProperty<?>)propEntry).getName())
+                    || ItemResourceConstants.JCR_NODETYPES_CND.equals(((DavProperty<?>)propEntry).getName()))) {
                 DavProperty<?> namespaceProp = (DavProperty<?>) propEntry;
                 setProperty(namespaceProp);
             } else {
@@ -456,5 +522,6 @@ public class WorkspaceResourceImpl exten
         }
 
         // TODO: required property DAV:workspace-checkout-set (computed)
+        // TODO: create node type cnd property only if explicitly requested (see JCR-2946 and patch at JCR-2454) 
     }
 }

Modified: jackrabbit/trunk/jackrabbit-jcr2dav/pom.xml
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr2dav/pom.xml?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr2dav/pom.xml (original)
+++ jackrabbit/trunk/jackrabbit-jcr2dav/pom.xml Thu Apr 14 16:48:42 2011
@@ -64,9 +64,6 @@
                       org.apache.jackrabbit.test.api.lock.LockManagerTest#testAddLockTokenToAnotherSession
                       org.apache.jackrabbit.test.api.lock.LockManagerTest#testLockTransfer2
                       org.apache.jackrabbit.jcr2spi.lock.OpenScopedLockTest#testLogoutHasNoEffect 
-                      <!-- JCR-2454 : node type registration -->
-                      org.apache.jackrabbit.test.api.nodetype.NodeTypeCreationTest#testRegisterNodeType
-                      org.apache.jackrabbit.test.api.nodetype.NodeTypeCreationTest#testRegisterNodeTypes
                       <!-- JCR-2539 : user data (observation) -->
                       org.apache.jackrabbit.test.api.observation.GetUserDataTest
                       <!-- JCR-2540 : move/reorder (observation) -->

Added: jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java?rev=1092393&view=auto
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java (added)
+++ jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java Thu Apr 14 16:48:42 2011
@@ -0,0 +1,114 @@
+/*
+ * 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.jcr2spi.nodetype;
+
+import org.apache.jackrabbit.test.AbstractJCRTest;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.jcr.RepositoryException;
+import javax.jcr.UnsupportedRepositoryOperationException;
+import javax.jcr.nodetype.NoSuchNodeTypeException;
+import javax.jcr.nodetype.NodeType;
+import javax.jcr.nodetype.NodeTypeExistsException;
+import javax.jcr.nodetype.NodeTypeManager;
+import javax.jcr.nodetype.NodeTypeTemplate;
+
+/**
+ * <code>NodeTypeManagerImplTest</code>...
+ */
+public class NodeTypeManagerImplTest extends AbstractJCRTest {
+
+    /**
+     * logger instance
+     */
+    private static final Logger log = LoggerFactory.getLogger(NodeTypeManagerImplTest.class);
+
+    private NodeTypeManager ntMgr;
+
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+
+        ntMgr = superuser.getWorkspace().getNodeTypeManager();
+    }
+
+    public void testRegisterNodeTypes() throws RepositoryException {
+        NodeTypeTemplate test = ntMgr.createNodeTypeTemplate();
+        test.setName("testNodeType");
+
+        ntMgr.registerNodeType(test, true);
+
+        NodeType nt = ntMgr.getNodeType("testNodeType");
+        assertNotNull(nt);
+        assertEquals("testNodeType", nt.getName());
+
+        test.setOrderableChildNodes(true);
+
+        ntMgr.registerNodeType(test, true);
+
+        nt = ntMgr.getNodeType("testNodeType");
+        assertNotNull(nt);
+        assertEquals("testNodeType", nt.getName());
+        assertEquals(test.hasOrderableChildNodes(), nt.hasOrderableChildNodes());
+
+        test.setDeclaredSuperTypeNames(new String[] {"nt:unstructured"});
+
+        try {
+            ntMgr.registerNodeType(test, false);
+            fail("NodeTypeExistsException expected");
+        } catch (NodeTypeExistsException e) {
+            // success
+        }
+    }
+    
+    public void testUnregisterNodeTypes() throws RepositoryException {
+        NodeTypeTemplate test = ntMgr.createNodeTypeTemplate();
+        test.setName("testNodeType2");
+
+        ntMgr.registerNodeType(test, true);
+
+        NodeType nt = ntMgr.getNodeType("testNodeType2");
+        assertNotNull(nt);
+        assertEquals("testNodeType2", nt.getName());
+
+        boolean supported = false;
+        try {
+            ntMgr.unregisterNodeType(test.getName());
+            supported = true;
+        } catch (UnsupportedRepositoryOperationException e) {
+            // ok
+        } catch (RepositoryException e) {
+            // TODO improve
+            if (e.getMessage().contains("not yet implemented")) {
+                // ok (original message in jr-core)
+            } else {
+                throw e;
+            }
+
+        }
+
+        if (supported) {
+            try {
+                ntMgr.getNodeType("testNodeType2");
+                fail("should not be available any more");
+            } catch (NoSuchNodeTypeException e) {
+                // success
+            }
+        }
+    }
+}
\ No newline at end of file

Propchange: jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/NodeTypeManagerImplTest.java
------------------------------------------------------------------------------
    svn:keywords = Author Date Id Revision Rev URL

Modified: jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/TestAll.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/TestAll.java?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/TestAll.java (original)
+++ jackrabbit/trunk/jackrabbit-jcr2spi/src/test/java/org/apache/jackrabbit/jcr2spi/nodetype/TestAll.java Thu Apr 14 16:48:42 2011
@@ -33,6 +33,7 @@ public class TestAll extends TestCase {
         suite.addTestSuite(MandatoryItemTest.class);
 
         suite.addTestSuite(NodeTypeImplTest.class);
+        suite.addTestSuite(NodeTypeManagerImplTest.class);
 
         return suite;
     }

Modified: jackrabbit/trunk/jackrabbit-spi2dav/pom.xml
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-spi2dav/pom.xml?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-spi2dav/pom.xml (original)
+++ jackrabbit/trunk/jackrabbit-spi2dav/pom.xml Thu Apr 14 16:48:42 2011
@@ -61,9 +61,6 @@
                   org.apache.jackrabbit.test.api.lock.LockManagerTest#testAddInvalidLockToken
                   org.apache.jackrabbit.test.api.lock.LockManagerTest#testAddLockTokenToAnotherSession
                   org.apache.jackrabbit.test.api.lock.LockManagerTest#testLockTransfer2
-                  <!-- JCR-2454 : node type registration -->
-                  org.apache.jackrabbit.test.api.nodetype.NodeTypeCreationTest#testRegisterNodeType
-                  org.apache.jackrabbit.test.api.nodetype.NodeTypeCreationTest#testRegisterNodeTypes
                   <!-- JCR-2539 : user data (observation) -->
                   org.apache.jackrabbit.test.api.observation.GetUserDataTest
                   <!-- JCR-2540 : move/reorder (observation) -->

Modified: jackrabbit/trunk/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/trunk/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java?rev=1092393&r1=1092392&r2=1092393&view=diff
==============================================================================
--- jackrabbit/trunk/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java (original)
+++ jackrabbit/trunk/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java Thu Apr 14 16:48:42 2011
@@ -20,8 +20,10 @@ import java.io.IOException;
 import java.io.InputStream;
 import java.io.InputStreamReader;
 import java.io.Reader;
+import java.io.StringWriter;
 import java.io.UnsupportedEncodingException;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collection;
 import java.util.Collections;
 import java.util.HashMap;
@@ -119,6 +121,7 @@ import org.apache.jackrabbit.spi.commons
 import org.apache.jackrabbit.spi.commons.name.NameConstants;
 import org.apache.jackrabbit.spi.commons.namespace.AbstractNamespaceResolver;
 import org.apache.jackrabbit.spi.commons.namespace.NamespaceResolver;
+import org.apache.jackrabbit.spi.commons.nodetype.compact.CompactNodeTypeDefWriter;
 import org.apache.jackrabbit.spi.commons.value.QValueValue;
 import org.apache.jackrabbit.spi.commons.value.ValueFactoryQImpl;
 import org.apache.jackrabbit.spi.commons.value.ValueFormat;
@@ -2240,16 +2243,48 @@ public class RepositoryServiceImpl imple
      * {@inheritDoc}
      */
     public void registerNodeTypes(SessionInfo sessionInfo, QNodeTypeDefinition[] nodeTypeDefinitions, boolean allowUpdate) throws InvalidNodeTypeDefinitionException, NodeTypeExistsException, UnsupportedRepositoryOperationException, RepositoryException {
-        // TODO
-        throw new UnsupportedOperationException("JCR-2003. Implementation missing");
+        PropPatchMethod method = null;
+     	try {
+             DavPropertySet setProperties = new DavPropertySet();
+             setProperties.add(createRegisterNodeTypesProperty(sessionInfo, nodeTypeDefinitions, allowUpdate));
+             String uri = uriResolver.getWorkspaceUri(sessionInfo.getWorkspaceName());
+             method = new PropPatchMethod(uri, setProperties, new DavPropertyNameSet());
+             initMethod(method, sessionInfo, true);
+             getClient(sessionInfo).executeMethod(method);
+             method.checkSuccess();
+         } catch (IOException e) {
+             throw new RepositoryException(e);
+         } catch (DavException e) {
+             throw ExceptionConverter.generate(e);
+         } finally {
+             if (method != null) {
+                 method.releaseConnection();
+             }
+         }
     }
 
     /**
      * {@inheritDoc}
      */
     public void unregisterNodeTypes(SessionInfo sessionInfo, Name[] nodeTypeNames) throws UnsupportedRepositoryOperationException, NoSuchNodeTypeException, RepositoryException {
-        // TODO
-        throw new UnsupportedOperationException("JCR-2003. Implementation missing");
+        PropPatchMethod method = null;
+     	try {
+             DavPropertySet setProperties = new DavPropertySet();
+             setProperties.add(createUnRegisterNodeTypesProperty(sessionInfo, nodeTypeNames));
+             String uri = uriResolver.getWorkspaceUri(sessionInfo.getWorkspaceName());
+             method = new PropPatchMethod(uri, setProperties, new DavPropertyNameSet());
+             initMethod(method, sessionInfo, true);
+             getClient(sessionInfo).executeMethod(method);
+             method.checkSuccess();
+         } catch (IOException e) {
+             throw new RepositoryException(e);
+         } catch (DavException e) {
+             throw ExceptionConverter.generate(e);
+         } finally {
+             if (method != null) {
+                 method.releaseConnection();
+             }
+         }
     }
 
     /**
@@ -2293,6 +2328,51 @@ public class RepositoryServiceImpl imple
             return ntDefs.iterator();
     }
 
+    private DavProperty<List<XmlSerializable>> createRegisterNodeTypesProperty(SessionInfo sessionInfo, QNodeTypeDefinition[] nodeTypeDefinitions, final boolean allowUpdate) throws IOException {
+        // create xml elements for both cnd and allow update value.
+        List<XmlSerializable> val = new ArrayList<XmlSerializable>();
+
+        StringWriter sw = new StringWriter();
+        CompactNodeTypeDefWriter writer = new CompactNodeTypeDefWriter(sw, new NamespaceResolverImpl(sessionInfo), true);
+        writer.write(Arrays.asList(nodeTypeDefinitions));
+        writer.close();
+
+        final String cnd = sw.toString();
+        val.add(new XmlSerializable() {
+            public Element toXml(Document document) {
+                Element cndElem = document.createElementNS(JcrRemotingConstants.NS_URI, JcrRemotingConstants.NS_PREFIX +  ":" + JcrRemotingConstants.XML_CND);
+                DomUtil.setText(cndElem, cnd);
+                return cndElem;
+            }
+        });
+        val.add(new XmlSerializable() {
+            public Element toXml(Document document) {
+                Element allowElem = document.createElementNS(JcrRemotingConstants.NS_URI, JcrRemotingConstants.NS_PREFIX  + ":" + JcrRemotingConstants.XML_ALLOWUPDATE);
+                DomUtil.setText(allowElem, Boolean.toString(allowUpdate));
+                return allowElem;
+            }
+        });
+
+        return new DefaultDavProperty<List<XmlSerializable>>(JcrRemotingConstants.JCR_NODETYPES_CND_LN, val, ItemResourceConstants.NAMESPACE, false);
+    }
+
+    private DavProperty<List<XmlSerializable>> createUnRegisterNodeTypesProperty(SessionInfo sessionInfo, Name[] nodeTypeNames) throws IOException, RepositoryException {
+        NamePathResolver resolver = getNamePathResolver(sessionInfo);
+        List<XmlSerializable> val = new ArrayList<XmlSerializable>();
+        for (Name ntName : nodeTypeNames) {
+            final String jcrName = resolver.getJCRName(ntName);
+            val.add(new XmlSerializable() {
+                public Element toXml(Document document) {
+                    Element ntNameElem = document.createElementNS(JcrRemotingConstants.NS_URI, JcrRemotingConstants.NS_PREFIX + ":" + JcrRemotingConstants.XML_NODETYPENAME);
+                    org.w3c.dom.Text txt = document.createTextNode(jcrName);
+                    ntNameElem.appendChild(txt);
+                    return ntNameElem;
+                }
+            });
+        }
+        return new DefaultDavProperty<List<XmlSerializable>>(JcrRemotingConstants.JCR_NODETYPES_CND_LN, val, ItemResourceConstants.NAMESPACE, false);
+    }
+
     private static DavProperty<List<XmlSerializable>> createValuesProperty(Value[] jcrValues) {
         // convert the specified jcr values to a xml-serializable value
         List<XmlSerializable> val = new ArrayList<XmlSerializable>();