From 29c3c463b862d2b9d91cc66e71af031aa532e77a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Uwe=20J=C3=A4ger?= Date: Thu, 31 Mar 2011 21:45:17 +0200 Subject: [PATCH] Implement JCR-2454 registerNodeTypes via DAVEX This implements registration of node types via DAVEX remoting. The client create a CND version of the node type definition and passes this on to the server that parses the cnd and registers the node type --- .../commons/webdav/JcrRemotingConstants.java | 1 + .../webdav/jcr/ItemResourceConstants.java | 1 + .../webdav/jcr/WorkspaceResourceImpl.java | 24 +++++++++++++++-- .../jackrabbit/spi2dav/RepositoryServiceImpl.java | 27 ++++++++++++++++++- 4 files changed, 48 insertions(+), 5 deletions(-) diff --git a/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java b/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java index 95ef57d..11fb733 100644 --- a/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java +++ b/jackrabbit-jcr-commons/src/main/java/org/apache/jackrabbit/commons/webdav/JcrRemotingConstants.java @@ -126,6 +126,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"; diff --git a/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java b/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java index 175dcde..d8acbe9 100644 --- a/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java +++ b/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/ItemResourceConstants.java @@ -84,6 +84,7 @@ public interface ItemResourceConstants extends JcrRemotingConstants { // 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); diff --git a/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java b/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java index 9b6fa89..bc7aba5 100644 --- a/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java +++ b/jackrabbit-jcr-server/src/main/java/org/apache/jackrabbit/webdav/jcr/WorkspaceResourceImpl.java @@ -18,6 +18,8 @@ package org.apache.jackrabbit.webdav.jcr; import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import org.apache.jackrabbit.commons.cnd.CndImporter; +import org.apache.jackrabbit.commons.cnd.ParseException; import org.apache.jackrabbit.webdav.version.WorkspaceResource; import org.apache.jackrabbit.webdav.version.DeltaVResource; import org.apache.jackrabbit.webdav.version.UpdateInfo; @@ -61,6 +63,7 @@ import java.util.Collections; import java.io.IOException; import java.io.PrintWriter; import java.io.OutputStreamWriter; +import java.io.StringReader; /** * WorkspaceResourceImpl... @@ -239,8 +242,10 @@ public class WorkspaceResourceImpl extends AbstractResource } /** - * Allows to alter the registered namespaces ({@link ItemResourceConstants#JCR_NAMESPACES}) and - * forwards any other property to the super class.

+ * 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.

* Note that again no property status is set. Any failure while setting * a property results in an exception (violating RFC 2518). * @@ -274,6 +279,18 @@ public class WorkspaceResourceImpl extends AbstractResource } catch (RepositoryException e) { throw new JcrDavException(e); } + } else if (ItemResourceConstants.JCR_NODETYPES_CND.equals(property.getName())) { + try { + StringReader reader =new StringReader(property.getValue().toString()); + CndImporter.registerNodeTypes(reader, getRepositorySession(), true); + } catch (IOException e) { + throw new DavException(DavServletResponse.SC_INTERNAL_SERVER_ERROR, e); + } 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 throw new DavException(DavServletResponse.SC_CONFLICT); @@ -293,7 +310,8 @@ public class WorkspaceResourceImpl extends AbstractResource 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 { diff --git a/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java b/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java index 6074779..999ff8d 100644 --- a/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java +++ b/jackrabbit-spi2dav/src/main/java/org/apache/jackrabbit/spi2dav/RepositoryServiceImpl.java @@ -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.conversion.PathResolver; 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; @@ -2236,8 +2239,28 @@ public class RepositoryServiceImpl implements RepositoryService, DavConstants { * {@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 { + StringWriter sw = new StringWriter(); + CompactNodeTypeDefWriter writer = new CompactNodeTypeDefWriter(sw, new NamespaceResolverImpl(sessionInfo), true); + writer.write(Arrays.asList(nodeTypeDefinitions)); + writer.close(); + DavPropertySet setProperties = new DavPropertySet(); + setProperties.add(new DefaultDavProperty(JcrRemotingConstants.JCR_NODETYPES_CND_LN, sw.toString(), ItemResourceConstants.NAMESPACE, false)); + 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(); + } + } } /** -- 1.7.4