Package org.apache.torque.engine.database.model

Source Code of org.apache.torque.engine.database.model.Database

package org.apache.torque.engine.database.model;

/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements.  See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership.  The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License.  You may obtain a copy of the License at
*
*   http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied.  See the License for the
* specific language governing permissions and limitations
* under the License.
*/

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.apache.commons.collections.map.ListOrderedMap;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.torque.engine.EngineException;
import org.apache.torque.engine.database.transform.DTDResolver;
import org.apache.torque.engine.platform.Platform;
import org.apache.torque.engine.platform.PlatformFactory;
import org.xml.sax.Attributes;


/**
* A class for holding application data structures.
*
* @author <a href="mailto:leon@opticode.co.za>Leon Messerschmidt</a>
* @author <a href="mailto:jmcnally@collab.net>John McNally</a>
* @author <a href="mailto:mpoeschl@marmot.at>Martin Poeschl</a>
* @author <a href="mailto:dlr@collab.net>Daniel Rall</a>
* @author <a href="mailto:byron_foster@byron_foster@yahoo.com>Byron Foster</a>
* @author <a href="mailto:monroe@dukece.com>Greg Monroe</a>
* @version $Id: Database.java 473814 2006-11-11 22:30:30Z tv $
*/
public class Database
{
    /** Logging class from commons.logging */
    private static Log log = LogFactory.getLog(Database.class);

    private String databaseType = null;
    private List tableList = new ArrayList(100);
    private Map domainMap = new HashMap();
    private String name;
    private String javaName;
    private String pkg;
    private String baseClass;
    private String basePeer;
    private String defaultIdMethod;
    private String defaultJavaType;
    private String defaultJavaNamingMethod;
    private Hashtable tablesByName = new Hashtable();
    private Hashtable tablesByJavaName = new Hashtable();
    private boolean heavyIndexing;
    /** the name of the definition file */
    private String fileName;
    private Map options = Collections.synchronizedMap(new ListOrderedMap());


    /**
     * Creates a new instance for the specified database type.
     *
     * @param databaseType The default type for this database.
     */
    public Database(String databaseType)
    {
        this.databaseType = databaseType;
    }

    /**
     * Load the database object from an xml tag.
     *
     * @param attrib the xml attributes
     */
    public void loadFromXML(Attributes attrib)
    {
        setName(attrib.getValue("name"));
        pkg = attrib.getValue("package");
        baseClass = attrib.getValue("baseClass");
        basePeer = attrib.getValue("basePeer");
        defaultJavaType = attrib.getValue("defaultJavaType");
        defaultIdMethod = attrib.getValue("defaultIdMethod");
        defaultJavaNamingMethod = attrib.getValue("defaultJavaNamingMethod");
        if (defaultJavaNamingMethod == null)
        {
            defaultJavaNamingMethod = NameGenerator.CONV_METHOD_UNDERSCORE;
        }
        heavyIndexing = "true".equals(attrib.getValue("heavyIndexing"));
    }

    /**
     * Get the name of the Database
     *
     * @return name of the Database
     */
    public String getName()
    {
        return name;
    }

    /**
     * Set the name of the Database
     *
     * @param name name of the Database
     */
    public void setName(String name)
    {
        /** @task check this */
//        this.name = (name == null ? Torque.getDefaultDB() : name);
        this.name = (name == null ? "default" : name);
    }

    public String getFileName()
    {
        return fileName;
    }

    public void setFileName(String name)
    {
        this.fileName = name;
    }

    /**
     * Get the value of package.
     * @return value of package.
     */
    public String getPackage()
    {
        return pkg;
    }

    /**
     * Set the value of package.
     * @param v  Value to assign to package.
     */
    public void setPackage(String v)
    {
        this.pkg = v;
    }

    /**
     * Get the value of baseClass.
     * @return value of baseClass.
     */
    public String getBaseClass()
    {
        if (baseClass == null)
        {
            return "BaseObject";
        }
        return baseClass;
    }

    /**
     * Set the value of baseClass.
     * @param v  Value to assign to baseClass.
     */
    public void setBaseClass(String v)
    {
        this.baseClass = v;
    }

    /**
     * Get the value of basePeer.
     * @return value of basePeer.
     */
    public String getBasePeer()
    {
        if (basePeer == null)
        {
            return "BasePeer";
        }
        return basePeer;
    }

    /**
     * Set the value of basePeer.
     * @param v Value to assign to basePeer.
     */
    public void setBasePeer(String v)
    {
        this.basePeer = v;
    }

    /**
     * Get the value of defaultIdMethod.
     * @return value of defaultIdMethod.
     */
    public String getDefaultIdMethod()
    {
        return defaultIdMethod;
    }

    /**
     * Set the value of defaultIdMethod.
     * @param v Value to assign to defaultIdMethod.
     */
    public void setDefaultIdMethod(String v)
    {
        this.defaultIdMethod = v;
    }

