openjpa-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Kevin Sutter" <kwsut...@gmail.com>
Subject Re: svn commit: r482189 [1/2] - in /incubator/openjpa/trunk: openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/meta/ openjpa-jdbc/src/main/java/org/apache/openjpa/jdbc/sql/ openjpa-lib/src/main/java/org/apache/openjpa/lib/jdbc/
Date Mon, 04 Dec 2006 19:37:28 GMT
Abe,
One thought is that I am committed a change after applying a patch.  When I
commit a change that originated from me (no patch), then it seems to do the
commit diffs just fine.

Kevin

On 12/4/06, Abe White <awhite@bea.com> wrote:
>
> Does anyone know how we can avoid commit diffs like this?  I have no
> idea what actually changed in the MappingTool, because every line is
> reported as changed.
>
>
> On Dec 4, 2006, at 6:42 AM, kwsutter@apache.org wrote:
>
> > Author: kwsutter
> > Date: Mon Dec  4 06:42:09 2006
> > New Revision: 482189
> >
> > URL: http://svn.apache.org/viewvc?view=rev&rev=482189
> > Log:
> > Resolving JIRA report OPENJPA-63 for better pessimistic lock
> > support for DB2.  Instead of the usual "for update" clause, db2
> > dictionary will now use "with rr use and keep update locks" clause.
> >
> > A couple of additional changes were necessary to properly detect
> > the version of DB2 currently in use.
> >
> > Modified:
> >     incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/
> > openjpa/jdbc/meta/MappingTool.java
> >     incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/
> > openjpa/jdbc/sql/DB2Dictionary.java
> >     incubator/openjpa/trunk/openjpa-lib/src/main/java/org/apache/
> > openjpa/lib/jdbc/DelegatingDatabaseMetaData.java
> >
> > Modified: incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/
> > apache/openjpa/jdbc/meta/MappingTool.java
> > URL: http://svn.apache.org/viewvc/incubator/openjpa/trunk/openjpa-
> > jdbc/src/main/java/org/apache/openjpa/jdbc/meta/MappingTool.java?
> > view=diff&rev=482189&r1=482188&r2=482189
> > ======================================================================
> > ========
> > --- incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/
> > openjpa/jdbc/meta/MappingTool.java (original)
> > +++ incubator/openjpa/trunk/openjpa-jdbc/src/main/java/org/apache/
> > openjpa/jdbc/meta/MappingTool.java Mon Dec  4 06:42:09 2006
> > @@ -1,1123 +1,1123 @@
> > -/*
> > - * Copyright 2006 The Apache Software Foundation.
> > - *
> > - * Licensed 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.openjpa.jdbc.meta;
> > -
> > -import java.io.File;
> > -import java.io.IOException;
> > -import java.io.PrintWriter;
> > -import java.io.Writer;
> > -import java.sql.SQLException;
> > -import java.util.Arrays;
> > -import java.util.Collection;
> > -import java.util.HashMap;
> > -import java.util.HashSet;
> > -import java.util.Iterator;
> > -import java.util.Map;
> > -import java.util.Set;
> > -
> > -import org.apache.openjpa.conf.OpenJPAConfiguration;
> > -import org.apache.openjpa.jdbc.conf.JDBCConfiguration;
> > -import org.apache.openjpa.jdbc.conf.JDBCConfigurationImpl;
> > -import org.apache.openjpa.jdbc.kernel.JDBCSeq;
> > -import org.apache.openjpa.jdbc.schema.Column;
> > -import org.apache.openjpa.jdbc.schema.DynamicSchemaFactory;
> > -import org.apache.openjpa.jdbc.schema.LazySchemaFactory;
> > -import org.apache.openjpa.jdbc.schema.Schema;
> > -import org.apache.openjpa.jdbc.schema.SchemaGenerator;
> > -import org.apache.openjpa.jdbc.schema.SchemaGroup;
> > -import org.apache.openjpa.jdbc.schema.SchemaSerializer;
> > -import org.apache.openjpa.jdbc.schema.SchemaTool;
> > -import org.apache.openjpa.jdbc.schema.Table;
> > -import org.apache.openjpa.jdbc.schema.XMLSchemaSerializer;
> > -import org.apache.openjpa.jdbc.sql.DBDictionary;
> > -import org.apache.openjpa.kernel.Seq;
> > -import org.apache.openjpa.lib.conf.Configurations;
> > -import org.apache.openjpa.lib.log.Log;
> > -import org.apache.openjpa.lib.meta.ClassArgParser;
> > -import org.apache.openjpa.lib.util.Files;
> > -import org.apache.openjpa.lib.util.Localizer;
> > -import org.apache.openjpa.lib.util.Options;
> > -import org.apache.openjpa.lib.util.Services;
> > -import org.apache.openjpa.meta.ClassMetaData;
> > -import org.apache.openjpa.meta.FieldMetaData;
> > -import org.apache.openjpa.meta.JavaTypes;
> > -import org.apache.openjpa.meta.MetaDataFactory;
> > -import org.apache.openjpa.meta.MetaDataModes;
> > -import org.apache.openjpa.meta.QueryMetaData;
> > -import org.apache.openjpa.meta.SequenceMetaData;
> > -import org.apache.openjpa.meta.ValueStrategies;
> > -import org.apache.openjpa.util.GeneralException;
> > -import org.apache.openjpa.util.InternalException;
> > -import org.apache.openjpa.util.MetaDataException;
> > -
> > -/**
> > - * Tool for manipulating class mappings and associated schema.
> > - *
> > - * @author Abe White
> > - */
> > -public class MappingTool
> > -    implements MetaDataModes {
> > -
> > -    public static final String SCHEMA_ACTION_NONE = "none";
> > -
> > -    public static final String ACTION_ADD = "add";
> > -    public static final String ACTION_REFRESH = "refresh";
> > -    public static final String ACTION_BUILD_SCHEMA = "buildSchema";
> > -    public static final String ACTION_DROP = "drop";
> > -    public static final String ACTION_VALIDATE = "validate";
> > -    public static final String ACTION_EXPORT = "export";
> > -    public static final String ACTION_IMPORT = "import";
> > -
> > -    public static final String[] ACTIONS = new String[]{
> > -        ACTION_ADD,
> > -        ACTION_REFRESH,
> > -        ACTION_BUILD_SCHEMA,
> > -        ACTION_DROP,
> > -        ACTION_VALIDATE,
> > -        ACTION_EXPORT,
> > -        ACTION_IMPORT,
> > -    };
> > -
> > -    private static Localizer _loc = Localizer.forPackage
> > (MappingTool.class);
> > -
> > -    private final JDBCConfiguration _conf;
> > -    private final Log _log;
> > -    private final String _action;
> > -    private final boolean _meta;
> > -    private final int _mode;
> > -
> > -    private MappingRepository _repos = null;
> > -    private SchemaGroup _schema = null;
> > -    private SchemaTool _schemaTool = null;
> > -    private String _schemaAction = SchemaTool.ACTION_ADD;
> > -    private boolean _readSchema = false;
> > -    private boolean _pks = false;
> > -    private boolean _fks = false;
> > -    private boolean _indexes = false;
> > -    private boolean _seqs = true;
> > -    private boolean _dropUnused = true;
> > -    private boolean _ignoreErrors = false;
> > -    private File _file = null;
> > -    private Writer _mappingWriter = null;
> > -    private Writer _schemaWriter = null;
> > -
> > -    // buffer metadatas to be dropped
> > -    private Set _dropCls = null;
> > -    private Set _dropMap = null;
> > -    private boolean _flush = false;
> > -    private boolean _flushSchema = false;
> > -
> > -    /**
> > -     * Constructor. Supply configuration and action.
> > -     */
> > -    public MappingTool(JDBCConfiguration conf, String action,
> > boolean meta) {
> > -        _conf = conf;
> > -        _log = conf.getLog(JDBCConfiguration.LOG_METADATA);
> > -        _meta = meta;
> > -
> > -        if (action == null)
> > -            _action = ACTION_REFRESH;
> > -        else if (!Arrays.asList(ACTIONS).contains(action))
> > -            throw new IllegalArgumentException("action == " +
> > action);
> > -        else
> > -            _action = action;
> > -
> > -        if (meta && ACTION_ADD.equals(_action))
> > -            _mode = MODE_META;
> > -        else if (meta && ACTION_DROP.equals(_action))
> > -            _mode = MODE_META | MODE_MAPPING | MODE_QUERY;
> > -        else
> > -            _mode = MODE_MAPPING;
> > -    }
> > -
> > -    /**
> > -     * The action supplied on construction.
> > -     */
> > -    public String getAction() {
> > -        return _action;
> > -    }
> > -
> > -    /**
> > -     * Whether the action works on metadata as well as mappings.
> > -     */
> > -    public boolean isMetaDataAction() {
> > -        return _meta;
> > -    }
> > -
> > -    /**
> > -     * The schema modification policy, or <code>none</code>. See the
> > -     * ACTION constants in {@link SchemaTool}. Defaults to
> > -     * {@link SchemaTool#ACTION_ADD}.
> > -     */
> > -    public String getSchemaAction() {
> > -        return _schemaAction;
> > -    }
> > -
> > -    /**
> > -     * The schema modification policy, or <code>none</code>. See the
> > -     * ACTION constants in {@link SchemaTool}. Defaults to
> > -     * {@link SchemaTool#ACTION_ADD}.
> > -     */
> > -    public void setSchemaAction(String schemaAction) {
> > -        _schemaAction = schemaAction;
> > -    }
> > -
> > -    /**
> > -     * Set to true to read the entire schema before mapping.
> > -     * Leaving this option false saves time, but is dangerous when
> > adding
> > -     * new mappings, because without full knowledge of the
> > existing schema the
> > -     * mapping tool might create tables or indexes that conflict with
> > -     * existing components.
> > -     */
> > -    public boolean getReadSchema() {
> > -        return _readSchema;
> > -    }
> > -
> > -    /**
> > -     * Set to true to read the entire schema before mapping.
> > -     * Leaving this option false saves time, but is dangerous when
> > adding
> > -     * new mappings, because without full knowledge of the
> > existing schema the
> > -     * mapping tool might create tables or indexes that conflict with
> > -     * existing components.
> > -     */
> > -    public void setReadSchema(boolean readSchema) {
> > -        _readSchema = readSchema;
> > -    }
> > -
> > -    /**
> > -     * Whether to manipulate sequences. Defaults to true.
> > -     */
> > -    public boolean getSequences() {
> > -        return _seqs;
> > -    }
> > -
> > -    /**
> > -     * Whether to manipulate sequences. Defaults to true.
> > -     */
> > -    public void setSequences(boolean seqs) {
> > -        _seqs = seqs;
> > -    }
> > -
> > -    /**
> > -     * Whether indexes on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public boolean getIndexes() {
> > -        return _indexes;
> > -    }
> > -
> > -    /**
> > -     * Whether indexes on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public void setIndexes(boolean indexes) {
> > -        _indexes = indexes;
> > -    }
> > -
> > -    /**
> > -     * Whether foreign keys on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public boolean getForeignKeys() {
> > -        return _fks;
> > -    }
> > -
> > -    /**
> > -     * Whether foreign keys on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public void setForeignKeys(boolean fks) {
> > -        _fks = fks;
> > -    }
> > -
> > -    /**
> > -     * Whether primary keys on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public boolean getPrimaryKeys() {
> > -        return _pks;
> > -    }
> > -
> > -    /**
> > -     * Whether primary keys on existing tables should be manipulated.
> > -     * Defaults to false.
> > -     */
> > -    public void setPrimaryKeys(boolean pks) {
> > -        _pks = pks;
> > -    }
> > -
> > -    /**
> > -     * Whether schema components that are unused by any mapping
> > will be
> > -     * dropped from this tool's {@link SchemaGroup}, and,
> > depending on
> > -     * the schema action, from the database. Defaults to true.
> > -     */
> > -    public boolean getDropUnusedComponents() {
> > -        return _dropUnused;
> > -    }
> > -
> > -    /**
> > -     * Whether schema components that are unused by any mapping
> > will be
> > -     * dropped from this tool's {@link SchemaGroup}, and,
> > depending on
> > -     * the schema action, from the database. Defaults to true.
> > -     */
> > -    public void setDropUnusedComponents(boolean dropUnused) {
> > -        _dropUnused = dropUnused;
> > -    }
> > -
> > -    /**
> > -     * Whether and SQL errors should cause a failure or just issue
> > a warning.
> > -     */
> > -    public void setIgnoreErrors(boolean ignoreErrors) {
> > -        _ignoreErrors = ignoreErrors;
> > -    }
> > -
> > -    /**
> > -     * Whether and SQL errors should cause a failure or just issue
> > a warning.
> > -     */
> > -    public boolean getIgnoreErrors() {
> > -        return _ignoreErrors;
> > -    }
> > -
> > -    /**
> > -     * Return the schema tool to use for schema modification.
> > -     */
> > -    public SchemaTool getSchemaTool() {
> > -        if (_schemaTool == null)
> > -            _schemaTool = newSchemaTool(_schemaAction);
> > -        return _schemaTool;
> > -    }
> > -
> > -    /**
> > -     * Return the schema tool to use for schema modification.
> > -     */
> > -    private SchemaTool newSchemaTool(String action) {
> > -        if (SCHEMA_ACTION_NONE.equals(action))
> > -            action = null;
> > -        SchemaTool tool = new SchemaTool(_conf, action);
> > -        tool.setIgnoreErrors(getIgnoreErrors());
> > -        tool.setPrimaryKeys(getPrimaryKeys());
> > -        tool.setForeignKeys(getForeignKeys());
> > -        tool.setIndexes(getIndexes());
> > -        tool.setSequences(getSequences());
> > -        return tool;
> > -    }
> > -
> > -    /**
> > -     * Set the schema tool to use for schema modification.
> > -     */
> > -    public void setSchemaTool(SchemaTool tool) {
> > -        _schemaTool = tool;
> > -    }
> > -
> > -    /**
> > -     * The stream to export the planned schema to as an XML document.
> > -     * If non-null, then the database schema will not be altered.
> > -     */
> > -    public Writer getSchemaWriter() {
> > -        return _schemaWriter;
> > -    }
> > -
> > -    /**
> > -     * The stream to export the planned schema to as an XML document.
> > -     * If non-null, then the database schema will not be altered.
> > -     */
> > -    public void setSchemaWriter(Writer schemaWriter) {
> > -        _schemaWriter = schemaWriter;
> > -    }
> > -
> > -    /**
> > -     * The stream to export the planned mappings to as an XML
> > document.
> > -     * If non-null, then the mapping repository will not be altered.
> > -     */
> > -    public Writer getMappingWriter() {
> > -        return _mappingWriter;
> > -    }
> > -
> > -    /**
> > -     * The stream to export the planned mappings to as an XML
> > document.
> > -     * If non-null, then the mapping repository will not be altered.
> > -     */
> > -    public void setMappingWriter(Writer mappingWriter) {
> > -        _mappingWriter = mappingWriter;
> > -    }
> > -
> > -    /**
> > -     * If adding metadata, the metadata file to add to.
> > -     */
> > -    public File getMetaDataFile() {
> > -        return _file;
> > -    }
> > -
> > -    /**
> > -     * If adding metadata, the metadata file to add to.
> > -     */
> > -    public void setMetaDataFile(File file) {
> > -        _file = file;
> > -    }
> > -
> > -    /**
> > -     * Return the repository to use to access mapping information.
> > -     * Defaults to a new {@link MappingRepository}.
> > -     */
> > -    public MappingRepository getRepository() {
> > -        if (_repos == null) {
> > -            _repos = _conf.newMappingRepositoryInstance();
> > -            _repos.setSchemaGroup(getSchemaGroup());
> > -            _repos.setValidate(_repos.VALIDATE_UNENHANCED, false);
> > -        }
> > -        return _repos;
> > -    }
> > -
> > -    /**
> > -     * Set the repository to use to access mapping information.
> > -     */
> > -    public void setRepository(MappingRepository repos) {
> > -        _repos = repos;
> > -    }
> > -
> > -    /**
> > -     * Return the schema group to use in mapping. If none has been
> > set, the
> > -     * schema will be generated from the database.
> > -     */
> > -    public SchemaGroup getSchemaGroup() {
> > -        if (_schema == null) {
> > -            if (ACTION_BUILD_SCHEMA.equals(_action)) {
> > -                DynamicSchemaFactory factory = new
> > DynamicSchemaFactory();
> > -                factory.setConfiguration(_conf);
> > -                _schema = factory;
> > -            } else if (_readSchema
> > -                || SchemaTool.ACTION_RETAIN.equals(_schemaAction)
> > -                || SchemaTool.ACTION_REFRESH.equals(_schemaAction)) {
> > -                _schema = (SchemaGroup) getSchemaTool
> > ().getDBSchemaGroup().
> > -                    clone();
> > -            } else {
> > -                // with this we'll just read tables as different
> > mappings
> > -                // look for them
> > -                LazySchemaFactory factory = new LazySchemaFactory();
> > -                factory.setConfiguration(_conf);
> > -                factory.setPrimaryKeys(getPrimaryKeys());
> > -                factory.setForeignKeys(getForeignKeys());
> > -                factory.setIndexes(getIndexes());
> > -                _schema = factory;
> > -            }
> > -
> > -            if (_schema.getSchemas().length == 0)
> > -                _schema.addSchema();
> > -        }
> > -        return _schema;
> > -    }
> > -
> > -    /**
> > -     * Set the schema to use in mapping.
> > -     */
> > -    public void setSchemaGroup(SchemaGroup schema) {
> > -        _schema = schema;
> > -    }
> > -
> > -    /**
> > -     * Reset the internal repository. This is called automatically
> > after
> > -     * every {@link #record}.
> > -     */
> > -    public void clear() {
> > -        _repos = null;
> > -        _schema = null;
> > -        _schemaTool = null;
> > -        _flush = false;
> > -        _flushSchema = false;
> > -        if (_dropCls != null)
> > -            _dropCls.clear();
> > -        if (_dropMap != null)
> > -            _dropMap.clear();
> > -    }
> > -
> > -    /**
> > -     * Records the changes that have been made to both the
> > mappings and the
> > -     * associated schema, and clears the tool for further use.
> > This also
> > -     * involves clearing the internal mapping repository.
> > -     */
> > -    public void record() {
> > -        MappingRepository repos = getRepository();
> > -        MetaDataFactory io = repos.getMetaDataFactory();
> > -        ClassMapping[] mappings;
> > -        if (!ACTION_DROP.equals(_action))
> > -            mappings = repos.getMappings();
> > -        else if (_dropMap != null)
> > -            mappings = (ClassMapping[]) _dropMap.toArray
> > -                (new ClassMapping[_dropMap.size()]);
> > -        else
> > -            mappings = new ClassMapping[0];
> > -
> > -        try {
> > -            if (_dropCls != null && !_dropCls.isEmpty()) {
> > -                Class[] cls = (Class[]) _dropCls.toArray
> > -                    (new Class[_dropCls.size()]);
> > -                if (!io.drop(cls, _mode, null))
> > -                    _log.warn(_loc.get("bad-drop", _dropCls));
> > -            }
> > -
> > -            if (_flushSchema) {
> > -                // drop portions of the known schema that no
> > mapping uses, and
> > -                // add sequences used for value generation
> > -                if (_dropUnused)
> > -                    dropUnusedSchemaComponents(mappings);
> > -                addSequenceComponents(mappings);
> > -
> > -                // now run the schematool as long as we're doing
> > some schema
> > -                // action and the user doesn't just want an xml
> > output
> > -                if (!SCHEMA_ACTION_NONE.equals(_schemaAction)
> > -                    && (_schemaWriter == null || (_schemaTool != null
> > -                    && _schemaTool.getWriter() != null))) {
> > -                    SchemaTool tool = getSchemaTool();
> > -                    tool.setSchemaGroup(getSchemaGroup());
> > -                    tool.run();
> > -                    tool.record();
> > -                }
> > -
> > -                // xml output of schema?
> > -                if (_schemaWriter != null) {
> > -                    // serialize the planned schema to the stream
> > -                    SchemaSerializer ser = new XMLSchemaSerializer
> > (_conf);
> > -                    ser.addAll(getSchemaGroup());
> > -                    ser.serialize(_schemaWriter, ser.PRETTY);
> > -                    _schemaWriter.flush();
> > -                }
> > -            }
> > -            if (!_flush)
> > -                return;
> > -
> > -            QueryMetaData[] queries = repos.getQueryMetaDatas();
> > -            SequenceMetaData[] seqs = repos.getSequenceMetaDatas();
> > -            Map output = null;
> > -
> > -            // if we're outputting to stream, set all metas to
> > same file so
> > -            // they get placed in single string
> > -            if (_mappingWriter != null) {
> > -                output = new HashMap();
> > -                File tmp = new File("openjpatmp");
> > -                for (int i = 0; i < mappings.length; i++)
> > -                    mappings[i].setSource(tmp, mappings
> > [i].SRC_OTHER);
> > -                for (int i = 0; i < queries.length; i++)
> > -                    queries[i].setSource(tmp, queries
> > [i].getSourceScope(),
> > -                        queries[i].SRC_OTHER);
> > -                for (int i = 0; i < seqs.length; i++)
> > -                    seqs[i].setSource(tmp, seqs[i].getSourceScope(),
> > -                        seqs[i].SRC_OTHER);
> > -            }
> > -
> > -            // store
> > -            if (!io.store(mappings, queries, seqs, _mode, output))
> > -                throw new MetaDataException(_loc.get("bad-store"));
> > -
> > -            // write to stream
> > -            if (_mappingWriter != null) {
> > -                PrintWriter out = new PrintWriter(_mappingWriter);
> > -                for (Iterator itr = output.values().iterator();
> > -                    itr.hasNext();)
> > -                    out.println((String) itr.next());
> > -                out.flush();
> > -            }
> > -        }
> > -        catch (RuntimeException re) {
> > -            throw re;
> > -        } catch (Exception e) {
> > -            throw new GeneralException(e);
> > -        } finally {
> > -            clear();
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Drops schema components that appear to be unused from the
> > local
> > -     * copy of the schema group.
> > -     */
> > -    private void dropUnusedSchemaComponents(ClassMapping[]
> > mappings) {
> > -        FieldMapping[] fields;
> > -        for (int i = 0; i < mappings.length; i++) {
> > -            mappings[i].refSchemaComponents();
> > -            mappings[i].getDiscriminator().refSchemaComponents();
> > -            mappings[i].getVersion().refSchemaComponents();
> > -            fields = mappings[i].getDefinedFieldMappings();
> > -            for (int j = 0; j < fields.length; j++)
> > -                fields[j].refSchemaComponents();
> > -        }
> > -
> > -        // also allow the dbdictionary to ref any schema
> > components that
> > -        // it adds apart from mappings
> > -        SchemaGroup group = getSchemaGroup();
> > -        Schema[] schemas = group.getSchemas();
> > -        Table[] tables;
> > -        DBDictionary dict = _conf.getDBDictionaryInstance();
> > -        for (int i = 0; i < schemas.length; i++) {
> > -            tables = schemas[i].getTables();
> > -            for (int j = 0; j < tables.length; j++)
> > -                dict.refSchemaComponents(tables[j]);
> > -        }
> > -
> > -        group.removeUnusedComponents();
> > -    }
> > -
> > -    /**
> > -     * Add tables used by sequences to the given schema.
> > -     */
> > -    private void addSequenceComponents(ClassMapping[] mappings) {
> > -        SchemaGroup group = getSchemaGroup();
> > -        for (int i = 0; i < mappings.length; i++)
> > -            addSequenceComponents(mappings[i], group);
> > -    }
> > -
> > -    /**
> > -     * Add tables used by sequences to the given schema.
> > -     */
> > -    private void addSequenceComponents(ClassMapping mapping,
> > -        SchemaGroup group) {
> > -        SequenceMetaData smd = mapping.getIdentitySequenceMetaData();
> > -        Seq seq = null;
> > -        if (smd != null)
> > -            seq = smd.getInstance(null);
> > -        else if (mapping.getIdentityStrategy() ==
> > ValueStrategies.NATIVE
> > -            || (mapping.getIdentityStrategy() == ValueStrategies.NONE
> > -            && mapping.getIdentityType() ==
> > ClassMapping.ID_DATASTORE))
> > -            seq = _conf.getSequenceInstance();
> > -
> > -        if (seq instanceof JDBCSeq)
> > -            ((JDBCSeq) seq).addSchema(mapping, group);
> > -
> > -        FieldMapping[] fmds;
> > -        if (mapping.getEmbeddingMetaData() == null)
> > -            fmds = mapping.getDefinedFieldMappings();
> > -        else
> > -            fmds = mapping.getFieldMappings();
> > -        for (int i = 0; i < fmds.length; i++) {
> > -            smd = fmds[i].getValueSequenceMetaData();
> > -            if (smd != null) {
> > -                seq = smd.getInstance(null);
> > -                if (seq instanceof JDBCSeq)
> > -                    ((JDBCSeq) seq).addSchema(mapping, group);
> > -            } else if (fmds[i].getEmbeddedMapping() != null)
> > -                addSequenceComponents(fmds[i].getEmbeddedMapping
> > (), group);
> > -        }
> > -    }
> > -
> > -    ///////////
> > -    // Actions
> > -    ///////////
> > -
> > -    /**
> > -     * Run the configured action on the given instance.
> > -     */
> > -    public void run(Class cls) {
> > -        if (ACTION_ADD.equals(_action)) {
> > -            if (_meta)
> > -                addMeta(cls);
> > -            else
> > -                add(cls);
> > -        } else if (ACTION_REFRESH.equals(_action))
> > -            refresh(cls);
> > -        else if (ACTION_BUILD_SCHEMA.equals(_action))
> > -            buildSchema(cls);
> > -        else if (ACTION_DROP.equals(_action))
> > -            drop(cls);
> > -        else if (ACTION_VALIDATE.equals(_action))
> > -            validate(cls);
> > -    }
> > -
> > -    /**
> > -     * Add the mapping for the given instance.
> > -     */
> > -    private void add(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        MappingRepository repos = getRepository();
> > -        repos.setStrategyInstaller(new MappingStrategyInstaller
> > (repos));
> > -        if (getMapping(repos, cls, true) != null) {
> > -            _flush = true;
> > -            _flushSchema = true;
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Return the mapping for the given type, or null if the type is
> > -     * persistence-aware.
> > -     */
> > -    private static ClassMapping getMapping(MappingRepository
> > repos, Class cls,
> > -        boolean validate) {
> > -        // this will parse all possible metadata rsrcs looking for
> > cls, so
> > -        // will detect if p-aware
> > -        ClassMapping mapping = repos.getMapping(cls, null, false);
> > -        if (mapping != null)
> > -            return mapping;
> > -        if (!validate || cls.isInterface()
> > -            || repos.getPersistenceAware(cls) != null)
> > -            return null;
> > -        throw new MetaDataException(_loc.get("no-meta", cls));
> > -    }
> > -
> > -    /**
> > -     * Create a metadata for the given instance.
> > -     */
> > -    private void addMeta(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        _flush = true;
> > -        MappingRepository repos = getRepository();
> > -        repos.setResolve(MODE_MAPPING, false);
> > -        MetaDataFactory factory = repos.getMetaDataFactory();
> > -        factory.getDefaults().setIgnoreNonPersistent(false);
> > -        factory.setStoreMode(MetaDataFactory.STORE_VERBOSE);
> > -
> > -        ClassMetaData meta = repos.addMetaData(cls);
> > -        FieldMetaData[] fmds = meta.getDeclaredFields();
> > -        for (int i = 0; i < fmds.length; i++) {
> > -            if (fmds[i].getDeclaredTypeCode() == JavaTypes.OBJECT
> > -                && fmds[i].getDeclaredType() != Object.class)
> > -                fmds[i].setDeclaredTypeCode(JavaTypes.PC);
> > -        }
> > -        meta.setSource(_file, meta.getSourceType());
> > -        meta.setResolve(MODE_META, true);
> > -    }
> > -
> > -    /**
> > -     * Refresh or add the mapping for the given instance.
> > -     */
> > -    private void refresh(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        MappingRepository repos = getRepository();
> > -        repos.setStrategyInstaller(new RefreshStrategyInstaller
> > (repos));
> > -        if (getMapping(repos, cls, true) != null) {
> > -            _flush = true;
> > -            _flushSchema = true;
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Validate the mappings for the given class and its fields.
> > -     */
> > -    private void validate(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        MappingRepository repos = getRepository();
> > -        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > -        if (getMapping(repos, cls, true) != null)
> > -            _flushSchema = !SCHEMA_ACTION_NONE.equals(_schemaAction)
> > -                && !SchemaTool.ACTION_ADD.equals(_schemaAction);
> > -    }
> > -
> > -    /**
> > -     * Create the schema using the mapping for the given instance.
> > -     */
> > -    private void buildSchema(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        MappingRepository repos = getRepository();
> > -        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > -        if (getMapping(repos, cls, true) == null)
> > -            return;
> > -
> > -        // set any logical pks to non-logical so they get flushed
> > -        _flushSchema = true;
> > -        Schema[] schemas = _schema.getSchemas();
> > -        Table[] tables;
> > -        Column[] cols;
> > -        for (int i = 0; i < schemas.length; i++) {
> > -            tables = schemas[i].getTables();
> > -            for (int j = 0; j < tables.length; j++) {
> > -                if (tables[j].getPrimaryKey() == null)
> > -                    continue;
> > -
> > -                tables[j].getPrimaryKey().setLogical(false);
> > -                cols = tables[j].getPrimaryKey().getColumns();
> > -                for (int k = 0; k < cols.length; k++)
> > -                    cols[k].setNotNull(true);
> > -            }
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Drop mapping for given class.
> > -     */
> > -    private void drop(Class cls) {
> > -        if (cls == null)
> > -            return;
> > -
> > -        if (_dropCls == null)
> > -            _dropCls = new HashSet();
> > -        _dropCls.add(cls);
> > -        if (!SchemaTool.ACTION_DROP.equals(_schemaAction))
> > -            return;
> > -
> > -        MappingRepository repos = getRepository();
> > -        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > -        ClassMapping mapping = null;
> > -        try {
> > -            mapping = repos.getMapping(cls, null, false);
> > -        } catch (Exception e) {
> > -        }
> > -
> > -        if (mapping != null) {
> > -            _flushSchema = true;
> > -            if (_dropMap == null)
> > -                _dropMap = new HashSet();
> > -            _dropMap.add(mapping);
> > -        } else
> > -            _log.warn(_loc.get("no-drop-meta", cls));
> > -    }
> > -
> > -    ////////
> > -    // Main
> > -    ////////
> > -
> > -    /**
> > -     * Usage: java org.apache.openjpa.jdbc.meta.MappingTool [option]*
> > -     * [-action/-a &lt;refresh | add | buildSchema | drop |
> > validate | import
> > -     * | export&gt;] &lt;class name | .java file | .class file
> > | .jdo file&gt;*
> > -     * Where the following options are recognized.
> > -     * <ul>
> > -     * <li><i>-properties/-p &lt;properties file or resource&gt;</
> > i>: The
> > -     * path or resource name of a OpenJPA properties file containing
> > -     * information as outlined in {@link OpenJPAConfiguration}.
> > Optional.</li>
> > -     * <li><i>-&lt;property name&gt; &lt;property value&gt;</i>:
> > All bean
> > -     * properties of the OpenJPA {@link JDBCConfiguration} can be
> > set by
> > -     * using their   names and supplying a value. For example:
> > -     * <code>-licenseKey adslfja83r3lkadf</code></li>
> > -     * <li><i>-file/-f &lt;stdout | output file or resource&gt;</
> > i>: Use
> > -     * this option to write the planned mappings to an XML
> > document rather
> > -     * than store them in the repository. This option also
> > specifies the
> > -     * metadata file to write to if using the <code>add</code>
> > action with
> > -     * the <code>-meta true</code> flag, or the file to dump to if
> > using
> > -     * the <code>export</code> action.</li>
> > -     * <li><i>-schemaAction/-sa &lt;schema action | none&gt;</i>: The
> > -     * {@link SchemaTool} defines the actions possible. The
> > actions will
> > -     * apply to all schema components used by the mappings involved.
> > -     * Unless you are running the mapping tool on all of your
> > persistent
> > -     * types at once, be careful running schema actions that can
> > drop data.
> > -     * It is possible to accidentally drop schema components that are
> > -     * used by classes you aren't currently running the tool over.
> > The
> > -     * action defaults to <code>add</code>.</li>
> > -     * <li><i>-schemaFile/-sf &lt;stdout | output file or
> > resource&gt;</i>: Use
> > -     * this option to write the planned schema to an XML document
> > rather
> > -     * than modify the data store.</li>
> > -     * <li><i>-sqlFile/-sql &lt;stdout | output file or
> > resource&gt;</i>: Use
> > -     * this option rather to write the planned schema changes as a
> > SQL
> > -     * script rather than modifying the data store.</li>
> > -     * <li><i>-dropTables/-dt &lt;true/t | false/f&gt;</i>:
> > Corresponds to the
> > -     * same-named option in the {@link SchemaTool}.</li>
> > -     * <li><i>-dropSequences/-dsq &lt;true/t | false/f&gt;</i>:
> > Corresponds
> > -     * to the same-named option in the {@link SchemaTool}.</li>
> > -     * <li><i>-openjpaTables/-kt &lt;true/t | false/f&gt;</i>:
> > Corresponds to
> > -     * the same-named option in the {@link SchemaTool}.</li>
> > -     * <li><i>-ignoreErrors/-i &lt;true/t | false/f&gt;</i>:
> > Corresponds to the
> > -     * same-named option in the {@link SchemaTool}.</li>
> > -     * <li><i>-readSchema/-rs &lt;true/t | false/f&gt;</i>: Set
> > this to true
> > -     * to read the entire existing schema (even when false the
> > parts of
> > -     * the schema used by classes the tool is run on will still be
> > read).
> > -     * Turning on schema reading can ensure that no naming
> > conflicts will
> > -     * occur, but it can take a long time.</li>
> > -     * <li><i>-primaryKeys/-pk &lt;true/t | false/f&gt;</i>:
> > Whether primary
> > -     * keys on existing tables are manipulated. Defaults to
> > false.</li>
> > -     * <li><i>-foreignKeys/-fk &lt;true/t | false/f&gt;</i>:
> > Whether foreign
> > -     * keys on existing tables are manipulated. Defaults to
> > false.</li>
> > -     * <li><i>-indexes/-ix &lt;true/t | false/f&gt;</i>: Whether
> > indexes on
> > -     * existing tables are manipulated. Defaults to false.</li>
> > -     * <li><i>-sequences/-sq &lt;true/t | false/f&gt;</i>: Whether
> > sequences
> > -     * are manipulated. Defaults to true.</li>
> > -     * <li><i>-schemas/-s &lt;schema and table names&gt;</i>: A
> > list of schemas
> > -     * and/or tables to read. Corresponds to the
> > -     * same-named option in the {@link SchemaGenerator}. This option
> > -     * is ignored if <code>readSchema</code> is false.</li>
> > -     * <li><i>-meta/-m &lt;true/t | false/f&gt;</i>: Whether the
> > given action
> > -     * applies to metadata as well as mappings.</li>
> > -     * </ul>
> > -     *  The various actions are as follows.
> > -     * <ul>
> > -     * <li><i>refresh</i>: Bring the mapping information up-to-date
> > -     * with the class definitions. OpenJPA will attempt to use any
> > provided
> > -     * mapping information, and fill in missing information. If the
> > -     * provided information conflicts with the class definition, the
> > -     * conflicting information will be discarded and the class/
> > field will
> > -     * be re-mapped to new columns/tables. This is the default
> > action.</li>
> > -     * <li><i>add</i>: If used with the <code>-meta</code> option,
> > adds new
> > -     * default metadata for the given class(es). Otherwise, brings
> > the
> > -     * mapping information up-to-date with the class
> > -     * definitions. OpenJPA will attempt to use any provided mapping
> > -     * information, and fill in missing information. OpenJPA will
> > fail if
> > -     * the provided information conflicts with the class
> > definition.</li>
> > -     * <li><i>buildSchema</i>: Create the schema matching the
> > existing
> > -     * mappings for the given class(es). Any invalid mapping
> > information
> > -     * will cause an exception.</li>
> > -     * <li><i>drop</i>: Delete mappings for the given classes. If
> > used with
> > -     * the <code>-meta</code> option, also deletes metadata.</li>
> > -     * <li><i>validate</i>: Validate the given mappings. The mapping
> > -     * repository and schema will not be affected.</li>
> > -     * <li><i>import</i>: Import mappings from an XML document and
> > store
> > -     * them as the current system mappings.</li>
> > -     * <li><i>export</i>: Dump the current mappings for the given
> > classes to
> > -     * an XML document specified by the <code>file</code> option.</
> > li>
> > -     * If used with the <code>-meta</code> option, the metadata
> > will be
> > -     * included in the export.
> > -     * </ul>
> > -     *  Each class supplied as an argument must have valid
> > metadata. If
> > -     * no class arguments are given, the tool runs on all metadata
> > files in
> > -     * the CLASSPATH.
> > -     *  Examples:
> > -     * <ul>
> > -     * <li>Refresh the mappings for given package, without
> > dropping any
> > -     * schema components:<br />
> > -     * <code>java org.apache.openjpa.jdbc.meta.MappingTool
> > mypackage.jdo</code></li>
> > -     * <li>Refresh the mappings for all persistent classes in the
> > classpath,
> > -     * dropping any unused columns and even tables:<br />
> > -     * <code>java org.apache.openjpa.jdbc.meta.MappingTool -sa
> > refresh
> > -     * -dt true</code></li>
> > -     * <li>Make sure the mappings you've created by hand match the
> > object
> > -     * model and schema:<br />
> > -     * <code>java org.apache.openjpa.jbdc.meta.MappingTool
> > -     * -a validate Person.java</code></li>
> > -     * <li>Remove the recorded mapping for a given class:<br />
> > -     * <code>java org.apache.openjpa.jbdc.meta.MappingTool
> > -     * -a drop Person.java</code></li>
> > -     * <li>Record the current mappings in an XML file:<br />
> > -     * <code>java org.apache.openjpa.jdbc.meta.MappingTool
> > -     * -f mypackage.orm -a export mypackage.jdo</code></li>
> > -     * </ul>
> > -     */
> > -    public static void main(String[] args)
> > -        throws IOException, SQLException {
> > -        Options opts = new Options();
> > -        args = opts.setFromCmdLine(args);
> > -        JDBCConfiguration conf = new JDBCConfigurationImpl();
> > -        try {
> > -            if (!run(conf, args, opts))
> > -                System.err.println(_loc.get("tool-usage"));
> > -        } finally {
> > -            conf.close();
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Run the tool. Returns false if invalid options are given.
> > -     *
> > -     * @see #main
> > -     */
> > -    public static boolean run(JDBCConfiguration conf, String[] args,
> > -        Options opts)
> > -        throws IOException, SQLException {
> > -        if (opts.containsKey("help") || opts.containsKey("-help"))
> > -            return false;
> > -
> > -        // flags
> > -        Flags flags = new Flags();
> > -        flags.action = opts.removeProperty("action", "a",
> > flags.action);
> > -        flags.schemaAction = opts.removeProperty("schemaAction",
> > "sa",
> > -            flags.schemaAction);
> > -        flags.dropTables = opts.removeBooleanProperty
> > -            ("dropTables", "dt", flags.dropTables);
> > -        flags.openjpaTables = opts.removeBooleanProperty
> > -            ("openjpaTables", "ot", flags.openjpaTables);
> > -        flags.dropSequences = opts.removeBooleanProperty
> > -            ("dropSequences", "dsq", flags.dropSequences);
> > -        flags.readSchema = opts.removeBooleanProperty
> > -            ("readSchema", "rs", flags.readSchema);
> > -        flags.primaryKeys = opts.removeBooleanProperty
> > -            ("primaryKeys", "pk", flags.primaryKeys);
> > -        flags.indexes = opts.removeBooleanProperty("indexes", "ix",
> > -            flags.indexes);
> > -        flags.foreignKeys = opts.removeBooleanProperty
> > ("foreignKeys", "fk",
> > -            flags.foreignKeys);
> > -        flags.sequences = opts.removeBooleanProperty("sequences",
> > "sq",
> > -            flags.sequences);
> > -        flags.ignoreErrors = opts.removeBooleanProperty
> > -            ("ignoreErrors", "i", flags.ignoreErrors);
> > -        flags.meta = opts.removeBooleanProperty("meta", "m",
> > flags.meta);
> > -        String fileName = opts.removeProperty("file", "f", null);
> > -        String schemaFileName = opts.removeProperty("schemaFile",
> > "sf", null);
> > -        String sqlFileName = opts.removeProperty("sqlFile", "sql",
> > null);
> > -        String schemas = opts.removeProperty("s");
> > -        if (schemas != null)
> > -            opts.setProperty("schemas", schemas);
> > -
> > -        Configurations.populateConfiguration(conf, opts);
> > -        ClassLoader loader = conf.getClassResolverInstance().
> > -            getClassLoader(MappingTool.class, null);
> > -        if (flags.meta && ACTION_ADD.equals(flags.action))
> > -            flags.metaDataFile = Files.getFile(fileName, loader);
> > -        else
> > -            flags.mappingWriter = Files.getWriter(fileName, loader);
> > -        flags.schemaWriter = Files.getWriter(schemaFileName, loader);
> > -        flags.sqlWriter = Files.getWriter(sqlFileName, loader);
> > -
> > -        return run(conf, args, flags, loader);
> > -    }
> > -
> > -    /**
> > -     * Run the tool. Return false if an invalid option was given.
> > -     */
> > -    public static boolean run(JDBCConfiguration conf, String[] args,
> > -        Flags flags, ClassLoader loader)
> > -        throws IOException, SQLException {
> > -        // default action based on whether the mapping defaults
> > fills in
> > -        // missing info
> > -        if (flags.action == null) {
> > -            if (conf.getMappingDefaultsInstance
> > ().defaultMissingInfo())
> > -                flags.action = ACTION_BUILD_SCHEMA;
> > -            else
> > -                flags.action = ACTION_REFRESH;
> > -        }
> > -
> > -        // collect the classes to act on
> > -        Log log = conf.getLog(OpenJPAConfiguration.LOG_TOOL);
> > -        Collection classes = null;
> > -        if (args.length == 0) {
> > -            if (ACTION_IMPORT.equals(flags.action))
> > -                return false;
> > -            log.info(_loc.get("running-all-classes"));
> > -            classes = conf.getMappingRepositoryInstance().
> > -                loadPersistentTypes(true, loader);
> > -        } else {
> > -            classes = new HashSet();
> > -            ClassArgParser classParser =
> > conf.getMetaDataRepositoryInstance().
> > -                getMetaDataFactory().newClassArgParser();
> > -            classParser.setClassLoader(loader);
> > -            Class[] parsed;
> > -            for (int i = 0; args != null && i < args.length; i++) {
> > -                parsed = classParser.parseTypes(args[i]);
> > -                classes.addAll(Arrays.asList(parsed));
> > -            }
> > -        }
> > -
> > -        Class[] act = (Class[]) classes.toArray(new Class
> > [classes.size()]);
> > -        if (ACTION_EXPORT.equals(flags.action)) {
> > -            // run exports until the first export succeeds
> > -            ImportExport[] instances = newImportExports();
> > -            for (int i = 0; i < instances.length; i++) {
> > -                if (instances[i].exportMappings(conf, act,
> > flags.meta, log,
> > -                    flags.mappingWriter))
> > -                    return true;
> > -            }
> > -            return false;
> > -        }
> > -        if (ACTION_IMPORT.equals(flags.action)) {
> > -            // run exports until the first export succeeds
> > -            ImportExport[] instances = newImportExports();
> > -            for (int i = 0; i < instances.length; i++) {
> > -                if (instances[i].importMappings(conf, act, args,
> > flags.meta,
> > -                    log, loader))
> > -                    return true;
> > -            }
> > -            return false;
> > -        }
> > -
> > -        MappingTool tool;
> > -        try {
> > -            tool = new MappingTool(conf, flags.action, flags.meta);
> > -        } catch (IllegalArgumentException iae) {
> > -            return false;
> > -        }
> > -
> > -        // setup the tool
> > -        tool.setIgnoreErrors(flags.ignoreErrors);
> > -        tool.setMetaDataFile(flags.metaDataFile);
> > -        tool.setMappingWriter(flags.mappingWriter);
> > -        tool.setSchemaAction(flags.schemaAction);
> > -        tool.setSchemaWriter(flags.schemaWriter);
> > -        tool.setReadSchema(flags.readSchema
> > -            && !ACTION_VALIDATE.equals(flags.action));
> > -        tool.setPrimaryKeys(flags.primaryKeys);
> > -        tool.setForeignKeys(flags.foreignKeys);
> > -        tool.setIndexes(flags.indexes);
> > -        tool.setSequences(flags.sequences || flags.dropSequences);
> > -
> > -        // make sure to do this after other settings so that other
> > settings
> > -        // are passed on to schema tool
> > -        tool.getSchemaTool().setDropTables(flags.dropTables);
> > -        tool.getSchemaTool().setDropSequences(flags.dropSequences);
> > -        tool.getSchemaTool().setWriter(flags.sqlWriter);
> > -        tool.getSchemaTool().setOpenJPATables(flags.openjpaTables);
> > -
> > -        // and run the action
> > -        for (int i = 0; i < act.length; i++) {
> > -            log.info(_loc.get("tool-running", act[i], flags.action));
> > -            if (i == 0 && flags.readSchema)
> > -                log.info(_loc.get("tool-time"));
> > -            tool.run(act[i]);
> > -        }
> > -        log.info(_loc.get("tool-record"));
> > -        tool.record();
> > -        return true;
> > -    }
> > -
> > -    /**
> > -     * Create an {@link ImportExport} instance.
> > -     */
> > -    private static ImportExport[] newImportExports() {
> > -        try {
> > -            Class[] types = Services.getImplementorClasses
> > (ImportExport.class);
> > -            ImportExport[] instances = new ImportExport
> > [types.length];
> > -            for (int i = 0; i < types.length; i++)
> > -                instances[i] = (ImportExport) types[i].newInstance();
> > -            return instances;
> > -        } catch (Throwable t) {
> > -            throw new InternalException(_loc.get("importexport-
> > instantiate"),t);
> > -        }
> > -    }
> > -
> > -    /**
> > -     * Run flags.
> > -     */
> > -    public static class Flags {
> > -
> > -        public String action = null;
> > -        public boolean meta = false;
> > -        public String schemaAction = SchemaTool.ACTION_ADD;
> > -        public File metaDataFile = null;
> > -        public Writer mappingWriter = null;
> > -        public Writer schemaWriter = null;
> > -        public Writer sqlWriter = null;
> > -        public boolean ignoreErrors = false;
> > -        public boolean readSchema = false;
> > -        public boolean dropTables = false;
> > -        public boolean openjpaTables = false;
> > -        public boolean dropSequences = false;
> > -        public boolean sequences = true;
> > -        public boolean primaryKeys = false;
> > -        public boolean foreignKeys = false;
> > -        public boolean indexes = false;
> > -    }
> > -
> > -    /**
> > -     * Helper used to import and export mapping data.
> > -     */
> > -    public static interface ImportExport {
> > -
> > -        /**
> > -         * Import mappings for the given classes based on the
> > given arguments.
> > -         */
> > -        public boolean importMappings(JDBCConfiguration conf, Class
> > [] act,
> > -            String[] args, boolean meta, Log log, ClassLoader loader)
> > -            throws IOException;
> > -
> > -        /**
> > -         * Export mappings for the given classes based on the
> > given arguments.
> > -         */
> > -        public boolean exportMappings(JDBCConfiguration conf, Class
> > [] act,
> > -            boolean meta, Log log, Writer writer)
> > -            throws IOException;
> > -    }
> > -}
> > +/*
> > + * Copyright 2006 The Apache Software Foundation.
> > + *
> > + * Licensed 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.openjpa.jdbc.meta;
> > +
> > +import java.io.File;
> > +import java.io.IOException;
> > +import java.io.PrintWriter;
> > +import java.io.Writer;
> > +import java.sql.SQLException;
> > +import java.util.Arrays;
> > +import java.util.Collection;
> > +import java.util.HashMap;
> > +import java.util.HashSet;
> > +import java.util.Iterator;
> > +import java.util.Map;
> > +import java.util.Set;
> > +
> > +import org.apache.openjpa.conf.OpenJPAConfiguration;
> > +import org.apache.openjpa.jdbc.conf.JDBCConfiguration;
> > +import org.apache.openjpa.jdbc.conf.JDBCConfigurationImpl;
> > +import org.apache.openjpa.jdbc.kernel.JDBCSeq;
> > +import org.apache.openjpa.jdbc.schema.Column;
> > +import org.apache.openjpa.jdbc.schema.DynamicSchemaFactory;
> > +import org.apache.openjpa.jdbc.schema.LazySchemaFactory;
> > +import org.apache.openjpa.jdbc.schema.Schema;
> > +import org.apache.openjpa.jdbc.schema.SchemaGenerator;
> > +import org.apache.openjpa.jdbc.schema.SchemaGroup;
> > +import org.apache.openjpa.jdbc.schema.SchemaSerializer;
> > +import org.apache.openjpa.jdbc.schema.SchemaTool;
> > +import org.apache.openjpa.jdbc.schema.Table;
> > +import org.apache.openjpa.jdbc.schema.XMLSchemaSerializer;
> > +import org.apache.openjpa.jdbc.sql.DBDictionary;
> > +import org.apache.openjpa.kernel.Seq;
> > +import org.apache.openjpa.lib.conf.Configurations;
> > +import org.apache.openjpa.lib.log.Log;
> > +import org.apache.openjpa.lib.meta.ClassArgParser;
> > +import org.apache.openjpa.lib.util.Files;
> > +import org.apache.openjpa.lib.util.Localizer;
> > +import org.apache.openjpa.lib.util.Options;
> > +import org.apache.openjpa.lib.util.Services;
> > +import org.apache.openjpa.meta.ClassMetaData;
> > +import org.apache.openjpa.meta.FieldMetaData;
> > +import org.apache.openjpa.meta.JavaTypes;
> > +import org.apache.openjpa.meta.MetaDataFactory;
> > +import org.apache.openjpa.meta.MetaDataModes;
> > +import org.apache.openjpa.meta.QueryMetaData;
> > +import org.apache.openjpa.meta.SequenceMetaData;
> > +import org.apache.openjpa.meta.ValueStrategies;
> > +import org.apache.openjpa.util.GeneralException;
> > +import org.apache.openjpa.util.InternalException;
> > +import org.apache.openjpa.util.MetaDataException;
> > +
> > +/**
> > + * Tool for manipulating class mappings and associated schema.
> > + *
> > + * @author Abe White
> > + */
> > +public class MappingTool
> > +    implements MetaDataModes {
> > +
> > +    public static final String SCHEMA_ACTION_NONE = "none";
> > +
> > +    public static final String ACTION_ADD = "add";
> > +    public static final String ACTION_REFRESH = "refresh";
> > +    public static final String ACTION_BUILD_SCHEMA = "buildSchema";
> > +    public static final String ACTION_DROP = "drop";
> > +    public static final String ACTION_VALIDATE = "validate";
> > +    public static final String ACTION_EXPORT = "export";
> > +    public static final String ACTION_IMPORT = "import";
> > +
> > +    public static final String[] ACTIONS = new String[]{
> > +        ACTION_ADD,
> > +        ACTION_REFRESH,
> > +        ACTION_BUILD_SCHEMA,
> > +        ACTION_DROP,
> > +        ACTION_VALIDATE,
> > +        ACTION_EXPORT,
> > +        ACTION_IMPORT,
> > +    };
> > +
> > +    private static Localizer _loc = Localizer.forPackage
> > (MappingTool.class);
> > +
> > +    private final JDBCConfiguration _conf;
> > +    private final Log _log;
> > +    private final String _action;
> > +    private final boolean _meta;
> > +    private final int _mode;
> > +
> > +    private MappingRepository _repos = null;
> > +    private SchemaGroup _schema = null;
> > +    private SchemaTool _schemaTool = null;
> > +    private String _schemaAction = SchemaTool.ACTION_ADD;
> > +    private boolean _readSchema = false;
> > +    private boolean _pks = false;
> > +    private boolean _fks = false;
> > +    private boolean _indexes = false;
> > +    private boolean _seqs = true;
> > +    private boolean _dropUnused = true;
> > +    private boolean _ignoreErrors = false;
> > +    private File _file = null;
> > +    private Writer _mappingWriter = null;
> > +    private Writer _schemaWriter = null;
> > +
> > +    // buffer metadatas to be dropped
> > +    private Set _dropCls = null;
> > +    private Set _dropMap = null;
> > +    private boolean _flush = false;
> > +    private boolean _flushSchema = false;
> > +
> > +    /**
> > +     * Constructor. Supply configuration and action.
> > +     */
> > +    public MappingTool(JDBCConfiguration conf, String action,
> > boolean meta) {
> > +        _conf = conf;
> > +        _log = conf.getLog(JDBCConfiguration.LOG_METADATA);
> > +        _meta = meta;
> > +
> > +        if (action == null)
> > +            _action = ACTION_REFRESH;
> > +        else if (!Arrays.asList(ACTIONS).contains(action))
> > +            throw new IllegalArgumentException("action == " +
> > action);
> > +        else
> > +            _action = action;
> > +
> > +        if (meta && ACTION_ADD.equals(_action))
> > +            _mode = MODE_META;
> > +        else if (meta && ACTION_DROP.equals(_action))
> > +            _mode = MODE_META | MODE_MAPPING | MODE_QUERY;
> > +        else
> > +            _mode = MODE_MAPPING;
> > +    }
> > +
> > +    /**
> > +     * The action supplied on construction.
> > +     */
> > +    public String getAction() {
> > +        return _action;
> > +    }
> > +
> > +    /**
> > +     * Whether the action works on metadata as well as mappings.
> > +     */
> > +    public boolean isMetaDataAction() {
> > +        return _meta;
> > +    }
> > +
> > +    /**
> > +     * The schema modification policy, or <code>none</code>. See the
> > +     * ACTION constants in {@link SchemaTool}. Defaults to
> > +     * {@link SchemaTool#ACTION_ADD}.
> > +     */
> > +    public String getSchemaAction() {
> > +        return _schemaAction;
> > +    }
> > +
> > +    /**
> > +     * The schema modification policy, or <code>none</code>. See the
> > +     * ACTION constants in {@link SchemaTool}. Defaults to
> > +     * {@link SchemaTool#ACTION_ADD}.
> > +     */
> > +    public void setSchemaAction(String schemaAction) {
> > +        _schemaAction = schemaAction;
> > +    }
> > +
> > +    /**
> > +     * Set to true to read the entire schema before mapping.
> > +     * Leaving this option false saves time, but is dangerous when
> > adding
> > +     * new mappings, because without full knowledge of the
> > existing schema the
> > +     * mapping tool might create tables or indexes that conflict with
> > +     * existing components.
> > +     */
> > +    public boolean getReadSchema() {
> > +        return _readSchema;
> > +    }
> > +
> > +    /**
> > +     * Set to true to read the entire schema before mapping.
> > +     * Leaving this option false saves time, but is dangerous when
> > adding
> > +     * new mappings, because without full knowledge of the
> > existing schema the
> > +     * mapping tool might create tables or indexes that conflict with
> > +     * existing components.
> > +     */
> > +    public void setReadSchema(boolean readSchema) {
> > +        _readSchema = readSchema;
> > +    }
> > +
> > +    /**
> > +     * Whether to manipulate sequences. Defaults to true.
> > +     */
> > +    public boolean getSequences() {
> > +        return _seqs;
> > +    }
> > +
> > +    /**
> > +     * Whether to manipulate sequences. Defaults to true.
> > +     */
> > +    public void setSequences(boolean seqs) {
> > +        _seqs = seqs;
> > +    }
> > +
> > +    /**
> > +     * Whether indexes on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public boolean getIndexes() {
> > +        return _indexes;
> > +    }
> > +
> > +    /**
> > +     * Whether indexes on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public void setIndexes(boolean indexes) {
> > +        _indexes = indexes;
> > +    }
> > +
> > +    /**
> > +     * Whether foreign keys on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public boolean getForeignKeys() {
> > +        return _fks;
> > +    }
> > +
> > +    /**
> > +     * Whether foreign keys on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public void setForeignKeys(boolean fks) {
> > +        _fks = fks;
> > +    }
> > +
> > +    /**
> > +     * Whether primary keys on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public boolean getPrimaryKeys() {
> > +        return _pks;
> > +    }
> > +
> > +    /**
> > +     * Whether primary keys on existing tables should be manipulated.
> > +     * Defaults to false.
> > +     */
> > +    public void setPrimaryKeys(boolean pks) {
> > +        _pks = pks;
> > +    }
> > +
> > +    /**
> > +     * Whether schema components that are unused by any mapping
> > will be
> > +     * dropped from this tool's {@link SchemaGroup}, and,
> > depending on
> > +     * the schema action, from the database. Defaults to true.
> > +     */
> > +    public boolean getDropUnusedComponents() {
> > +        return _dropUnused;
> > +    }
> > +
> > +    /**
> > +     * Whether schema components that are unused by any mapping
> > will be
> > +     * dropped from this tool's {@link SchemaGroup}, and,
> > depending on
> > +     * the schema action, from the database. Defaults to true.
> > +     */
> > +    public void setDropUnusedComponents(boolean dropUnused) {
> > +        _dropUnused = dropUnused;
> > +    }
> > +
> > +    /**
> > +     * Whether and SQL errors should cause a failure or just issue
> > a warning.
> > +     */
> > +    public void setIgnoreErrors(boolean ignoreErrors) {
> > +        _ignoreErrors = ignoreErrors;
> > +    }
> > +
> > +    /**
> > +     * Whether and SQL errors should cause a failure or just issue
> > a warning.
> > +     */
> > +    public boolean getIgnoreErrors() {
> > +        return _ignoreErrors;
> > +    }
> > +
> > +    /**
> > +     * Return the schema tool to use for schema modification.
> > +     */
> > +    public SchemaTool getSchemaTool() {
> > +        if (_schemaTool == null)
> > +            _schemaTool = newSchemaTool(_schemaAction);
> > +        return _schemaTool;
> > +    }
> > +
> > +    /**
> > +     * Return the schema tool to use for schema modification.
> > +     */
> > +    private SchemaTool newSchemaTool(String action) {
> > +        if (SCHEMA_ACTION_NONE.equals(action))
> > +            action = null;
> > +        SchemaTool tool = new SchemaTool(_conf, action);
> > +        tool.setIgnoreErrors(getIgnoreErrors());
> > +        tool.setPrimaryKeys(getPrimaryKeys());
> > +        tool.setForeignKeys(getForeignKeys());
> > +        tool.setIndexes(getIndexes());
> > +        tool.setSequences(getSequences());
> > +        return tool;
> > +    }
> > +
> > +    /**
> > +     * Set the schema tool to use for schema modification.
> > +     */
> > +    public void setSchemaTool(SchemaTool tool) {
> > +        _schemaTool = tool;
> > +    }
> > +
> > +    /**
> > +     * The stream to export the planned schema to as an XML document.
> > +     * If non-null, then the database schema will not be altered.
> > +     */
> > +    public Writer getSchemaWriter() {
> > +        return _schemaWriter;
> > +    }
> > +
> > +    /**
> > +     * The stream to export the planned schema to as an XML document.
> > +     * If non-null, then the database schema will not be altered.
> > +     */
> > +    public void setSchemaWriter(Writer schemaWriter) {
> > +        _schemaWriter = schemaWriter;
> > +    }
> > +
> > +    /**
> > +     * The stream to export the planned mappings to as an XML
> > document.
> > +     * If non-null, then the mapping repository will not be altered.
> > +     */
> > +    public Writer getMappingWriter() {
> > +        return _mappingWriter;
> > +    }
> > +
> > +    /**
> > +     * The stream to export the planned mappings to as an XML
> > document.
> > +     * If non-null, then the mapping repository will not be altered.
> > +     */
> > +    public void setMappingWriter(Writer mappingWriter) {
> > +        _mappingWriter = mappingWriter;
> > +    }
> > +
> > +    /**
> > +     * If adding metadata, the metadata file to add to.
> > +     */
> > +    public File getMetaDataFile() {
> > +        return _file;
> > +    }
> > +
> > +    /**
> > +     * If adding metadata, the metadata file to add to.
> > +     */
> > +    public void setMetaDataFile(File file) {
> > +        _file = file;
> > +    }
> > +
> > +    /**
> > +     * Return the repository to use to access mapping information.
> > +     * Defaults to a new {@link MappingRepository}.
> > +     */
> > +    public MappingRepository getRepository() {
> > +        if (_repos == null) {
> > +            _repos = _conf.newMappingRepositoryInstance();
> > +            _repos.setSchemaGroup(getSchemaGroup());
> > +            _repos.setValidate(_repos.VALIDATE_UNENHANCED, false);
> > +        }
> > +        return _repos;
> > +    }
> > +
> > +    /**
> > +     * Set the repository to use to access mapping information.
> > +     */
> > +    public void setRepository(MappingRepository repos) {
> > +        _repos = repos;
> > +    }
> > +
> > +    /**
> > +     * Return the schema group to use in mapping. If none has been
> > set, the
> > +     * schema will be generated from the database.
> > +     */
> > +    public SchemaGroup getSchemaGroup() {
> > +        if (_schema == null) {
> > +            if (ACTION_BUILD_SCHEMA.equals(_action)) {
> > +                DynamicSchemaFactory factory = new
> > DynamicSchemaFactory();
> > +                factory.setConfiguration(_conf);
> > +                _schema = factory;
> > +            } else if (_readSchema
> > +                || SchemaTool.ACTION_RETAIN.equals(_schemaAction)
> > +                || SchemaTool.ACTION_REFRESH.equals(_schemaAction)) {
> > +                _schema = (SchemaGroup) getSchemaTool
> > ().getDBSchemaGroup().
> > +                    clone();
> > +            } else {
> > +                // with this we'll just read tables as different
> > mappings
> > +                // look for them
> > +                LazySchemaFactory factory = new LazySchemaFactory();
> > +                factory.setConfiguration(_conf);
> > +                factory.setPrimaryKeys(getPrimaryKeys());
> > +                factory.setForeignKeys(getForeignKeys());
> > +                factory.setIndexes(getIndexes());
> > +                _schema = factory;
> > +            }
> > +
> > +            if (_schema.getSchemas().length == 0)
> > +                _schema.addSchema();
> > +        }
> > +        return _schema;
> > +    }
> > +
> > +    /**
> > +     * Set the schema to use in mapping.
> > +     */
> > +    public void setSchemaGroup(SchemaGroup schema) {
> > +        _schema = schema;
> > +    }
> > +
> > +    /**
> > +     * Reset the internal repository. This is called automatically
> > after
> > +     * every {@link #record}.
> > +     */
> > +    public void clear() {
> > +        _repos = null;
> > +        _schema = null;
> > +        _schemaTool = null;
> > +        _flush = false;
> > +        _flushSchema = false;
> > +        if (_dropCls != null)
> > +            _dropCls.clear();
> > +        if (_dropMap != null)
> > +            _dropMap.clear();
> > +    }
> > +
> > +    /**
> > +     * Records the changes that have been made to both the
> > mappings and the
> > +     * associated schema, and clears the tool for further use.
> > This also
> > +     * involves clearing the internal mapping repository.
> > +     */
> > +    public void record() {
> > +        MappingRepository repos = getRepository();
> > +        MetaDataFactory io = repos.getMetaDataFactory();
> > +        ClassMapping[] mappings;
> > +        if (!ACTION_DROP.equals(_action))
> > +            mappings = repos.getMappings();
> > +        else if (_dropMap != null)
> > +            mappings = (ClassMapping[]) _dropMap.toArray
> > +                (new ClassMapping[_dropMap.size()]);
> > +        else
> > +            mappings = new ClassMapping[0];
> > +
> > +        try {
> > +            if (_dropCls != null && !_dropCls.isEmpty()) {
> > +                Class[] cls = (Class[]) _dropCls.toArray
> > +                    (new Class[_dropCls.size()]);
> > +                if (!io.drop(cls, _mode, null))
> > +                    _log.warn(_loc.get("bad-drop", _dropCls));
> > +            }
> > +
> > +            if (_flushSchema) {
> > +                // drop portions of the known schema that no
> > mapping uses, and
> > +                // add sequences used for value generation
> > +                if (_dropUnused)
> > +                    dropUnusedSchemaComponents(mappings);
> > +                addSequenceComponents(mappings);
> > +
> > +                // now run the schematool as long as we're doing
> > some schema
> > +                // action and the user doesn't just want an xml
> > output
> > +                if (!SCHEMA_ACTION_NONE.equals(_schemaAction)
> > +                    && (_schemaWriter == null || (_schemaTool != null
> > +                    && _schemaTool.getWriter() != null))) {
> > +                    SchemaTool tool = getSchemaTool();
> > +                    tool.setSchemaGroup(getSchemaGroup());
> > +                    tool.run();
> > +                    tool.record();
> > +                }
> > +
> > +                // xml output of schema?
> > +                if (_schemaWriter != null) {
> > +                    // serialize the planned schema to the stream
> > +                    SchemaSerializer ser = new XMLSchemaSerializer
> > (_conf);
> > +                    ser.addAll(getSchemaGroup());
> > +                    ser.serialize(_schemaWriter, ser.PRETTY);
> > +                    _schemaWriter.flush();
> > +                }
> > +            }
> > +            if (!_flush)
> > +                return;
> > +
> > +            QueryMetaData[] queries = repos.getQueryMetaDatas();
> > +            SequenceMetaData[] seqs = repos.getSequenceMetaDatas();
> > +            Map output = null;
> > +
> > +            // if we're outputting to stream, set all metas to
> > same file so
> > +            // they get placed in single string
> > +            if (_mappingWriter != null) {
> > +                output = new HashMap();
> > +                File tmp = new File("openjpatmp");
> > +                for (int i = 0; i < mappings.length; i++)
> > +                    mappings[i].setSource(tmp, mappings
> > [i].SRC_OTHER);
> > +                for (int i = 0; i < queries.length; i++)
> > +                    queries[i].setSource(tmp, queries
> > [i].getSourceScope(),
> > +                        queries[i].SRC_OTHER);
> > +                for (int i = 0; i < seqs.length; i++)
> > +                    seqs[i].setSource(tmp, seqs[i].getSourceScope(),
> > +                        seqs[i].SRC_OTHER);
> > +            }
> > +
> > +            // store
> > +            if (!io.store(mappings, queries, seqs, _mode, output))
> > +                throw new MetaDataException(_loc.get("bad-store"));
> > +
> > +            // write to stream
> > +            if (_mappingWriter != null) {
> > +                PrintWriter out = new PrintWriter(_mappingWriter);
> > +                for (Iterator itr = output.values().iterator();
> > +                    itr.hasNext();)
> > +                    out.println((String) itr.next());
> > +                out.flush();
> > +            }
> > +        }
> > +        catch (RuntimeException re) {
> > +            throw re;
> > +        } catch (Exception e) {
> > +            throw new GeneralException(e);
> > +        } finally {
> > +            clear();
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Drops schema components that appear to be unused from the
> > local
> > +     * copy of the schema group.
> > +     */
> > +    private void dropUnusedSchemaComponents(ClassMapping[]
> > mappings) {
> > +        FieldMapping[] fields;
> > +        for (int i = 0; i < mappings.length; i++) {
> > +            mappings[i].refSchemaComponents();
> > +            mappings[i].getDiscriminator().refSchemaComponents();
> > +            mappings[i].getVersion().refSchemaComponents();
> > +            fields = mappings[i].getDefinedFieldMappings();
> > +            for (int j = 0; j < fields.length; j++)
> > +                fields[j].refSchemaComponents();
> > +        }
> > +
> > +        // also allow the dbdictionary to ref any schema
> > components that
> > +        // it adds apart from mappings
> > +        SchemaGroup group = getSchemaGroup();
> > +        Schema[] schemas = group.getSchemas();
> > +        Table[] tables;
> > +        DBDictionary dict = _conf.getDBDictionaryInstance();
> > +        for (int i = 0; i < schemas.length; i++) {
> > +            tables = schemas[i].getTables();
> > +            for (int j = 0; j < tables.length; j++)
> > +                dict.refSchemaComponents(tables[j]);
> > +        }
> > +
> > +        group.removeUnusedComponents();
> > +    }
> > +
> > +    /**
> > +     * Add tables used by sequences to the given schema.
> > +     */
> > +    private void addSequenceComponents(ClassMapping[] mappings) {
> > +        SchemaGroup group = getSchemaGroup();
> > +        for (int i = 0; i < mappings.length; i++)
> > +            addSequenceComponents(mappings[i], group);
> > +    }
> > +
> > +    /**
> > +     * Add tables used by sequences to the given schema.
> > +     */
> > +    private void addSequenceComponents(ClassMapping mapping,
> > +        SchemaGroup group) {
> > +        SequenceMetaData smd = mapping.getIdentitySequenceMetaData();
> > +        Seq seq = null;
> > +        if (smd != null)
> > +            seq = smd.getInstance(null);
> > +        else if (mapping.getIdentityStrategy() ==
> > ValueStrategies.NATIVE
> > +            || (mapping.getIdentityStrategy() == ValueStrategies.NONE
> > +            && mapping.getIdentityType() ==
> > ClassMapping.ID_DATASTORE))
> > +            seq = _conf.getSequenceInstance();
> > +
> > +        if (seq instanceof JDBCSeq)
> > +            ((JDBCSeq) seq).addSchema(mapping, group);
> > +
> > +        FieldMapping[] fmds;
> > +        if (mapping.getEmbeddingMetaData() == null)
> > +            fmds = mapping.getDefinedFieldMappings();
> > +        else
> > +            fmds = mapping.getFieldMappings();
> > +        for (int i = 0; i < fmds.length; i++) {
> > +            smd = fmds[i].getValueSequenceMetaData();
> > +            if (smd != null) {
> > +                seq = smd.getInstance(null);
> > +                if (seq instanceof JDBCSeq)
> > +                    ((JDBCSeq) seq).addSchema(mapping, group);
> > +            } else if (fmds[i].getEmbeddedMapping() != null)
> > +                addSequenceComponents(fmds[i].getEmbeddedMapping
> > (), group);
> > +        }
> > +    }
> > +
> > +    ///////////
> > +    // Actions
> > +    ///////////
> > +
> > +    /**
> > +     * Run the configured action on the given instance.
> > +     */
> > +    public void run(Class cls) {
> > +        if (ACTION_ADD.equals(_action)) {
> > +            if (_meta)
> > +                addMeta(cls);
> > +            else
> > +                add(cls);
> > +        } else if (ACTION_REFRESH.equals(_action))
> > +            refresh(cls);
> > +        else if (ACTION_BUILD_SCHEMA.equals(_action))
> > +            buildSchema(cls);
> > +        else if (ACTION_DROP.equals(_action))
> > +            drop(cls);
> > +        else if (ACTION_VALIDATE.equals(_action))
> > +            validate(cls);
> > +    }
> > +
> > +    /**
> > +     * Add the mapping for the given instance.
> > +     */
> > +    private void add(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        MappingRepository repos = getRepository();
> > +        repos.setStrategyInstaller(new MappingStrategyInstaller
> > (repos));
> > +        if (getMapping(repos, cls, true) != null) {
> > +            _flush = true;
> > +            _flushSchema = true;
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Return the mapping for the given type, or null if the type is
> > +     * persistence-aware.
> > +     */
> > +    private static ClassMapping getMapping(MappingRepository
> > repos, Class cls,
> > +        boolean validate) {
> > +        // this will parse all possible metadata rsrcs looking for
> > cls, so
> > +        // will detect if p-aware
> > +        ClassMapping mapping = repos.getMapping(cls, null, false);
> > +        if (mapping != null)
> > +            return mapping;
> > +        if (!validate || cls.isInterface()
> > +            || repos.getPersistenceAware(cls) != null)
> > +            return null;
> > +        throw new MetaDataException(_loc.get("no-meta", cls));
> > +    }
> > +
> > +    /**
> > +     * Create a metadata for the given instance.
> > +     */
> > +    private void addMeta(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        _flush = true;
> > +        MappingRepository repos = getRepository();
> > +        repos.setResolve(MODE_MAPPING, false);
> > +        MetaDataFactory factory = repos.getMetaDataFactory();
> > +        factory.getDefaults().setIgnoreNonPersistent(false);
> > +        factory.setStoreMode(MetaDataFactory.STORE_VERBOSE);
> > +
> > +        ClassMetaData meta = repos.addMetaData(cls);
> > +        FieldMetaData[] fmds = meta.getDeclaredFields();
> > +        for (int i = 0; i < fmds.length; i++) {
> > +            if (fmds[i].getDeclaredTypeCode() == JavaTypes.OBJECT
> > +                && fmds[i].getDeclaredType() != Object.class)
> > +                fmds[i].setDeclaredTypeCode(JavaTypes.PC);
> > +        }
> > +        meta.setSource(_file, meta.getSourceType());
> > +        meta.setResolve(MODE_META, true);
> > +    }
> > +
> > +    /**
> > +     * Refresh or add the mapping for the given instance.
> > +     */
> > +    private void refresh(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        MappingRepository repos = getRepository();
> > +        repos.setStrategyInstaller(new RefreshStrategyInstaller
> > (repos));
> > +        if (getMapping(repos, cls, true) != null) {
> > +            _flush = true;
> > +            _flushSchema = true;
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Validate the mappings for the given class and its fields.
> > +     */
> > +    private void validate(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        MappingRepository repos = getRepository();
> > +        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > +        if (getMapping(repos, cls, true) != null)
> > +            _flushSchema = !SCHEMA_ACTION_NONE.equals(_schemaAction)
> > +                && !SchemaTool.ACTION_ADD.equals(_schemaAction);
> > +    }
> > +
> > +    /**
> > +     * Create the schema using the mapping for the given instance.
> > +     */
> > +    private void buildSchema(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        MappingRepository repos = getRepository();
> > +        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > +        if (getMapping(repos, cls, true) == null)
> > +            return;
> > +
> > +        // set any logical pks to non-logical so they get flushed
> > +        _flushSchema = true;
> > +        Schema[] schemas = _schema.getSchemas();
> > +        Table[] tables;
> > +        Column[] cols;
> > +        for (int i = 0; i < schemas.length; i++) {
> > +            tables = schemas[i].getTables();
> > +            for (int j = 0; j < tables.length; j++) {
> > +                if (tables[j].getPrimaryKey() == null)
> > +                    continue;
> > +
> > +                tables[j].getPrimaryKey().setLogical(false);
> > +                cols = tables[j].getPrimaryKey().getColumns();
> > +                for (int k = 0; k < cols.length; k++)
> > +                    cols[k].setNotNull(true);
> > +            }
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Drop mapping for given class.
> > +     */
> > +    private void drop(Class cls) {
> > +        if (cls == null)
> > +            return;
> > +
> > +        if (_dropCls == null)
> > +            _dropCls = new HashSet();
> > +        _dropCls.add(cls);
> > +        if (!SchemaTool.ACTION_DROP.equals(_schemaAction))
> > +            return;
> > +
> > +        MappingRepository repos = getRepository();
> > +        repos.setStrategyInstaller(new RuntimeStrategyInstaller
> > (repos));
> > +        ClassMapping mapping = null;
> > +        try {
> > +            mapping = repos.getMapping(cls, null, false);
> > +        } catch (Exception e) {
> > +        }
> > +
> > +        if (mapping != null) {
> > +            _flushSchema = true;
> > +            if (_dropMap == null)
> > +                _dropMap = new HashSet();
> > +            _dropMap.add(mapping);
> > +        } else
> > +            _log.warn(_loc.get("no-drop-meta", cls));
> > +    }
> > +
> > +    ////////
> > +    // Main
> > +    ////////
> > +
> > +    /**
> > +     * Usage: java org.apache.openjpa.jdbc.meta.MappingTool [option]*
> > +     * [-action/-a &lt;refresh | add | buildSchema | drop |
> > validate | import
> > +     * | export&gt;] &lt;class name | .java file | .class file
> > | .jdo file&gt;*
> > +     * Where the following options are recognized.
> > +     * <ul>
> > +     * <li><i>-properties/-p &lt;properties file or resource&gt;</
> > i>: The
> > +     * path or resource name of a OpenJPA properties file containing
> > +     * information as outlined in {@link OpenJPAConfiguration}.
> > Optional.</li>
> > +     * <li><i>-&lt;property name&gt; &lt;property value&gt;</i>:
> > All bean
> > +     * properties of the OpenJPA {@link JDBCConfiguration} can be
> > set by
> > +     * using their   names and supplying a value. For example:
> > +     * <code>-licenseKey adslfja83r3lkadf</code></li>
> > +     * <li><i>-file/-f &lt;stdout | output file or resource&gt;</
> > i>: Use
> > +     * this option to write the planned mappings to an XML
> > document rather
> > +     * than store them in the repository. This option also
> > specifies the
> > +     * metadata file to write to if using the <code>add</code>
> > action with
> > +     * the <code>-meta true</code> flag, or the file to dump to if
> > using
> > +     * the <code>export</code> action.</li>
> > +     * <li><i>-schemaAction/-sa &lt;schema action | none&gt;</i>: The
> > +     * {@link SchemaTool} defines the actions possible. The
> > actions will
> > +     * apply to all schema components used by the mappings involved.
> > +     * Unless you are running the mapping tool on all of your
> > persistent
> > +     * types at once, be careful running schema actions that can
> > drop data.
> > +     * It is possible to accidentally drop schema components that are
> > +     * used by classes you aren't currently running the tool over.
> > The
> > +     * action defaults to <code>add</code>.</li>
> > +     * <li><i>-schemaFile/-sf &lt;stdout | output file or
> > resource&gt;</i>: Use
> > +     * this option to write the planned schema to an XML document
> > rather
> > +     * than modify the data store.</li>
> > +     * <li><i>-sqlFile/-sql &lt;stdout | output file or
> > resource&gt;</i>: Use
> > +     * this option to write the planned schema changes as a SQL
> > +     * script rather than modifying the data store.</li>
> > +     * <li><i>-dropTables/-dt &lt;true/t | false/f&gt;</i>:
> > Corresponds to the
> > +     * same-named option in the {@link SchemaTool}.</li>
> > +     * <li><i>-dropSequences/-dsq &lt;true/t | false/f&gt;</i>:
> > Corresponds
> > +     * to the same-named option in the {@link SchemaTool}.</li>
> > +     * <li><i>-openjpaTables/-kt &lt;true/t | false/f&gt;</i>:
> > Corresponds to
> > +     * the same-named option in the {@link SchemaTool}.</li>
> > +     * <li><i>-ignoreErrors/-i &lt;true/t | false/f&gt;</i>:
> > Corresponds to the
> > +     * same-named option in the {@link SchemaTool}.</li>
> > +     * <li><i>-readSchema/-rs &lt;true/t | false/f&gt;</i>: Set
> > this to true
> > +     * to read the entire existing schema (even when false the
> > parts of
> > +     * the schema used by classes the tool is run on will still be
> > read).
> > +     * Turning on schema reading can ensure that no naming
> > conflicts will
> > +     * occur, but it can take a long time.</li>
> > +     * <li><i>-primaryKeys/-pk &lt;true/t | false/f&gt;</i>:
> > Whether primary
> > +     * keys on existing tables are manipulated. Defaults to
> > false.</li>
> > +     * <li><i>-foreignKeys/-fk &lt;true/t | false/f&gt;</i>:
> > Whether foreign
> > +     * keys on existing tables are manipulated. Defaults to
> > false.</li>
> > +     * <li><i>-indexes/-ix &lt;true/t | false/f&gt;</i>: Whether
> > indexes on
> > +     * existing tables are manipulated. Defaults to false.</li>
> > +     * <li><i>-sequences/-sq &lt;true/t | false/f&gt;</i>: Whether
> > sequences
> > +     * are manipulated. Defaults to true.</li>
> > +     * <li><i>-schemas/-s &lt;schema and table names&gt;</i>: A
> > list of schemas
> > +     * and/or tables to read. Corresponds to the
> > +     * same-named option in the {@link SchemaGenerator}. This option
> > +     * is ignored if <code>readSchema</code> is false.</li>
> > +     * <li><i>-meta/-m &lt;true/t | false/f&gt;</i>: Whether the
> > given action
> > +     * applies to metadata as well as mappings.</li>
> > +     * </ul>
> > +     *  The various actions are as follows.
> > +     * <ul>
> > +     * <li><i>refresh</i>: Bring the mapping information up-to-date
> > +     * with the class definitions. OpenJPA will attempt to use any
> > provided
> > +     * mapping information, and fill in missing information. If the
> > +     * provided information conflicts with the class definition, the
> > +     * conflicting information will be discarded and the class/
> > field will
> > +     * be re-mapped to new columns/tables. This is the default
> > action.</li>
> > +     * <li><i>add</i>: If used with the <code>-meta</code> option,
> > adds new
> > +     * default metadata for the given class(es). Otherwise, brings
> > the
> > +     * mapping information up-to-date with the class
> > +     * definitions. OpenJPA will attempt to use any provided mapping
> > +     * information, and fill in missing information. OpenJPA will
> > fail if
> > +     * the provided information conflicts with the class
> > definition.</li>
> > +     * <li><i>buildSchema</i>: Create the schema matching the
> > existing
> > +     * mappings for the given class(es). Any invalid mapping
> > information
> > +     * will cause an exception.</li>
> > +     * <li><i>drop</i>: Delete mappings for the given classes. If
> > used with
> > +     * the <code>-meta</code> option, also deletes metadata.</li>
> > +     * <li><i>validate</i>: Validate the given mappings. The mapping
> > +     * repository and schema will not be affected.</li>
> > +     * <li><i>import</i>: Import mappings from an XML document and
> > store
> > +     * them as the current system mappings.</li>
> > +     * <li><i>export</i>: Dump the current mappings for the given
> > classes to
> > +     * an XML document specified by the <code>file</code> option.</
> > li>
> > +     * If used with the <code>-meta</code> option, the metadata
> > will be
> > +     * included in the export.
> > +     * </ul>
> > +     *  Each class supplied as an argument must have valid
> > metadata. If
> > +     * no class arguments are given, the tool runs on all metadata
> > files in
> > +     * the CLASSPATH.
> > +     *  Examples:
> > +     * <ul>
> > +     * <li>Refresh the mappings for given package, without
> > dropping any
> > +     * schema components:<br />
> > +     * <code>java org.apache.openjpa.jdbc.meta.MappingTool
> > mypackage.jdo</code></li>
> > +     * <li>Refresh the mappings for all persistent classes in the
> > classpath,
> > +     * dropping any unused columns and even tables:<br />
> > +     * <code>java org.apache.openjpa.jdbc.meta.MappingTool -sa
> > refresh
> > +     * -dt true</code></li>
> > +     * <li>Make sure the mappings you've created by hand match the
> > object
> > +     * model and schema:<br />
> > +     * <code>java org.apache.openjpa.jbdc.meta.MappingTool
> > +     * -a validate Person.java</code></li>
> > +     * <li>Remove the recorded mapping for a given class:<br />
> > +     * <code>java org.apache.openjpa.jbdc.meta.MappingTool
> > +     * -a drop Person.java</code></li>
> > +     * <li>Record the current mappings in an XML file:<br />
> > +     * <code>java org.apache.openjpa.jdbc.meta.MappingTool
> > +     * -f mypackage.orm -a export mypackage.jdo</code></li>
> > +     * </ul>
> > +     */
> > +    public static void main(String[] args)
> > +        throws IOException, SQLException {
> > +        Options opts = new Options();
> > +        args = opts.setFromCmdLine(args);
> > +        JDBCConfiguration conf = new JDBCConfigurationImpl();
> > +        try {
> > +            if (!run(conf, args, opts))
> > +                System.err.println(_loc.get("tool-usage"));
> > +        } finally {
> > +            conf.close();
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Run the tool. Returns false if invalid options are given.
> > +     *
> > +     * @see #main
> > +     */
> > +    public static boolean run(JDBCConfiguration conf, String[] args,
> > +        Options opts)
> > +        throws IOException, SQLException {
> > +        if (opts.containsKey("help") || opts.containsKey("-help"))
> > +            return false;
> > +
> > +        // flags
> > +        Flags flags = new Flags();
> > +        flags.action = opts.removeProperty("action", "a",
> > flags.action);
> > +        flags.schemaAction = opts.removeProperty("schemaAction",
> > "sa",
> > +            flags.schemaAction);
> > +        flags.dropTables = opts.removeBooleanProperty
> > +            ("dropTables", "dt", flags.dropTables);
> > +        flags.openjpaTables = opts.removeBooleanProperty
> > +            ("openjpaTables", "ot", flags.openjpaTables);
> > +        flags.dropSequences = opts.removeBooleanProperty
> > +            ("dropSequences", "dsq", flags.dropSequences);
> > +        flags.readSchema = opts.removeBooleanProperty
> > +            ("readSchema", "rs", flags.readSchema);
> > +        flags.primaryKeys = opts.removeBooleanProperty
> > +            ("primaryKeys", "pk", flags.primaryKeys);
> > +        flags.indexes = opts.removeBooleanProperty("indexes", "ix",
> > +            flags.indexes);
> > +        flags.foreignKeys = opts.removeBooleanProperty
> > ("foreignKeys", "fk",
> > +            flags.foreignKeys);
> > +        flags.sequences = opts.removeBooleanProperty("sequences",
> > "sq",
> > +            flags.sequences);
> > +        flags.ignoreErrors = opts.removeBooleanProperty
> > +            ("ignoreErrors", "i", flags.ignoreErrors);
> > +        flags.meta = opts.removeBooleanProperty("meta", "m",
> > flags.meta);
> > +        String fileName = opts.removeProperty("file", "f", null);
> > +        String schemaFileName = opts.removeProperty("schemaFile",
> > "sf", null);
> > +        String sqlFileName = opts.removeProperty("sqlFile", "sql",
> > null);
> > +        String schemas = opts.removeProperty("s");
> > +        if (schemas != null)
> > +            opts.setProperty("schemas", schemas);
> > +
> > +        Configurations.populateConfiguration(conf, opts);
> > +        ClassLoader loader = conf.getClassResolverInstance().
> > +            getClassLoader(MappingTool.class, null);
> > +        if (flags.meta && ACTION_ADD.equals(flags.action))
> > +            flags.metaDataFile = Files.getFile(fileName, loader);
> > +        else
> > +            flags.mappingWriter = Files.getWriter(fileName, loader);
> > +        flags.schemaWriter = Files.getWriter(schemaFileName, loader);
> > +        flags.sqlWriter = Files.getWriter(sqlFileName, loader);
> > +
> > +        return run(conf, args, flags, loader);
> > +    }
> > +
> > +    /**
> > +     * Run the tool. Return false if an invalid option was given.
> > +     */
> > +    public static boolean run(JDBCConfiguration conf, String[] args,
> > +        Flags flags, ClassLoader loader)
> > +        throws IOException, SQLException {
> > +        // default action based on whether the mapping defaults
> > fills in
> > +        // missing info
> > +        if (flags.action == null) {
> > +            if (conf.getMappingDefaultsInstance
> > ().defaultMissingInfo())
> > +                flags.action = ACTION_BUILD_SCHEMA;
> > +            else
> > +                flags.action = ACTION_REFRESH;
> > +        }
> > +
> > +        // collect the classes to act on
> > +        Log log = conf.getLog(OpenJPAConfiguration.LOG_TOOL);
> > +        Collection classes = null;
> > +        if (args.length == 0) {
> > +            if (ACTION_IMPORT.equals(flags.action))
> > +                return false;
> > +            log.info(_loc.get("running-all-classes"));
> > +            classes = conf.getMappingRepositoryInstance().
> > +                loadPersistentTypes(true, loader);
> > +        } else {
> > +            classes = new HashSet();
> > +            ClassArgParser classParser =
> > conf.getMetaDataRepositoryInstance().
> > +                getMetaDataFactory().newClassArgParser();
> > +            classParser.setClassLoader(loader);
> > +            Class[] parsed;
> > +            for (int i = 0; args != null && i < args.length; i++) {
> > +                parsed = classParser.parseTypes(args[i]);
> > +                classes.addAll(Arrays.asList(parsed));
> > +            }
> > +        }
> > +
> > +        Class[] act = (Class[]) classes.toArray(new Class
> > [classes.size()]);
> > +        if (ACTION_EXPORT.equals(flags.action)) {
> > +            // run exports until the first export succeeds
> > +            ImportExport[] instances = newImportExports();
> > +            for (int i = 0; i < instances.length; i++) {
> > +                if (instances[i].exportMappings(conf, act,
> > flags.meta, log,
> > +                    flags.mappingWriter))
> > +                    return true;
> > +            }
> > +            return false;
> > +        }
> > +        if (ACTION_IMPORT.equals(flags.action)) {
> > +            // run exports until the first export succeeds
> > +            ImportExport[] instances = newImportExports();
> > +            for (int i = 0; i < instances.length; i++) {
> > +                if (instances[i].importMappings(conf, act, args,
> > flags.meta,
> > +                    log, loader))
> > +                    return true;
> > +            }
> > +            return false;
> > +        }
> > +
> > +        MappingTool tool;
> > +        try {
> > +            tool = new MappingTool(conf, flags.action, flags.meta);
> > +        } catch (IllegalArgumentException iae) {
> > +            return false;
> > +        }
> > +
> > +        // setup the tool
> > +        tool.setIgnoreErrors(flags.ignoreErrors);
> > +        tool.setMetaDataFile(flags.metaDataFile);
> > +        tool.setMappingWriter(flags.mappingWriter);
> > +        tool.setSchemaAction(flags.schemaAction);
> > +        tool.setSchemaWriter(flags.schemaWriter);
> > +        tool.setReadSchema(flags.readSchema
> > +            && !ACTION_VALIDATE.equals(flags.action));
> > +        tool.setPrimaryKeys(flags.primaryKeys);
> > +        tool.setForeignKeys(flags.foreignKeys);
> > +        tool.setIndexes(flags.indexes);
> > +        tool.setSequences(flags.sequences || flags.dropSequences);
> > +
> > +        // make sure to do this after other settings so that other
> > settings
> > +        // are passed on to schema tool
> > +        tool.getSchemaTool().setDropTables(flags.dropTables);
> > +        tool.getSchemaTool().setDropSequences(flags.dropSequences);
> > +        tool.getSchemaTool().setWriter(flags.sqlWriter);
> > +        tool.getSchemaTool().setOpenJPATables(flags.openjpaTables);
> > +
> > +        // and run the action
> > +        for (int i = 0; i < act.length; i++) {
> > +            log.info(_loc.get("tool-running", act[i], flags.action));
> > +            if (i == 0 && flags.readSchema)
> > +                log.info(_loc.get("tool-time"));
> > +            tool.run(act[i]);
> > +        }
> > +        log.info(_loc.get("tool-record"));
> > +        tool.record();
> > +        return true;
> > +    }
> > +
> > +    /**
> > +     * Create an {@link ImportExport} instance.
> > +     */
> > +    private static ImportExport[] newImportExports() {
> > +        try {
> > +            Class[] types = Services.getImplementorClasses
> > (ImportExport.class);
> > +            ImportExport[] instances = new ImportExport
> > [types.length];
> > +            for (int i = 0; i < types.length; i++)
> > +                instances[i] = (ImportExport) types[i].newInstance();
> > +            return instances;
> > +        } catch (Throwable t) {
> > +            throw new InternalException(_loc.get("importexport-
> > instantiate"),t);
> > +        }
> > +    }
> > +
> > +    /**
> > +     * Run flags.
> > +     */
> > +    public static class Flags {
> > +
> > +        public String action = null;
> > +        public boolean meta = false;
> > +        public String schemaAction = SchemaTool.ACTION_ADD;
> > +        public File metaDataFile = null;
> > +        public Writer mappingWriter = null;
> > +        public Writer schemaWriter = null;
> > +        public Writer sqlWriter = null;
> > +        public boolean ignoreErrors = false;
> > +        public boolean readSchema = false;
> > +        public boolean dropTables = false;
> > +        public boolean openjpaTables = false;
> > +        public boolean dropSequences = false;
> > +        public boolean sequences = true;
> > +        public boolean primaryKeys = false;
> > +        public boolean foreignKeys = false;
> > +        public boolean indexes = false;
> > +    }
> > +
> > +    /**
> > +     * Helper used to import and export mapping data.
> > +     */
> > +    public static interface ImportExport {
> > +
> > +        /**
> > +         * Import mappings for the given classes based on the
> > given arguments.
> > +         */
> > +        public boolean importMappings(JDBCConfiguration conf, Class
> > [] act,
> > +            String[] args, boolean meta, Log log, ClassLoader loader)
> > +            throws IOException;
> > +
> > +        /**
> > +         * Export mappings for the given classes based on the
> > given arguments.
> > +         */
> > +        public boolean exportMappings(JDBCConfiguration conf, Class
> > [] act,
> > +            boolean meta, Log log, Writer writer)
> > +            throws IOException;
> > +    }
> > +}
> >
> >
>
> _______________________________________________________________________
> Notice:  This email message, together with any attachments, may contain
> information  of  BEA Systems,  Inc.,  its subsidiaries  and  affiliated
> entities,  that may be confidential,  proprietary,  copyrighted  and/or
> legally privileged, and is intended solely for the use of the individual
> or entity named in this message. If you are not the intended recipient,
> and have received this message in error, please immediately return this
> by email and then delete it.
>

Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message