directory-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From seelm...@apache.org
Subject svn commit: r1044959 - /directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java
Date Sun, 12 Dec 2010 23:50:25 GMT
Author: seelmann
Date: Sun Dec 12 23:50:25 2010
New Revision: 1044959

URL: http://svn.apache.org/viewvc?rev=1044959&view=rev
Log:
Added a schema extractor that adds LDIF entries directly to a partition. This can be used
for bootstrapping the schema partition in case the schema partition isn't a LDIF partition.

Added:
    directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java

Added: directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java
URL: http://svn.apache.org/viewvc/directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java?rev=1044959&view=auto
==============================================================================
--- directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java
(added)
+++ directory/apacheds/trunk/core/src/main/java/org/apache/directory/server/core/schema/SchemaLdifToPartitionExtractor.java
Sun Dec 12 23:50:25 2010
@@ -0,0 +1,264 @@
+/*
+ *  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.directory.server.core.schema;
+
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InvalidObjectException;
+import java.util.Map;
+import java.util.TreeMap;
+import java.util.UUID;
+import java.util.regex.Pattern;
+
+import org.apache.directory.server.core.interceptor.context.AddOperationContext;
+import org.apache.directory.server.core.interceptor.context.EntryOperationContext;
+import org.apache.directory.server.core.partition.Partition;
+import org.apache.directory.shared.i18n.I18n;
+import org.apache.directory.shared.ldap.constants.SchemaConstants;
+import org.apache.directory.shared.ldap.csn.Csn;
+import org.apache.directory.shared.ldap.csn.CsnFactory;
+import org.apache.directory.shared.ldap.entry.DefaultEntry;
+import org.apache.directory.shared.ldap.entry.Entry;
+import org.apache.directory.shared.ldap.exception.LdapException;
+import org.apache.directory.shared.ldap.ldif.LdapLdifException;
+import org.apache.directory.shared.ldap.ldif.LdifEntry;
+import org.apache.directory.shared.ldap.ldif.LdifReader;
+import org.apache.directory.shared.ldap.name.DN;
+import org.apache.directory.shared.ldap.schema.SchemaManager;
+import org.apache.directory.shared.ldap.schema.ldif.extractor.SchemaLdifExtractor;
+import org.apache.directory.shared.ldap.schema.ldif.extractor.impl.DefaultSchemaLdifExtractor;
+import org.apache.directory.shared.ldap.schema.ldif.extractor.impl.ResourceMap;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+
+/**
+ * An schema extractor that adds schema LDIF entries directly to the schema partition.
+ *
+ * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
+ */
+public class SchemaLdifToPartitionExtractor implements SchemaLdifExtractor
+{
+
+    /** The base path. */
+    private static final String BASE_PATH = "";
+
+    /** The logger. */
+    private static final Logger LOG = LoggerFactory.getLogger( SchemaLdifToPartitionExtractor.class
);
+
+    /**
+     * The pattern to extract the schema from LDIF files.
+     * java.util.regex.Pattern is immutable so only one instance is needed for all uses.
+     */
+    private static final Pattern EXTRACT_PATTERN = Pattern.compile( ".*schema" + "[/\\Q\\\\E]"
+ "ou=schema.*\\.ldif" );
+
+    private final CsnFactory csnFactory = new CsnFactory( 0 );
+
+    /** The extracted flag. */
+    private boolean extracted;
+
+    private final SchemaManager schemaManager;
+    private final Partition partition;
+
+
+    /**
+     * Creates an extractor which adds schema LDIF entries directly to the schema partition.
+     * The bootstrap schema manager must at least know the 'apachemeta' schema.
+     *
+     * @param schemaManager the bootstrap schema manager
+     * @param partition the destination partition
+     */
+    public SchemaLdifToPartitionExtractor( SchemaManager schemaManager, Partition partition
) throws LdapException
+    {
+        this.schemaManager = schemaManager;
+        this.partition = partition;
+
+        DN dn = new DN( SchemaConstants.OU_SCHEMA, schemaManager );
+        EntryOperationContext hasEntryContext = new EntryOperationContext( null, dn );
+        if ( partition.hasEntry( hasEntryContext ) )
+        {
+            LOG.info( "Schema entry 'ou=schema' exists: extracted state set to true." );
+            extracted = true;
+        }
+        else
+        {
+            LOG.info( "Schema entry 'ou=schema' does NOT exist: extracted state set to false."
);
+            extracted = false;
+        }
+    }
+
+
+    /**
+     * Gets whether or not the schema has already been added to the schema partition.
+     *
+     * @return true if schema has already been added to the schema partition
+     */
+    public boolean isExtracted()
+    {
+        return extracted;
+    }
+
+
+    /**
+     * {@inheritDoc}
+     */
+    public void extractOrCopy( boolean overwrite ) throws IOException
+    {
+        Map<String, Boolean> resources = ResourceMap.getResources( EXTRACT_PATTERN
);
+
+        // must sort the map to ensure parent entries are added before children
+        resources = new TreeMap<String, Boolean>( resources );
+
+        if ( !extracted || overwrite )
+        {
+            for ( Map.Entry<String, Boolean> entry : resources.entrySet() )
+            {
+                if ( entry.getValue() )
+                {
+                    addFromClassLoader( entry.getKey() );
+                }
+                else
+                {
+                    File resource = new File( entry.getKey() );
+                    addLdifFile( resource );
+                }
+            }
+
+            extracted = true;
+        }
+    }
+
+
+    /**
+     * {@inheritDoc}
+     */
+    public void extractOrCopy() throws IOException
+    {
+        extractOrCopy( false );
+    }
+
+
+    /**
+     * Adds an schema entry from an LDIF file.
+     *
+     * @param source the source file to copy
+     * @throws IOException if there are IO errors or the source does not exist
+     */
+    private void addLdifFile( File source ) throws IOException
+    {
+        LOG.debug( "copyFile(): source = {}", source );
+
+        if ( !source.getParentFile().exists() )
+        {
+            throw new FileNotFoundException( I18n.err( I18n.ERR_08002, source.getAbsolutePath()
) );
+        }
+
+        FileInputStream in = new FileInputStream( source );
+        addFromStream( in, source.getAbsolutePath() );
+    }
+
+
+    /**
+     * Adds an schema entry from a class loader resource.
+     *
+     * @param resource the LDIF schema resource
+     * @throws IOException if there are IO errors
+     */
+    private void addFromClassLoader( String resource ) throws IOException
+    {
+        InputStream in = DefaultSchemaLdifExtractor.getUniqueResourceAsStream( resource,
+            "LDIF file in schema repository" );
+        addFromStream( in, resource );
+    }
+
+
+    /**
+     * Adds an schema entry from the given stream to the schema partition
+     *
+     * @param in the input stream
+     * @param source the source
+     * @throws IOException signals that an I/O exception has occurred.
+     */
+    private void addFromStream( InputStream in, String source ) throws IOException
+    {
+        try
+        {
+            LdifReader ldifReader = new LdifReader( in );
+            boolean first = true;
+            LdifEntry ldifEntry = null;
+
+            while ( ldifReader.hasNext() )
+            {
+                if ( first )
+                {
+                    ldifEntry = ldifReader.next();
+
+                    if ( ldifEntry.get( SchemaConstants.ENTRY_UUID_AT ) == null )
+                    {
+                        // No UUID, let's create one
+                        UUID entryUuid = UUID.randomUUID();
+                        ldifEntry.addAttribute( SchemaConstants.ENTRY_UUID_AT, entryUuid.toString()
);
+                    }
+                    if ( ldifEntry.get( SchemaConstants.ENTRY_CSN_AT ) == null )
+                    {
+                        // No CSN, let's create one
+                        Csn csn = csnFactory.newInstance();
+                        ldifEntry.addAttribute( SchemaConstants.ENTRY_CSN_AT, csn.toString()
);
+                    }
+
+                    first = false;
+                }
+                else
+                {
+                    // throw an exception : we should not have more than one entry per schema
ldif file
+                    String msg = I18n.err( I18n.ERR_08003, source );
+                    LOG.error( msg );
+                    throw new InvalidObjectException( msg );
+                }
+            }
+
+            ldifReader.close();
+
+            // inject the entry
+            Entry entry = new DefaultEntry( schemaManager, ldifEntry.getEntry() );
+            AddOperationContext addContext = new AddOperationContext( null, entry );
+            partition.add( addContext );
+        }
+        catch ( LdapLdifException ne )
+        {
+            // throw an exception : we should not have more than one entry per schema ldif
file
+            String msg = I18n.err( I18n.ERR_08004, source, ne.getLocalizedMessage() );
+            LOG.error( msg );
+            throw new IOException( msg, ne );
+        }
+        catch ( LdapException ne )
+        {
+            // throw an exception : we should not have more than one entry per schema ldif
file
+            String msg = I18n.err( I18n.ERR_08004, source, ne.getLocalizedMessage() );
+            LOG.error( msg );
+            throw new IOException( msg, ne );
+        }
+    }
+
+}



Mime
View raw message