comparison artifacts/src/main/java/org/dive4elements/river/utils/MapUtils.java @ 9672:b70b1bc0eece 3.2.x

Essentially rewrite MapUtils.getConnection() to cope with driver capabilities
author Tom Gottfried <tom@intevation.de>
date Sat, 23 May 2020 10:37:23 +0200
parents 9cfc495a9f40
children 0a5239a1e46e
comparison
equal deleted inserted replaced
9671:9cfc495a9f40 9672:b70b1bc0eece
1 /* Copyright (C) 2011, 2012, 2013 by Bundesanstalt für Gewässerkunde 1 /* Copyright (C) 2011, 2012, 2013, 2020 by Bundesanstalt für Gewässerkunde
2 * Software engineering by Intevation GmbH 2 * Software engineering by Intevation GmbH
3 * 3 *
4 * This file is Free Software under the GNU AGPL (>=v3) 4 * This file is Free Software under the GNU AGPL (>=v3)
5 * and comes with ABSOLUTELY NO WARRANTY! Check out the 5 * and comes with ABSOLUTELY NO WARRANTY! Check out the
6 * documentation coming with Dive4Elements River for details. 6 * documentation coming with Dive4Elements River for details.
7 */ 7 */
8 8
9 package org.dive4elements.river.utils; 9 package org.dive4elements.river.utils;
10 10
11 import java.util.regex.Matcher; 11 import java.net.URI;
12 import java.util.regex.Pattern; 12 import java.net.URISyntaxException;
13 13
14 import org.apache.log4j.Logger; 14 import org.apache.log4j.Logger;
15 import org.hibernate.impl.SessionFactoryImpl; 15 import org.hibernate.impl.SessionFactoryImpl;
16 16
17 import org.dive4elements.river.backend.SessionFactoryProvider; 17 import org.dive4elements.river.backend.SessionFactoryProvider;
19 19
20 public class MapUtils 20 public class MapUtils
21 { 21 {
22 private static final Logger log = Logger.getLogger(MapUtils.class); 22 private static final Logger log = Logger.getLogger(MapUtils.class);
23 23
24 public static final Pattern DB_URL_PATTERN = 24 private static final String JDBC_SCHEME = "^jdbc:";
25 Pattern.compile("(.*)\\/\\/(.*):([0-9]+)\\/([\\.a-zA-Z0-9_-]+)"); 25
26 private static final String JDBC_DRV_PATTERN =
27 JDBC_SCHEME + "(postgresql|oracle:(thin|oci)):.*";
26 28
27 /** 29 /**
28 * This method returns a connection string for databases used by 30 * This method returns a connection string for databases used by
29 * Mapserver's Mapfile. 31 * Mapserver's Mapfile.
30 * 32 *
40 42
41 return getConnection(user, pass, url); 43 return getConnection(user, pass, url);
42 } 44 }
43 45
44 public static String getConnection(String user, String pass, String url) { 46 public static String getConnection(String user, String pass, String url) {
45 log.debug("Parse connection url: " + url); 47 log.info("Parse connection string: " + url);
46 48
47 Matcher m = DB_URL_PATTERN.matcher(url); 49 if (!url.matches(JDBC_DRV_PATTERN)) {
48 if (!m.matches()) { 50 log.error("Could not parse connection string: "
49 log.warn("Could not parse Connection string"); 51 + "Not a JDBC URL with PostgreSQL or Oracle driver");
50 return null; 52 return null;
51 } 53 }
52 54
53 int groups = m.groupCount(); 55 URI uri = null;
54 56 try {
55 if (log.isDebugEnabled()) { 57 // Strip JDBC_SCHEME to let the driver be parsed as scheme
56 for (int i = 0; i <= groups; i++) { 58 uri = new URI(url.replaceFirst(JDBC_SCHEME, ""));
57 log.debug("Group " + i + ": " + m.group(i));
58 }
59 } 59 }
60 60 catch (URISyntaxException e) {
61 String connection = null; 61 log.error("Could not parse connection string: " + e.getMessage());
62
63 if (groups < 4) {
64 log.warn("Could only partially parse connection string.");
65 return null; 62 return null;
66 } 63 }
67 64
68 String host = m.group(2); 65 String drv = uri.getScheme();
69 String port = m.group(3); 66 log.debug("Driver: " + drv);
70 String db = m.group(4);
71 67
72 if (url.startsWith("jdbc:oracle:")) { 68 String connection = null;
73 connection = user + "/" + pass 69 if (drv.equals("oracle")) {
74 + "@" + host + ":" + port + "/" + db; 70 try {
71 // Work-around the extra colon in the driver part of the scheme
72 String con = new URI(uri.getSchemeSpecificPart())
73 .getSchemeSpecificPart().replaceFirst("^@(//)?", "");
74 log.debug("Database specifier: " + con);
75 connection = user + "/" + pass + "@" + con;
76 }
77 catch (URISyntaxException e) {
78 log.error("Could not parse Oracle connection string: "
79 + e.getMessage());
80 return null;
81 }
75 } 82 }
76 else { 83 else { // assume PostgreSQL
84 String host = uri.getHost();
85 if (host == null && uri.getSchemeSpecificPart().startsWith("//")) {
86 // invalid hostnames (e.g. containing '_') are not parsed!
87 log.error("Could not parse PostgreSQL connection string: "
88 + "invalid host name");
89 return null;
90 }
91 String db = host == null
92 ? uri.getSchemeSpecificPart()
93 : uri.getPath();
94 int port = uri.getPort();
77 connection = createConnectionString(user, pass, host, db, port); 95 connection = createConnectionString(user, pass, host, db, port);
78 } 96 }
79 97
80 return connection; 98 return connection;
81 } 99 }
82 100
83 public static String createConnectionString( 101 private static String createConnectionString(
84 String user, 102 String user,
85 String pass, 103 String pass,
86 String host, 104 String host,
87 String db, 105 String db,
88 String port 106 int port
89 ) { 107 ) {
90 StringBuilder sb = new StringBuilder(); 108 StringBuilder sb = new StringBuilder();
91 sb.append("dbname=").append(db); 109 // Required parameters
92 sb.append(" host='").append(host).append("'"); 110 // defaults to user name in PostgreSQL JDBC:
111 if (db != null) {
112 db = db.replaceFirst("/", "");
113 }
114 sb.append("dbname=").append(db == null || db.equals("") ? user : db);
93 sb.append(" user=").append(user); 115 sb.append(" user=").append(user);
94 sb.append(" port=").append(port); 116
117 // Optional parameters
118 if (host != null) {
119 sb.append(" host='").append(host).append("'");
120 }
121 if (port != -1) {
122 sb.append(" port=").append(port);
123 }
95 // XXX: We need to escape this somehow. 124 // XXX: We need to escape this somehow.
96 sb.append(" password='").append(pass).append("'"); 125 sb.append(" password='").append(pass).append("'");
97 sb.append(" sslmode=disable"); 126 sb.append(" sslmode=disable");
98 return sb.toString(); 127 return sb.toString();
99 } 128 }

http://dive4elements.wald.intevation.org