Statistics
| Revision:

svn-gvsig-desktop / trunk / org.gvsig.desktop / org.gvsig.desktop.plugin / org.gvsig.h2spatial / org.gvsig.h2spatial.h2gis132 / org.gvsig.h2spatial.h2gis132.provider / src / main / java / org / gvsig / fmap / dal / store / h2 / H2SpatialUtils.java @ 47798

History | View | Annotate | Download (12.3 KB)

1
package org.gvsig.fmap.dal.store.h2;
2

    
3
import java.io.File;
4
import java.sql.Connection;
5
import java.sql.SQLException;
6
import java.text.MessageFormat;
7
import java.util.ArrayList;
8
import java.util.HashMap;
9
import java.util.List;
10
import java.util.Map;
11
import org.apache.commons.codec.binary.Hex;
12
import org.apache.commons.io.FileUtils;
13
import org.apache.commons.io.FilenameUtils;
14
import org.apache.commons.lang3.StringUtils;
15
import org.gvsig.fmap.dal.store.h2.H2SpatialHelper.H2SpatialConnectionProvider;
16
import static org.gvsig.fmap.dal.store.h2.H2SpatialHelper.LOGGER;
17
import org.gvsig.fmap.dal.store.jdbc.JDBCConnectionParameters;
18
import org.gvsig.fmap.dal.store.jdbc2.JDBCUtils;
19
import org.gvsig.fmap.dal.store.jdbc2.spi.ConnectionProvider;
20
import org.h2.tools.Server;
21
import org.h2gis.functions.system.H2GISversion;
22

    
23
/**
24
 *
25
 * @author gvSIG Team
26
 */
