/*
* GeoTools - The Open Source Java GIS Toolkit
* http://geotools.org
*
* (C) 2002-2008, Open Source Geospatial Foundation (OSGeo)
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation;
* version 2.1 of the License.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*/
package org.geotools.data.postgis.fidmapper;
import java.io.IOException;
import java.sql.Connection;
import java.sql.Statement;
import java.sql.Types;
import java.util.regex.Pattern;
import org.geotools.data.DataSourceException;
import org.geotools.data.jdbc.fidmapper.MultiColumnFIDMapper;
import org.opengis.feature.simple.SimpleFeature;
/**
* A versioned fid mapper working with UUID primary key, using a random generator
*/
class VersionedUUIDFIDMapper extends MultiColumnFIDMapper implements VersionedFIDMapper {
protected UUIDFIDMapper wrapped;
static final Pattern UUID_PATTERN = Pattern.compile("[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}");
public VersionedUUIDFIDMapper(String tableSchemaName, String tableName, String colName, int colType, int colSize) {
super(tableSchemaName, tableName, new String[] { "revision", colName }, new int[] {
colType, Types.OTHER}, new int[] { colSize, 0 }, new int[] { 0, 0 },
new boolean[] { false, false });
returnFIDColumnsAsAttributes = true;
wrapped = new UUIDFIDMapper(colName, colType);
}
public String getUnversionedFid(String versionedFID) {
// we assume revision is the last column, since it has been added with
// an alter table "add". Also, we make the fid "typed" to ensure WFS keeps on working
return tableName + "." + versionedFID.substring(versionedFID.lastIndexOf('&') + 1);
}
public String createVersionedFid(String extenalFID, long revision) {
return revision + "&" + extenalFID.substring(tableName.length() + 1);
}
public Object[] getUnversionedPKAttributes(String FID) throws IOException {
// check we can parse this
if (!FID.startsWith(tableName + "."))
throw new DataSourceException("The FID is invalid, should start with '" + tableName
+ ".'");
// leverate superclass parsing, then throw away the last element
Object[] values = getPKAttributes(FID.substring(tableName.length() + 1) + "&0");
Object[] unversioned = new Object[values.length - 1];
System.arraycopy(values, 0, unversioned, 0, unversioned.length);
return unversioned;
}
public String createID(Connection conn, SimpleFeature feature, Statement statement)
throws IOException {
if (feature.getAttribute(colNames[1]) == null) {
try {
String fid = feature.getID();
String id;
if(fid.startsWith(tableName + ".") &&
UUID_PATTERN.matcher(fid.substring(tableName.length() + 1)).matches()) {
id = fid.substring(tableName.length() + 1);
} else {
id = wrapped.createID(conn, feature, statement);
}
feature.setAttribute(colNames[1], id);
} catch (Exception e) {
throw new DataSourceException("Could not generate key for the "
+ "unset primary key column " + colNames[1], e);
}
}
return super.createID(conn, feature, statement);
}
}