    /**
     * Get type to use in Java sources (primitive || object)
     *
     * @return the type to use
     */
    public String getDefaultJavaType()
    {
        return defaultJavaType;
    }

    /**
     * Get the value of defaultJavaNamingMethod which specifies the
     * method for converting schema names for table and column to Java names.
     *
     * @return The default naming conversion used by this database.
     */
    public String getDefaultJavaNamingMethod()
    {
        return defaultJavaNamingMethod;
    }

    /**
     * Set the value of defaultJavaNamingMethod.
     * @param v The default naming conversion for this database to use.
     */
    public void setDefaultJavaNamingMethod(String v)
    {
        this.defaultJavaNamingMethod = v;
    }

    /**
     * Get the value of heavyIndexing.
     * @return value of heavyIndexing.
     */
    public boolean isHeavyIndexing()
    {
        return heavyIndexing;
    }

    /**
     * Set the value of heavyIndexing.
     * @param v  Value to assign to heavyIndexing.
     */
    public void setHeavyIndexing(boolean v)
    {
        this.heavyIndexing = v;
    }

    /**
     * Return an List of all tables
     *
     * @return List of all tables
     */
    public List getTables()
    {
        return tableList;
    }

    /**
     * Return the table with the specified name.
     *
     * @param name table name
     * @return A Table object.  If it does not exist it returns null
     */
    public Table getTable(String name)
    {
        return (Table) tablesByName.get(name);
    }

    /**
     * Return the table with the specified javaName.
     *
     * @param javaName name of the java object representing the table
     * @return A Table object.  If it does not exist it returns null
     */
    public Table getTableByJavaName(String javaName)
    {
        return (Table) tablesByJavaName.get(javaName);
    }

    /**
     * An utility method to add a new table from an xml attribute.
     *
     * @param attrib the xml attributes
     * @return the created Table
     */
    public Table addTable(Attributes attrib)
    {
        Table tbl = new Table();
        tbl.setDatabase(this);
        tbl.loadFromXML(attrib, this.getDefaultIdMethod());
        addTable(tbl);
        return tbl;
    }

    /**
     * Add a table to the list and sets the Database property to this Database
     *
     * @param tbl the table to add
     */
    public void addTable(Table tbl)
    {
        tbl.setDatabase(this);
        tableList.add(tbl);
        tablesByName.put(tbl.getName(), tbl);
        tablesByJavaName.put(tbl.getJavaName(), tbl);
        tbl.setPackage(getPackage());
    }

    public void addDomain(Domain domain)
    {
        domainMap.put(domain.getName(), domain);
    }

    public Domain getDomain(String domainName)
    {
        return (Domain) domainMap.get(domainName);
    }

    protected String getDatabaseType()
    {
        return databaseType;
    }

    public void setDatabaseType(String databaseType)
    {
        this.databaseType = databaseType;
    }

    /**
     * Returns the Platform implementation for this database.
     *
     * @return a Platform implementation
     */
    public Platform getPlatform()
    {
        return PlatformFactory.getPlatformFor(databaseType);
    }

    /**
     * Determines if this database will be using the
     * <code>IDMethod.ID_BROKER</code> to create ids for torque OM
     * objects.
     * @return true if there is at least one table in this database that
     * uses the <code>IDMethod.ID_BROKER</code> method of generating
     * ids. returns false otherwise.
     */
    public boolean requiresIdTable()
    {
        Iterator iter = getTables().iterator();
        while (iter.hasNext())
        {
            Table table = (Table) iter.next();
            if (table.getIdMethod().equals(IDMethod.ID_BROKER))
            {
                return true;
            }
        }
        return false;
    }

