    001    //$HeadURL: https://svn.wald.intevation.org/svn/deegree/base/branches/2.4_testing/src/org/deegree/io/datastore/sql/idgenerator/DBMaxIdGenerator.java $
    002    /*----------------    FILE HEADER  ------------------------------------------
    003
    004     This file is part of deegree.
    005     Copyright (C) 2006 by: M.O.S.S. Computer Grafik Systeme GmbH
    006     Hohenbrunner Weg 13
    007     D-82024 Taufkirchen
    008     http://www.moss.de/
    009
    010     This library is free software; you can redistribute it and/or
    011     modify it under the terms of the GNU Lesser General Public
    012     License as published by the Free Software Foundation; either
    013     version 2.1 of the License, or (at your option) any later version.
    014
    015     This library is distributed in the hope that it will be useful,
    016     but WITHOUT ANY WARRANTY; without even the implied warranty of
    017     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    018     Lesser General Public License for more details.
    019
    020     You should have received a copy of the GNU Lesser General Public
    021     License along with this library; if not, write to the Free Software
    022     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    023
    024     ---------------------------------------------------------------------------*/
    025    package org.deegree.io.datastore.sql.idgenerator;
    026
    027    import java.sql.Connection;
    028    import java.util.Properties;
    029
    030    import org.deegree.io.datastore.DatastoreException;
    031    import org.deegree.io.datastore.DatastoreTransaction;
    032    import org.deegree.io.datastore.FeatureId;
    033    import org.deegree.io.datastore.idgenerator.IdGenerationException;
    034    import org.deegree.io.datastore.idgenerator.IdGenerator;
    035    import org.deegree.io.datastore.schema.MappedFeatureType;
    036    import org.deegree.io.datastore.schema.MappedGMLId;
    037    import org.deegree.io.datastore.sql.AbstractSQLDatastore;
    038    import org.deegree.io.datastore.sql.transaction.SQLTransaction;
    039
    040    /**
    041     * Feature id generator that produces successive (+1) values and retrieves its start value from the
    042     * specified table value (the maximum stored in the field).
    043     * <p>
    044     * Please note that aborted transactions will also increase ids, so feature ids may be skipped.
    045     *
    046     * @author <a href="mailto:cpollmann@moss.de">Christoph Pollmann</a>
    047     * @author <a href="mailto:schneider@lat-lon.de">Markus Schneider</a>
    048     * @author last edited by: $Author: mschneider $
    049     *
    050     * @version $Revision: 6588 $, $Date: 2007-04-11 17:31:29 +0200 (Mi, 11. Apr 2007) $
    051     */
    052    public class DBMaxIdGenerator extends IdGenerator {
    053
    054        private String tableName;
    055
    056        private String columnName;
    057
    058        // initialized when #getNewId() is called the first time
    059        private int lastId = -1;
    060
    061        /**
    062         * Creates a new <code>DBMaxIdGenerator</code> instance.
    063         * <p>
    064         * Supported configuration parameters: <table>
    065         * <tr>
    066         * <th>Name</th>
    067         * <th>optional?</th>
    068         * <th>Usage</th>
    069         * </tr>
    070         * <tr>
    071         * <td>table</td>
    072         * <td>no</td>
    073         * <td>name of the table where the id field is stored</td>
    074         * </tr>
    075         * <tr>
    076         * <td>column</td>
    077         * <td>no</td>
    078         * <td>name of the id field</td>
    079         * </tr>
    080         * </table>
    081         *
    082         * @param params
    083         *            configuration parameters
    084         * @throws IdGenerationException
    085         */
    086        public DBMaxIdGenerator( Properties params ) throws IdGenerationException {
    087            super( params );
    088            this.tableName = params.getProperty( "table" );
    089            this.columnName = params.getProperty( "column" );
    090            if ( this.tableName == null || this.columnName == null ) {
    091                String msg = "DBMaxIdGenerator requires 'table' and 'column' parameters.";
    092                throw new IdGenerationException( msg );
    093            }
    094        }
    095
    096        /**
    097         * Returns a new primary key.
    098         *
    099         * @param ta
    100         *            datastore transaction (context)
    101         * @return a new primary key.
    102         * @throws IdGenerationException
    103         *             if the generation of the id could not be performed
    104         */
    105        @Override
    106        public Object getNewId( DatastoreTransaction ta )
    107                                throws IdGenerationException {
    108
    109            if ( this.lastId == -1 ) {
    110                initLastId( ta );
    111            }
    112
    113            return ++this.lastId;
    114        }
    115
    116        /**
    117         * Initialized the lastId field with the maximum value stored in the specified table field.
    118         *
    119         * @param ta
    120         *            datastore transaction (context)
    121         * @throws IdGenerationException
    122         */
    123        private void initLastId( DatastoreTransaction ta )
    124                                throws IdGenerationException {
    125
    126            if ( !( ta instanceof SQLTransaction ) ) {
    127                String msg = "DBMaxIdGenerator can only be used with SQL based datastores.";
    128                throw new IllegalArgumentException( msg );
    129            }
    130
    131            try {
    132                AbstractSQLDatastore ds = (AbstractSQLDatastore) ta.getDatastore();
    133                Connection conn = ( (SQLTransaction) ta ).getConnection();
    134                this.lastId = ds.getMaxValue( conn, this.tableName, this.columnName );
    135            } catch ( DatastoreException e ) {
    136                throw new IdGenerationException( e.getMessage(), e );
    137            }
    138        }
    139
    140        /**
    141         * Returns a new id for a feature of the given type.
    142         *
    143         * @param ft
    144         *            (mapped) feature type
    145         * @return a new feature id.
    146         * @throws IdGenerationException
    147         *             if the generation of the id could not be performed
    148         */
    149        @Override
    150        public FeatureId getNewId( MappedFeatureType ft, DatastoreTransaction ta )
    151                                throws IdGenerationException {
    152
    153            MappedGMLId fidDefinition = ft.getGMLId();
    154            if ( fidDefinition.getKeySize() != 1 ) {
    155                String msg = "Cannot generate feature ids that are mapped to more than one column.";
    156                throw new IdGenerationException( msg );
    157            }
    158
    159            if ( this.lastId == -1 ) {
    160                initLastId( ta );
    161            }
    162
    163            FeatureId fid = new FeatureId( ft, new Object[] { ++this.lastId } );
    164            return fid;
    165        }
    166    }