/** * {@inheritDoc} * * Look into the pool for an unused DbProvider. If no one find, create one. */ @Override public DbConnection getConnection() throws Exception { log().t(getName(),"getConnection"); boolean foundClosed = false; try { synchronized (pool) { for (InternalDbConnection con : pool) { if (con.isClosed() || con.checkTimedOut()) { foundClosed = true; } else if (!con.isUsed()) { con.setUsed(true); return new DbConnectionProxy(this, con); } } return createConnection(); } } finally { if (foundClosed) cleanup(false); } }
/** * Overwrite to configure new created connections before use. * * @return created connection or null if not possible * @throws Exception */ protected DbConnection createConnection() throws Exception { try { InternalDbConnection con = getProvider().createConnection(); if (con == null) return null; con.setPool(this); pool.add(con); if (tracePoolSize.value()) log().d("Create DB Connection",pool.size()); con.setUsed(true); //getDialect().initializeConnection(con, this); return new DbConnectionProxy(this, con); } catch (Exception e) { // special behavior for e.g. mysql, retry to get a connection after gc() // Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Too many connections if (e.getMessage() != null && e.getMessage().indexOf("Too many connections") > -1) { printStackTrace(); } throw e; } }
/** {@inheritDoc} */ @Override @JmxManaged(descrition="Return the usage of the connections") public String dumpUsage(boolean used) { StringBuilder out = new StringBuilder(); synchronized (pool) { for (ConnectionTrace trace : getStackTraces().values()) { out.append(trace.toString()).append("\n"); } } return out.toString(); }
/** * <p>getPool.</p> * * @param name a {@link java.lang.String} object. * @return a {@link de.mhus.lib.sql.DbPool} object. * @throws java.lang.Exception if any. */ public DbPool getPool(String name) throws Exception { if (bundle == null) throw new MException("Bundle already closed"); synchronized (bundle) { DbPool pool = bundle.get(name); if (pool == null) { IConfig poolCon = config.getNode(name); if (poolCon != null) { pool = new DefaultDbPool(poolCon, activator); bundle.put(name, pool); } else { throw new MException("pool config not found",name); } } return pool; } }
protected DbPool doCreateDataPool() { return new DefaultDbPool(new DataSourceProvider(getDataSource(), doCreateDialect(), doCreateConfig(), doCreateActivator() )); }
/** * {@inheritDoc} * * Cleanup the connection pool. Unused or closed connections will be removed. * TODO new strategy to remove unused connections - not prompt, need a timeout time or minimum pool size. */ @Override @JmxManaged(descrition="Cleanup unused connections") public void cleanup(boolean unusedAlso) { log().t(getName(),"cleanup"); boolean removed = false; synchronized (pool) { for (InternalDbConnection con : new LinkedList<InternalDbConnection>(pool)) { try { con.checkTimedOut(); if( unusedAlso && !con.isUsed() || con.isClosed()) { con.close(); pool.remove(con); removed = true; } } catch (Throwable t) {} // for secure - do not impact the thread } if (removed && tracePoolSize.value()) log().d("Pool cleanup",pool.size()); } }
storageDsProvider = new DataSourceProvider(); updateStorageDataSource(); storagePool = new DefaultDbPool(storageDsProvider); config.storage = new SqlDbStorage(storagePool,"storage"); archiveDsProvider = new DataSourceProvider(); updateArchiveDataSource(); archivePool = new DefaultDbPool(archiveDsProvider); config.archive = new SqlDbStorage(archivePool,"archive");