    /**
     * Initializes the model.
     *
     * @throws EngineException
     */
    public void doFinalInitialization() throws EngineException
    {
        Iterator iter = getTables().iterator();
        while (iter.hasNext())
        {
            Table currTable = (Table) iter.next();

            // check schema integrity
            // if idMethod="autoincrement", make sure a column is
            // specified as autoIncrement="true"
            // FIXME: Handle idMethod="native" via DB adapter.
            // TODO autoincrement is no longer supported!!!
            if (currTable.getIdMethod().equals("autoincrement"))
            {
                boolean foundOne = false;
                Iterator colIter = currTable.getColumns().iterator();
                while (colIter.hasNext() && !foundOne)
                {
                    foundOne = ((Column) colIter.next()).isAutoIncrement();
                }

                if (!foundOne)
                {
                    String errorMessage = "Table '" + currTable.getName()
                            + "' is marked as autoincrement, but it does not "
                            + "have a column which declared as the one to "
                            + "auto increment (i.e. autoIncrement=\"true\")\n";
                    throw new EngineException("Error in XML schema: " + errorMessage);
                }
            }

            currTable.doFinalInitialization();

            // setup reverse fk relations
            Iterator fks = currTable.getForeignKeys().iterator();
            while (fks.hasNext())
            {
                ForeignKey currFK = (ForeignKey) fks.next();
                Table foreignTable = getTable(currFK.getForeignTableName());
                if (foreignTable == null)
                {
                    throw new EngineException("Attempt to set foreign"
                            + " key to nonexistent table, "
                            + currFK.getForeignTableName());
                }
                else
                {
                    // TODO check type and size
                    List referrers = foreignTable.getReferrers();
                    if ((referrers == null || !referrers.contains(currFK)))
                    {
                        foreignTable.addReferrer(currFK);
                    }

                    // local column references
                    Iterator localColumnNames = currFK.getLocalColumns().iterator();
                    while (localColumnNames.hasNext())
                    {
                        Column local = currTable
                                .getColumn((String) localColumnNames.next());
                        // give notice of a schema inconsistency.
                        // note we do not prevent the npe as there is nothing
                        // that we can do, if it is to occur.
                        if (local == null)
                        {
                            throw new EngineException("Attempt to define foreign"
                                    + " key with nonexistent column in table, "
                                    + currTable.getName());
                        }
                        else
                        {
                            //check for foreign pk's
                            if (local.isPrimaryKey())
                            {
                                currTable.setContainsForeignPK(true);
                            }
                        }
                    }

                    // foreign column references
                    Iterator foreignColumnNames
                            = currFK.getForeignColumns().iterator();
                    while (foreignColumnNames.hasNext())
                    {
                        String foreignColumnName = (String) foreignColumnNames.next();
                        Column foreign = foreignTable.getColumn(foreignColumnName);
                        // if the foreign column does not exist, we may have an
                        // external reference or a misspelling
                        if (foreign == null)
                        {
                            throw new EngineException("Attempt to set foreign"
                                    + " key to nonexistent column: table="
                                    +  currTable.getName() + ", foreign column="
                                    +  foreignColumnName);
                        }
                        else
                        {
                            foreign.addReferrer(currFK);
                        }
                    }
                }
            }
        }
    }

    /**
     * Get the base name to use when creating related Java Classes.
     *
     * @return A Java syntax capatible version of the dbName using the method
     *         defined by the defaultJavaNamingMethod XML value.
     */
    public String getJavaName()
    {
        if (javaName == null)
        {
            List inputs = new ArrayList(2);
            inputs.add(name);
            inputs.add(defaultJavaNamingMethod);
            try
            {
                javaName = NameFactory.generateName(NameFactory.JAVA_GENERATOR,
                                                    inputs);
            }
            catch (EngineException e)
            {
                log.error(e, e);
            }
        }
        return javaName;
    }

    /**
     * Convert dbName to a Java compatible name by the JavaName method only
     * (ignores the defaultJavaNamingMethod).
     *
     * @return The current dbName converted to a standard format that can
     *          be used as part of a Java Object name.
     */
    public String getStandardJavaName()
    {
        if (javaName == null)
        {
            List inputs = new ArrayList(2);
            inputs.add(name);
            inputs.add(NameGenerator.CONV_METHOD_JAVANAME);
            try
            {
                javaName = NameFactory.generateName(NameFactory.JAVA_GENERATOR,
                                                    inputs);
            }
            catch (EngineException e)
            {
                log.error(e, e);
            }
        }
        return javaName;
    }

    /**
     * Creats a string representation of this Database.
     * The representation is given in xml format.
     *
     * @return string representation in xml
     */
    public String toString()
    {
        StringBuffer result = new StringBuffer();

        result.append ("<?xml version=\"1.0\"?>\n");
        result.append ("<!DOCTYPE database SYSTEM \""
                + DTDResolver.WEB_SITE_DTD + "\">\n");
        result.append("<!-- Autogenerated by SQLToXMLSchema! -->\n");
        result.append("<database name=\"").append(getName()).append('"')
            .append(" package=\"").append(getPackage()).append('"')
            .append(" defaultIdMethod=\"").append(getDefaultIdMethod())
            .append('"')
            .append(" baseClass=\"").append(getBaseClass()).append('"')
            .append(" basePeer=\"").append(getBasePeer()).append('"')
            .append(">\n");

        for (Iterator i = tableList.iterator(); i.hasNext();)
        {
            result.append(i.next());
        }

        result.append("</database>");
        return result.toString();
    }

    /**
     * Add an XML Specified option key/value pair to this element's option set.
     *
     * @param key the key of the option.
     * @param value the value of the option.
     */
    public void addOption(String key, String value)
    {
        options.put(key, value);
    }

    /**
     * Get the value that was associated with this key in an XML option
     * element.
     *
     * @param key the key of the option.
     * @return The value for the key or a null.
     */
    public String getOption(String key)
    {
        return (String) options.get(key);
    }

    /**
     * Gets the full ordered hashtable array of items specified by XML option
     * statements under this element.<p>
     *
     * Note, this is not thread save but since it's only used for
     * generation which is single threaded, there should be minimum
     * danger using this in Velocity.
     *
     * @return An Map of all options. Will not be null but may be empty.
     */
    public Map getOptions()
    {
        return options;
    }
}
TOP

Related Classes of org.apache.torque.engine.database.model.Database

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.