View Javadoc

1   package liquibase.ext.spatial.sqlgenerator;
2   
3   import java.util.regex.Matcher;
4   import java.util.regex.Pattern;
5   
6   import liquibase.database.Database;
7   
8   import com.vividsolutions.jts.geom.Geometry;
9   
10  public class WktConversionUtils {
11     /** The SRID regular expression. */
12     public static final String SRID_REGEX = "SRID[\\s]*=[\\s]*([0-9]+)[\\s]*;";
13  
14     /** The WKT regular expression. */
15     public static final String WKT_REGEX = "((((MULTI)?(POINT|LINESTRING|POLYGON)|GEOMETRYCOLLECTION)Z?M?)[\\s]*[(].*[)])";
16  
17     /** The PostGIS EWKT regular expression. */
18     public static final String EWKT_REGEX = "(" + SRID_REGEX + "[\\s]*)?" + WKT_REGEX;
19  
20     /** The EWKT <code>Pattern</code> instance. */
21     public static final Pattern EWKT_PATTERN = Pattern.compile(EWKT_REGEX, Pattern.CASE_INSENSITIVE);
22  
23     /** Hide the default constructor. */
24     private WktConversionUtils() {
25     }
26  
27     /**
28      * If the old value is a geometry or a Well-Known Text, convert it to the appropriate new value.
29      * Otherwise, this method returns the old value.
30      * 
31      * @param oldValue
32      *           the old value.
33      * @param database
34      *           the database instance.
35      * 
36      * @return the new value.
37      */
38     public static Object handleColumnValue(final Object oldValue, final Database database,
39           final WktInsertOrUpdateGenerator generator) {
40        Object newValue = oldValue;
41        if (oldValue instanceof Geometry) {
42           final Geometry geometry = (Geometry) oldValue;
43           final String wkt = geometry.toText();
44           String sridString = null;
45           if (geometry.getSRID() > 0) {
46              sridString = String.valueOf(geometry.getSRID());
47           }
48           newValue = generator.convertToFunction(wkt, sridString, database);
49        } else if (oldValue instanceof String) {
50           final String value = oldValue.toString().trim();
51           final Matcher matcher = EWKT_PATTERN.matcher(value);
52           if (matcher.matches()) {
53              final String sridString = matcher.group(2);
54              final String wkt = matcher.group(3);
55              final String function = generator.convertToFunction(wkt, sridString, database);
56              newValue = function;
57           }
58        }
59        return newValue;
60     }
61  
62     /**
63      * Converts the given Well-Known Text and SRID to the appropriate function call for the database.
64      * 
65      * @param wkt
66      *           the Well-Known Text string.
67      * @param srid
68      *           the SRID string which may be an empty string.
69      * @param database
70      *           the database instance.
71      * @return the string that converts the WKT to a database-specific geometry.
72      */
73     public static String convertToFunction(final String wkt, final String srid,
74           final Database database, final WktInsertOrUpdateGenerator generator) {
75        if (wkt == null || wkt.equals("")) {
76           throw new IllegalArgumentException("The Well-Known Text cannot be null or empty");
77        }
78        if (generator == null) {
79           throw new IllegalArgumentException("The generator cannot be null or empty");
80        }
81        final String geomFromTextFunction = generator.getGeomFromWktFunction();
82        String function = geomFromTextFunction + "('" + wkt + "'";
83        if (srid != null && !srid.equals("")) {
84           function += ", " + srid;
85        } else if (generator.isSridRequiredInFunction(database)) {
86           throw new IllegalArgumentException("An SRID was not provided with '" + wkt
87                 + "' but is required in call to '" + geomFromTextFunction + "'");
88        }
89        function += ")";
90        return function;
91     }
92  }