You are viewing a plain text version of this content. The canonical link for it is here.
Posted to oak-commits@jackrabbit.apache.org by ju...@apache.org on 2013/05/02 22:39:20 UTC

svn commit: r1478519 - in /jackrabbit/oak/trunk/oak-run/src: main/java/org/apache/jackrabbit/core/PersistenceCopier.java main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java

Author: jukka
Date: Thu May  2 20:39:19 2013
New Revision: 1478519

URL: http://svn.apache.org/r1478519
Log:
OAK-806: Content migration from Jackrabbit to Oak

Fixed node type migration code. Added a simple test case.

Added:
    jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java   (with props)
Modified:
    jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/PersistenceCopier.java
    jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java

Modified: jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/PersistenceCopier.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/PersistenceCopier.java?rev=1478519&r1=1478518&r2=1478519&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/PersistenceCopier.java (original)
+++ jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/PersistenceCopier.java Thu May  2 20:39:19 2013
@@ -152,7 +152,6 @@ class PersistenceCopier {
                 if (!exclude.contains(childId)) {
                     exclude.add(childId);
                     String name = getOakName(entry.getName());
-                    System.out.println(name);
                     copy(childId, builder.child(name));
                     exclude.remove(childId);
                 }
@@ -192,7 +191,6 @@ class PersistenceCopier {
             InternalValue[] values = sourceState.getValues();
             int type = sourceState.getType();
             String oakName = getOakName(name);
-            System.out.println("- " + oakName);
             if (sourceState.isMultiValued() || values.length != 1) {
                 builder.setProperty(getProperty(oakName, values, type));
             } else {

Modified: jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java?rev=1478519&r1=1478518&r2=1478519&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java (original)
+++ jackrabbit/oak/trunk/oak-run/src/main/java/org/apache/jackrabbit/core/RepositoryUpgrade.java Thu May  2 20:39:19 2013
@@ -16,10 +16,11 @@
  */
 package org.apache.jackrabbit.core;
 
-import static com.google.common.collect.Lists.newArrayList;
 import static com.google.common.collect.Lists.newArrayListWithCapacity;
 import static java.util.Arrays.asList;
 import static org.apache.jackrabbit.JcrConstants.JCR_AUTOCREATED;
+import static org.apache.jackrabbit.JcrConstants.JCR_CHILDNODEDEFINITION;
+import static org.apache.jackrabbit.JcrConstants.JCR_DEFAULTPRIMARYTYPE;
 import static org.apache.jackrabbit.JcrConstants.JCR_HASORDERABLECHILDNODES;
 import static org.apache.jackrabbit.JcrConstants.JCR_ISMIXIN;
 import static org.apache.jackrabbit.JcrConstants.JCR_MANDATORY;
@@ -31,11 +32,14 @@ import static org.apache.jackrabbit.JcrC
 import static org.apache.jackrabbit.JcrConstants.JCR_PRIMARYTYPE;
 import static org.apache.jackrabbit.JcrConstants.JCR_PROPERTYDEFINITION;
 import static org.apache.jackrabbit.JcrConstants.JCR_PROTECTED;
+import static org.apache.jackrabbit.JcrConstants.JCR_REQUIREDPRIMARYTYPES;
 import static org.apache.jackrabbit.JcrConstants.JCR_REQUIREDTYPE;
+import static org.apache.jackrabbit.JcrConstants.JCR_SAMENAMESIBLINGS;
 import static org.apache.jackrabbit.JcrConstants.JCR_SUPERTYPES;
 import static org.apache.jackrabbit.JcrConstants.JCR_SYSTEM;
 import static org.apache.jackrabbit.JcrConstants.JCR_VALUECONSTRAINTS;
 import static org.apache.jackrabbit.JcrConstants.JCR_VERSIONSTORAGE;
+import static org.apache.jackrabbit.JcrConstants.NT_CHILDNODEDEFINITION;
 import static org.apache.jackrabbit.JcrConstants.NT_NODETYPE;
 import static org.apache.jackrabbit.JcrConstants.NT_PROPERTYDEFINITION;
 import static org.apache.jackrabbit.oak.api.Type.NAME;
@@ -47,10 +51,12 @@ import static org.apache.jackrabbit.oak.
 import static org.apache.jackrabbit.oak.plugins.nodetype.NodeTypeConstants.JCR_IS_QUERYABLE;
 import static org.apache.jackrabbit.oak.plugins.nodetype.NodeTypeConstants.JCR_IS_QUERY_ORDERABLE;
 import static org.apache.jackrabbit.oak.plugins.nodetype.NodeTypeConstants.JCR_NODE_TYPES;
+import static org.apache.jackrabbit.spi.commons.name.NameConstants.ANY_NAME;
 
 import java.io.File;
 import java.io.IOException;
 import java.util.List;
+import java.util.Set;
 
 import javax.jcr.NamespaceException;
 import javax.jcr.NamespaceRegistry;
@@ -63,11 +69,15 @@ import org.apache.jackrabbit.core.Reposi
 import org.apache.jackrabbit.core.config.RepositoryConfig;
 import org.apache.jackrabbit.core.nodetype.NodeTypeRegistry;
 import org.apache.jackrabbit.oak.api.Type;
-import org.apache.jackrabbit.oak.spi.commit.EmptyHook;
+import org.apache.jackrabbit.oak.plugins.name.NamespaceConstants;
+import org.apache.jackrabbit.oak.plugins.nodetype.RegistrationEditorProvider;
+import org.apache.jackrabbit.oak.spi.commit.EditorHook;
 import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
 import org.apache.jackrabbit.oak.spi.state.NodeStore;
 import org.apache.jackrabbit.oak.spi.state.NodeStoreBranch;
 import org.apache.jackrabbit.spi.Name;
+import org.apache.jackrabbit.spi.QItemDefinition;
+import org.apache.jackrabbit.spi.QNodeDefinition;
 import org.apache.jackrabbit.spi.QNodeTypeDefinition;
 import org.apache.jackrabbit.spi.QPropertyDefinition;
 import org.apache.jackrabbit.spi.QValue;
@@ -75,6 +85,8 @@ import org.apache.jackrabbit.spi.QValueC
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
+import com.google.common.collect.ImmutableSet;
+
 public class RepositoryUpgrade {
 
     /**
@@ -182,7 +194,7 @@ public class RepositoryUpgrade {
             copyWorkspaces(builder);
 
             branch.setRoot(builder.getNodeState());
-            branch.merge(EmptyHook.INSTANCE); // TODO: default hooks?
+            branch.merge(new EditorHook(new RegistrationEditorProvider())); // TODO: default hooks?
         } catch (Exception e) {
             throw new RepositoryException("Failed to copy content", e);
         }
@@ -203,9 +215,19 @@ public class RepositoryUpgrade {
         NodeBuilder system = root.child(JCR_SYSTEM);
         NodeBuilder namespaces = system.child("rep:namespaces");
 
+        Set<String> defaults = ImmutableSet.of(
+                NamespaceRegistry.NAMESPACE_EMPTY,
+                NamespaceRegistry.NAMESPACE_JCR,
+                NamespaceRegistry.NAMESPACE_MIX,
+                NamespaceRegistry.NAMESPACE_NT,
+                NamespaceRegistry.NAMESPACE_XML,
+                NamespaceConstants.NAMESPACE_SV,
+                NamespaceConstants.NAMESPACE_REP);
         logger.info("Copying registered namespaces");
         for (String uri : sourceRegistry.getURIs()) {
-            namespaces.setProperty(sourceRegistry.getPrefix(uri), uri);
+            if (!defaults.contains(uri)) {
+                namespaces.setProperty(sourceRegistry.getPrefix(uri), uri);
+            }
         }
     }
 
@@ -231,7 +253,7 @@ public class RepositoryUpgrade {
         // - jcr:supertypes (NAME) protected multiple
         Name[] supertypes = def.getSupertypes();
         if (supertypes != null && supertypes.length > 0) {
-            List<String> names = newArrayList();
+            List<String> names = newArrayListWithCapacity(supertypes.length);
             for (Name supertype : supertypes) {
                 names.add(getOakName(supertype));
             }
@@ -261,6 +283,11 @@ public class RepositoryUpgrade {
         }
 
         // + jcr:childNodeDefinition (nt:childNodeDefinition) = nt:childNodeDefinition protected sns
+        QNodeDefinition[] childNodes = def.getChildNodeDefs();
+        for (int i = 0; i < childNodes.length; i++) {
+            String name = JCR_CHILDNODEDEFINITION + '[' + i + ']';
+            copyChildNodeDefinition(childNodes[i], builder.child(name));
+        }
     }
 
     private void copyPropertyDefinition(
@@ -268,19 +295,8 @@ public class RepositoryUpgrade {
             throws NamespaceException {
         builder.setProperty(JCR_PRIMARYTYPE, NT_PROPERTYDEFINITION, NAME);
 
-        // - jcr:name (NAME) protected
-        builder.setProperty(JCR_NAME, getOakName(def.getName()), NAME);
-        // - jcr:autoCreated (BOOLEAN) protected mandatory
-        builder.setProperty(JCR_AUTOCREATED, def.isAutoCreated());
-        // - jcr:mandatory (BOOLEAN) protected mandatory
-        builder.setProperty(JCR_MANDATORY, def.isMandatory());
-        // - jcr:onParentVersion (STRING) protected mandatory
-        //   < 'COPY', 'VERSION', 'INITIALIZE', 'COMPUTE', 'IGNORE', 'ABORT'
-        builder.setProperty(
-                JCR_ONPARENTVERSION,
-                OnParentVersionAction.nameFromValue(def.getOnParentVersion()));
-        // - jcr:protected (BOOLEAN) protected mandatory
-        builder.setProperty(JCR_PROTECTED, def.isProtected());
+        copyItemDefinition(def, builder);
+
         // - jcr:requiredType (STRING) protected mandatory
         //   < 'STRING', 'URI', 'BINARY', 'LONG', 'DOUBLE',
         //     'DECIMAL', 'BOOLEAN', 'DATE', 'NAME', 'PATH',
@@ -314,6 +330,49 @@ public class RepositoryUpgrade {
         builder.setProperty(JCR_IS_QUERY_ORDERABLE, def.isQueryOrderable());
     }
 
+    private void copyChildNodeDefinition(
+            QNodeDefinition def, NodeBuilder builder)
+            throws NamespaceException {
+        builder.setProperty(JCR_PRIMARYTYPE, NT_CHILDNODEDEFINITION, NAME);
+
+        copyItemDefinition(def, builder);
+
+        // - jcr:requiredPrimaryTypes (NAME) = 'nt:base' protected mandatory multiple
+        Name[] types = def.getRequiredPrimaryTypes();
+        List<String> names = newArrayListWithCapacity(types.length);
+        for (Name type : types) {
+            names.add(getOakName(type));
+        }
+        builder.setProperty(JCR_REQUIREDPRIMARYTYPES, names, NAMES);
+        // - jcr:defaultPrimaryType (NAME) protected
+        Name type = def.getDefaultPrimaryType();
+        if (type != null) {
+            builder.setProperty(JCR_DEFAULTPRIMARYTYPE, getOakName(type), NAME);
+        }
+        // - jcr:sameNameSiblings (BOOLEAN) protected mandatory
+        builder.setProperty(JCR_SAMENAMESIBLINGS, def.allowsSameNameSiblings());
+    }
+
+    private void copyItemDefinition(QItemDefinition def, NodeBuilder builder)
+            throws NamespaceException {
+        // - jcr:name (NAME) protected
+        Name name = def.getName();
+        if (name != null && !name.equals(ANY_NAME)) {
+            builder.setProperty(JCR_NAME, getOakName(name), NAME);
+        }
+        // - jcr:autoCreated (BOOLEAN) protected mandatory
+        builder.setProperty(JCR_AUTOCREATED, def.isAutoCreated());
+        // - jcr:mandatory (BOOLEAN) protected mandatory
+        builder.setProperty(JCR_MANDATORY, def.isMandatory());
+        // - jcr:onParentVersion (STRING) protected mandatory
+        //   < 'COPY', 'VERSION', 'INITIALIZE', 'COMPUTE', 'IGNORE', 'ABORT'
+        builder.setProperty(
+                JCR_ONPARENTVERSION,
+                OnParentVersionAction.nameFromValue(def.getOnParentVersion()));
+        // - jcr:protected (BOOLEAN) protected mandatory
+        builder.setProperty(JCR_PROTECTED, def.isProtected());
+    }
+
     private void copyVersionStore(NodeBuilder root)
             throws RepositoryException, IOException {
         logger.info("Copying version histories");
@@ -333,7 +392,7 @@ public class RepositoryUpgrade {
         logger.info("Copying default workspace");
 
         // Copy all the default workspace content
-
+        
         RepositoryImpl repository = source.getRepository();
         RepositoryConfig config = repository.getConfig();
         String name = config.getDefaultWorkspaceName();

Added: jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java?rev=1478519&view=auto
==============================================================================
--- jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java (added)
+++ jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java Thu May  2 20:39:19 2013
@@ -0,0 +1,237 @@
+/*
+ * 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.oak.run;
+
+import static junit.framework.Assert.assertEquals;
+import static junit.framework.Assert.assertFalse;
+import static junit.framework.Assert.assertTrue;
+
+import java.io.ByteArrayInputStream;
+import java.io.File;
+import java.io.InputStream;
+import java.math.BigDecimal;
+import java.util.Calendar;
+import java.util.Random;
+
+import javax.jcr.Binary;
+import javax.jcr.Credentials;
+import javax.jcr.NamespaceRegistry;
+import javax.jcr.Node;
+import javax.jcr.PropertyType;
+import javax.jcr.Repository;
+import javax.jcr.Session;
+import javax.jcr.SimpleCredentials;
+import javax.jcr.Value;
+import javax.jcr.nodetype.NodeType;
+import javax.jcr.nodetype.NodeTypeManager;
+import javax.jcr.nodetype.NodeTypeTemplate;
+
+import org.apache.commons.io.FileUtils;
+import org.apache.jackrabbit.core.RepositoryImpl;
+import org.apache.jackrabbit.core.RepositoryUpgrade;
+import org.apache.jackrabbit.core.config.RepositoryConfig;
+import org.apache.jackrabbit.mk.core.MicroKernelImpl;
+import org.apache.jackrabbit.oak.Oak;
+import org.apache.jackrabbit.oak.jcr.Jcr;
+import org.apache.jackrabbit.oak.kernel.KernelNodeStore;
+import org.apache.jackrabbit.oak.spi.state.NodeStore;
+import org.junit.Test;
+
+public class RepositoryUpgradeTest {
+
+    private static final Credentials CREDENTIALS =
+            new SimpleCredentials("admin", "admin".toCharArray());
+
+    private static final Calendar DATE = Calendar.getInstance();
+
+    private static final byte[] BINARY = new byte[64 * 1024];
+
+    static {
+        new Random().nextBytes(BINARY);
+    }
+
+    private String identifier;
+
+    @Test
+    public void testUpgrade() throws Exception{
+        File directory = new File("target", "upgrade");
+        FileUtils.deleteQuietly(directory);
+
+        RepositoryConfig config = RepositoryConfig.install(directory);
+        RepositoryImpl source = RepositoryImpl.create(config);
+        try {
+            createSourceContent(source);
+        } finally {
+            source.shutdown();
+        }
+
+        NodeStore store = new KernelNodeStore(new MicroKernelImpl());
+        RepositoryUpgrade.copy(directory, store);
+        Jcr jcr = new Jcr(new Oak(store));
+        verifyTargetContent(jcr.createRepository());
+    }
+
+    private void createSourceContent(Repository repository) throws Exception {
+        Session session = repository.login(CREDENTIALS);
+        try {
+            NamespaceRegistry registry =
+                session.getWorkspace().getNamespaceRegistry();
+            registry.registerNamespace("test", "http://www.example.org/");
+
+            NodeTypeManager manager =
+                session.getWorkspace().getNodeTypeManager();
+            NodeTypeTemplate template = manager.createNodeTypeTemplate();
+            template.setName("test:unstructured");
+            template.setDeclaredSuperTypeNames(
+                    new String[] { "nt:unstructured" });
+            manager.registerNodeType(template, false);
+
+            Node root = session.getRootNode();
+
+            Node referenceable =
+                root.addNode("referenceable", "test:unstructured");
+            referenceable.addMixin(NodeType.MIX_REFERENCEABLE);
+            session.save();
+            identifier = referenceable.getIdentifier();
+
+            Node properties = root.addNode("properties", "test:unstructured");
+            properties.setProperty("boolean", true);
+            Binary binary = session.getValueFactory().createBinary(
+                    new ByteArrayInputStream(BINARY));
+            try {
+                properties.setProperty("binary", binary);
+            } finally {
+                binary.dispose();
+            }
+            properties.setProperty("date", DATE);
+            properties.setProperty("decimal", new BigDecimal(123));
+            properties.setProperty("double", Math.PI);
+            properties.setProperty("long", 9876543210L);
+            properties.setProperty("reference", referenceable);
+            properties.setProperty("string", "test");
+            properties.setProperty("multiple", "a,b,c".split(","));
+            session.save();
+
+            binary = properties.getProperty("binary").getBinary();
+            try {
+                InputStream stream = binary.getStream();
+                try {
+                    for (int i = 0; i < BINARY.length; i++) {
+                        assertEquals(BINARY[i], (byte) stream.read());
+                    }
+                    assertEquals(-1, stream.read());
+                } finally {
+                    stream.close();
+                }
+            } finally {
+                binary.dispose();
+            }
+        } finally {
+            session.logout();
+        }
+    }
+
+    private void verifyTargetContent(Repository repository) throws Exception {
+        Session session = repository.login(CREDENTIALS);
+        try {
+            assertEquals(
+                    "http://www.example.org/",
+                    session.getNamespaceURI("test"));
+
+            NodeTypeManager manager =
+                    session.getWorkspace().getNodeTypeManager();
+            assertTrue(manager.hasNodeType("test:unstructured"));
+            NodeType type = manager.getNodeType("test:unstructured");
+            assertFalse(type.isMixin());
+            assertTrue(type.isNodeType("nt:unstructured"));
+
+            assertTrue(session.nodeExists("/properties"));
+            Node properties = session.getNode("/properties");
+            assertEquals(
+                    PropertyType.BOOLEAN,
+                    properties.getProperty("boolean").getType());
+            assertEquals(
+                    true, properties.getProperty("boolean").getBoolean());
+            assertEquals(
+                    PropertyType.BINARY,
+                    properties.getProperty("binary").getType());
+            Binary binary = properties.getProperty("binary").getBinary();
+            try {
+                InputStream stream = binary.getStream();
+                try {
+                    for (int i = 0; i < BINARY.length; i++) {
+                        assertEquals(BINARY[i], (byte) stream.read());
+                    }
+                    assertEquals(-1, stream.read());
+                } finally {
+                    stream.close();
+                }
+            } finally {
+                binary.dispose();
+            }
+            assertEquals(
+                    PropertyType.DATE,
+                    properties.getProperty("date").getType());
+            assertEquals(
+                    DATE.getTimeInMillis(),
+                    properties.getProperty("date").getDate().getTimeInMillis());
+            assertEquals(
+                    PropertyType.DECIMAL,
+                    properties.getProperty("decimal").getType());
+            assertEquals(
+                    new BigDecimal(123),
+                    properties.getProperty("decimal").getDecimal());
+            assertEquals(
+                    PropertyType.DOUBLE,
+                    properties.getProperty("double").getType());
+            assertEquals(
+                    Math.PI, properties.getProperty("double").getDouble());
+            assertEquals(
+                    PropertyType.LONG,
+                    properties.getProperty("long").getType());
+            assertEquals(
+                    9876543210L, properties.getProperty("long").getLong());
+            assertEquals(
+                    PropertyType.REFERENCE,
+                    properties.getProperty("reference").getType());
+            assertEquals(
+                    identifier,
+                    properties.getProperty("reference").getString());
+            assertEquals(
+                    "/referenceable",
+                    properties.getProperty("reference").getNode().getPath());
+            assertEquals(
+                    PropertyType.STRING,
+                    properties.getProperty("string").getType());
+            assertEquals(
+                    "test", properties.getProperty("string").getString());
+            assertEquals(
+                    PropertyType.STRING,
+                    properties.getProperty("multiple").getType());
+            Value[] values = properties.getProperty("multiple").getValues();
+            assertEquals(3, values.length);
+            assertEquals("a", values[0].getString());
+            assertEquals("b", values[1].getString());
+            assertEquals("c", values[2].getString());
+        } finally {
+            session.logout();
+        }
+    }
+
+}

Propchange: jackrabbit/oak/trunk/oak-run/src/test/java/org/apache/jackrabbit/oak/run/RepositoryUpgradeTest.java
------------------------------------------------------------------------------
    svn:eol-style = native