27
public class H2SpatialUtils {
28
    
29
    private static boolean enable_server = true;
30
    private static Server h2server = null;
31
    private static boolean startServer = true;
32
    private static boolean lastAllowOthers = true;
33
    private static String lastPort = "9123";
34
    private static Map<String,Connection> globalConnections;
35
    
36

    
37
    private static Thread shutdownHook = new Thread("H2_shutdown_hook") {
38
        @Override
39
        public void run() {
40
            server_stop();
41
        }
42
    };
43

    
44
    public static File[] getH2Files(File f) {
45
        if( f==null ) {
46
            return null;
47
        }
48
        String name = removeH2FileNameExtension(f.getName());
49
        File[] files = new File[62];
50
        files[0] = new File(f.getParentFile(), name+".mv.db");
51
        files[1] = new File(f.getParentFile(), name+".trace.db");
52
        for (int i = 2; i < files.length; i++) {
53
            files[i] = new File(f.getParentFile(), name+".mv.db."+(i-1)+".part");
54
        }
55
        return files;
56
    }
57
    
58
    public static boolean existsH2db(File f) {
59
        File[] files = getH2Files(f);
60
        for (File file : files) {
61
            if( file.exists() ) {
62
                return true;
63
            }
64
        }
65
        return false;
66
    }
67
    
68
    public static boolean removeH2db(File f) {
69
        try {
70
            File[] files = getH2Files(f);
71
            for (File file : files) {
72
                if( file.exists() ) {
73
                    FileUtils.delete(file);
74
                }
75
            }
76
        } catch(Throwable t) {
77
            return false;
78
        }
79
        return true;
80
    }
81
    
82
    public static File normalizeH2File(File f) {
83
        if( f==null ) {
84
            return null;
85
        }
86
        f = new File(f.getParentFile(), normalizeH2FileName(f.getName()));
87
        return f;
88
    }
89

    
90
    public static String normalizeH2FileName(String name) {
91
        String s = removeH2FileNameExtension(name);
92
        if( s == null ) {
93
            return null;
94
        }
95
        return s+".mv.db";
96
    }
97
    
98
    public static String removeH2FileNameExtension(String name) {
99
        if( StringUtils.isBlank(name) ) {
100
            return null;
101
        }
102
        if( name.endsWith(".mv.db") ) {
103
            int l = name.length();
104
            return name.substring(0, l-6);
105
        }
106
        if( name.endsWith(".trace.db") ) {
107
            int l = name.length();
108
            return name.substring(0, l-9);
109
        }
110
        return FilenameUtils.removeExtension(name);
111
    }
112

    
113
    public static File getLocalFile(H2SpatialConnectionParameters params) {
114
        String host = params.getHost();
115
        if( !StringUtils.isEmpty(host) ) {
116
          host = host.toLowerCase().trim();
117
          if( !(host.equals("localhost") || host.equals("127.0.0.1")) ) {
118
            return null;
119
          }
120
        }
121
        File f = params.getFile();
122
        return normalizeH2File(f);
123
    }
124
        
125
    public static String getConnectionURL(H2SpatialConnectionParameters params) {
126
        String connectionURL;
127
        String dbfilename = params.getFile().getAbsolutePath().replace("\\","/");
128
        if( dbfilename!=null ) {
129
            dbfilename = H2SpatialUtils.removeH2FileNameExtension(dbfilename);
130
        }
131
        StringBuilder commonParameters = new StringBuilder();
132
        commonParameters.append(";MODE=PostgreSQL");
133
        commonParameters.append(";SCHEMA=PUBLIC");
134
        commonParameters.append(";ALLOW_LITERALS=ALL");
135
        int splitSize = params.getSplitSize();
136
        
137
        if( StringUtils.isEmpty(params.getHost()) ) {
138
            // Asumimos que es una conexion directa sobre el filesystem
139
            if( StringUtils.equalsIgnoreCase(FilenameUtils.getExtension(params.getFile().getName()),"zip") ) {
140
                connectionURL =  MessageFormat.format(
141
                    "jdbc:h2:zip:{0}!/{1}"+commonParameters.toString(),
142
                    dbfilename,
143
                    params.getDBName()
144
                );
145
            } else if( splitSize>0 ) {
146
                connectionURL =  MessageFormat.format(
147
                    "jdbc:h2:split:{1,number,##}:{0}"+commonParameters.toString(),
148
                    dbfilename,
149
                    splitSize
150
                );
151
            } else {
152
                connectionURL =  MessageFormat.format(
153
                    "jdbc:h2:file:{0}"+commonParameters.toString(),
154
                    dbfilename
155
                );
156
            }
157
        } else if( params.getPort() == null ) {
158
            if( splitSize>0 ) {
159
                connectionURL =  MessageFormat.format(
160
                    "jdbc:h2:tcp://{0}/split:{2,number,##}:/{1}"+commonParameters.toString(),
161
                    params.getHost(),
162
                    dbfilename,
163
                    splitSize
164
                );      
165
            } else {
166
                connectionURL =  MessageFormat.format(
167
                    "jdbc:h2:tcp://{0}/{1}"+commonParameters.toString(),
168
                    params.getHost(),
169
                    dbfilename
170
                );      
171
            }
172
        } else if( splitSize>0 ) {
173
            connectionURL =  MessageFormat.format("jdbc:h2:tcp://{0}:{1,number,#######}/split:{3,number,##}:/{2}"+commonParameters.toString(),
174
                params.getHost(),
175
                (int) params.getPort(),
176
                dbfilename,
177
                splitSize
178
            );
179
        } else {
180
            connectionURL =  MessageFormat.format("jdbc:h2:tcp://{0}:{1,number,#######}/{2}"+commonParameters.toString(),
181
                params.getHost(),
182
                (int) params.getPort(),
183
                dbfilename
184
            );
185
        }
186
        LOGGER.debug("connectionURL: {}", connectionURL);
187
        return connectionURL;
188
    }
189
    
190
    public static synchronized void server_stop() {
191
            if (h2server == null) {
192
                LOGGER.info("The H2 server is already stopped.");
193
            } else {
194
                closeGlobalConnections();
195
                LOGGER.info("Stopping the H2 server.");
196
                LOGGER.info("  port  :" + h2server.getPort());
197
                LOGGER.info("  URL   :" + h2server.getURL());
198
                LOGGER.info("  shutdown server...");
199
                try {
200
                    h2server.shutdown();
201
                } catch (Throwable th) {
202
                    LOGGER.warn("Problems shutdown the H2 server.", th);
203
                }
204
                LOGGER.info("  Stoping server...");
205
                try {
206
                    h2server.stop();
207
                } catch (Throwable th) {
208
                    LOGGER.warn("Problems stopping the H2 server.", th);
209
                }
210
                LOGGER.info("  status:" + h2server.getStatus());
211
                h2server = null;
212
                LOGGER.info("H2 Server stopped");
213
            }
214
            startServer = true;
215
    }
216
    
217
    public static void server_start() {
218
        server_start(lastPort, lastAllowOthers);
219
    }
220
    
221
    public static synchronized void server_start(String port, Boolean allowOthers) {
222
            if( !enable_server ) {
223
                return;
224
            }
225
            if( startServer && h2server == null ) {
226
                if( StringUtils.isBlank(port) ) {
227
                    port = lastPort;
228
                }
229
                if( allowOthers==null ) {
230
                    allowOthers = lastAllowOthers;
231
                }
232
                try {
233
                    Server theH2Server;
234
                    if( allowOthers) {
235
                        theH2Server = Server.createTcpServer("-tcpPort", port, "-ifExists", "-tcpAllowOthers");
236
                    } else {
237
                        theH2Server = Server.createTcpServer("-tcpPort", port, "-ifExists");
238
                    }
239
                    theH2Server.start();
240
                    h2server = theH2Server;
241
                    LOGGER.info("H2 Server started" );
242
                    LOGGER.info("  Engine version : h2 "+ org.h2.engine.Constants.getFullVersion()+", h2gis "+H2GISversion.geth2gisVersion());
243
                    LOGGER.info("  Connection url : jdbc:h2:"+h2server.getURL()+"/ABSOLUTE_DATABASE_PATH;MODE=PostgreSQL;SCHEMA=PUBLIC;ALLOW_LITERALS=ALL");
244
                    LOGGER.info("  status:"+ h2server.getStatus());
245
                    Runtime.getRuntime().removeShutdownHook(shutdownHook);
246
                    Runtime.getRuntime().addShutdownHook(shutdownHook);
247
                    lastPort = port;
248
                    lastAllowOthers = allowOthers;
249
                } catch (SQLException ex) {
250
                    LOGGER.warn("H2 Server not started",ex);
251
                }
252
                // Tanto si consigue lanzar el server como si no, no lo vuelve a intentar
253
                startServer = false;
254
            }
255
    }
256
    
257
    public static void set_enable_server(boolean enable) {
258
        enable_server = enable;
259
    }
260
    
261
    public static void set_server_port(int port) {
262
        lastPort = Integer.toString(port);
263
    }
264
    
265
    public static boolean is_enable_server() {
266
        return enable_server;
267
    }
268
    
269
    public static synchronized boolean is_server_started() {
270
        return h2server!=null;
271
    }
272
    
273
    public static synchronized void addGlobalConnection(H2SpatialConnectionProvider connectionProvider) throws SQLException {
274
        if( globalConnections==null ) {
275
            globalConnections = new HashMap<>();
276
        }
277
        H2SpatialConnectionParameters connectionParameters = connectionProvider.getConnectionParameters();
278
        if( !connectionParameters.getMaintainGlobalConnection() ) {
279
            return;
280
        }
281
        String connectionProviderKey = getConnectionProviderKey(connectionParameters);
282
        Connection x = globalConnections.get(connectionProviderKey);
283
        if( x != null ) {
284
            return;
285
        }
286
        x = connectionProvider.getConnection();
287
        globalConnections.put(connectionProviderKey, x);
288
        
289
        //For debugging purposses, delete when finish.
290
        LOGGER.info("addGlobalConnection "+connectionProviderKey);
291
        LOGGER.info("globalConnections = "+globalConnections.size()+ " ");
292
        ThreadGroup threadGroup = Thread.currentThread().getThreadGroup();
293
        Thread[] threadList = new Thread[threadGroup.activeCount()];
294
        threadGroup.enumerate(threadList);
295
        List<String> threadNames = new ArrayList(); 
296
        for (Thread thread : threadList) {
297
            if(thread != null && StringUtils.startsWith(thread.getName(), "MVStore background writer")) {
298
                threadNames.add(thread.getName());
299
            }
300
        }
301
        if (threadNames.size() > 1) {
302
            for (String threadName : threadNames) {
303
                LOGGER.info("Thread "+threadName);
304
            }
305
            try {
306
                throw new RuntimeException("Excepcion para debug");
307
            } catch (Exception ex) {
308
                LOGGER.info("addGlobalConnection " + connectionProviderKey, ex);
309
            }
310
        }
311
        LOGGER.info("==================");
312
        // End "For debugging purposses, delete when finish."
313
    }
314
    
315
    public static String getConnectionProviderKey(JDBCConnectionParameters connectionParameters) {
316
        String pass = Hex.encodeHexString((connectionParameters.getPassword()+"").getBytes());
317
//        String pass = connectionParameters.getPassword();
318
        return connectionParameters.getUrl() + ";user:"+connectionParameters.getUser()+"@"+pass;
319
    }    
320
    
321
    public static synchronized void closeGlobalConnections() {
322
        if( globalConnections==null ) {
323
            return;
324
        }
325
        for (Connection conn : globalConnections.values()) {
326
            LOGGER.info("Clossing connection "+ JDBCUtils.getConnId(conn));
327
            JDBCUtils.closeQuietly(conn);
328
        }
329
        globalConnections = null;
330
    }
331
}