/** * Puts the specified HTable back into the pool. * * <p>If the pool already contains <i>maxSize</i> references to the table, then the table instance * gets closed after flushing buffered edits. * * @param table table */ private void returnTable(HTableInterface table) throws IOException { // this is the old putTable method renamed and made private String tableName = Bytes.toString(table.getTableName()); if (tables.size(tableName) >= maxSize) { // release table instance since we're not reusing it this.tables.remove(tableName, table); this.tableFactory.releaseHTableInterface(table); return; } tables.put(tableName, table); }
/** * Get a reference to the specified table from the pool. * * <p>Create a new one if one is not available. * * @param tableName table name * @return a reference to the specified table * @throws RuntimeException if there is a problem instantiating the HTable */ private HTableInterface findOrCreateTable(String tableName) { HTableInterface table = tables.get(tableName); if (table == null) { table = createHTable(tableName); } return table; }
/** Stop all threads related to this client. No further calls may be made using this client. */ public void stop() { if (LOG.isDebugEnabled()) { LOG.debug("Stopping client"); } if (!running.compareAndSet(true, false)) { return; } // wake up all connections synchronized (connections) { for (Connection conn : connections.values()) { conn.interrupt(); } } // wait until all connections are closed while (!connections.isEmpty()) { try { Thread.sleep(100); } catch (InterruptedException ignored) { } } }
/* Get a connection from the pool, or create a new one and add it to the * pool. Connections to a given host/port are reused. */ protected Connection getConnection( InetSocketAddress addr, Class<? extends VersionedProtocol> protocol, User ticket, int rpcTimeout, Call call) throws IOException, InterruptedException { if (!running.get()) { // the client is stopped throw new IOException("The client is stopped"); } Connection connection; /* we could avoid this allocation for each RPC by having a * connectionsId object and with set() method. We need to manage the * refs for keys in HashMap properly. For now its ok. */ ConnectionId remoteId = new ConnectionId(addr, protocol, ticket, rpcTimeout); synchronized (connections) { connection = connections.get(remoteId); if (connection == null) { connection = createConnection(remoteId); connections.put(remoteId, connection); } } connection.addCall(call); // we don't invoke the method below inside "synchronized (connections)" // block above. The reason for that is if the server happens to be slow, // it will take longer to establish a connection and that will slow the // entire system down. // Moreover, if the connection is currently created, there will be many threads // waiting here; as setupIOstreams is synchronized. If the connection fails with a // timeout, they will all fail simultaneously. This is checked in setupIOstreams. connection.setupIOstreams(); return connection; }
int getCurrentPoolSize(String tableName) { return tables.size(tableName); }
/** * Closes all the HTable instances , belonging to all tables in the table pool. * * <p>Note: this is a 'shutdown' of all the table pools. */ public void close() throws IOException { for (String tableName : tables.keySet()) { closeTablePool(tableName); } this.tables.clear(); }