Implemented rcube::sleep() method for disconnecting all external connection in long-running/sleeping scripts

Conflicts:

	program/lib/Roundcube/rcube_db.php
pull/5754/head
Aleksander Machniak 8 years ago
parent 6d8245523d
commit 4378699663

@ -209,25 +209,7 @@ class rcube
}
$this->memcache = new Memcache;
$this->mc_available = 0;
// add all configured hosts to pool
$pconnect = $this->config->get('memcache_pconnect', true);
$timeout = $this->config->get('memcache_timeout', 1);
$retry_interval = $this->config->get('memcache_retry_interval', 15);
foreach ($this->config->get('memcache_hosts', array()) as $host) {
if (substr($host, 0, 7) != 'unix://') {
list($host, $port) = explode(':', $host);
if (!$port) $port = 11211;
}
else {
$port = 0;
}
$this->mc_available += intval($this->memcache->addServer(
$host, $port, $pconnect, 1, $timeout, $retry_interval, false, array($this, 'memcache_failure')));
}
$this->memcache_init();
// test connection and failover (will result in $this->mc_available == 0 on complete failure)
$this->memcache->increment('__CONNECTIONTEST__', 1); // NOP if key doesn't exist
@ -240,6 +222,34 @@ class rcube
return $this->memcache;
}
/**
* Get global handle for memcache access
*
* @return object Memcache
*/
protected function memcache_init()
{
$this->mc_available = 0;
// add all configured hosts to pool
$pconnect = $this->config->get('memcache_pconnect', true);
$timeout = $this->config->get('memcache_timeout', 1);
$retry_interval = $this->config->get('memcache_retry_interval', 15);
foreach ($this->config->get('memcache_hosts', array()) as $host) {
if (substr($host, 0, 7) != 'unix://') {
list($host, $port) = explode(':', $host);
if (!$port) $port = 11211;
}
else {
$port = 0;
}
$this->mc_available += intval($this->memcache->addServer(
$host, $port, $pconnect, 1, $timeout, $retry_interval, false, array($this, 'memcache_failure')));
}
}
/**
* Callback for memcache failure
*/
@ -1021,6 +1031,40 @@ class rcube
$this->shutdown_functions[] = $function;
}
/**
* When you're going to sleep the script execution for a longer time
* it is good to close all external connections (sql, memcache, SMTP, IMAP).
*
* No action is required on wake up, all connections will be
* re-established automatically.
*/
public function sleep()
{
foreach ($this->caches as $cache) {
if (is_object($cache)) {
$cache->close();
}
}
if ($this->storage) {
$this->storage->close();
}
if ($this->db) {
$this->db->closeConnection();
}
if ($this->memcache) {
$this->memcache->close();
// after close() need to re-init memcache
$this->memcache_init();
}
if ($this->smtp) {
$this->smtp->disconnect();
}
}
/**
* Quote a given string.
* Shortcut function for rcube_utils::rep_specialchars_output()

@ -235,7 +235,11 @@ class rcube_cache
}
// reset internal cache index, thanks to this we can force index reload
$this->index = null;
$this->index = null;
$this->index_changed = false;
$this->cache = array();
$this->cache_sums = array();
$this->cache_changes = array();
}
/**
@ -640,13 +644,15 @@ class rcube_cache
$this->max_packet -= 2000;
}
else if ($this->type == 'memcache') {
$stats = $this->db->getStats();
$remaining = $stats['limit_maxbytes'] - $stats['bytes'];
$this->max_packet = min($remaining / 5, $this->max_packet);
if ($stats = $this->db->getStats()) {
$remaining = $stats['limit_maxbytes'] - $stats['bytes'];
$this->max_packet = min($remaining / 5, $this->max_packet);
}
}
else if ($this->type == 'apc' && function_exists('apc_sma_info')) {
$stats = apc_sma_info();
$this->max_packet = min($stats['avail_mem'] / 5, $this->max_packet);
if ($stats = apc_sma_info()) {
$this->max_packet = min($stats['avail_mem'] / 5, $this->max_packet);
}
}
}

@ -230,7 +230,11 @@ class rcube_cache_shared
}
// reset internal cache index, thanks to this we can force index reload
$this->index = null;
$this->index = null;
$this->index_changed = false;
$this->cache = array();
$this->cache_sums = array();
$this->cache_changes = array();
}
/**
@ -627,13 +631,15 @@ class rcube_cache_shared
$this->max_packet -= 2000;
}
else if ($this->type == 'memcache') {
$stats = $this->db->getStats();
$remaining = $stats['limit_maxbytes'] - $stats['bytes'];
$this->max_packet = min($remaining / 5, $this->max_packet);
if ($stats = $this->db->getStats()) {
$remaining = $stats['limit_maxbytes'] - $stats['bytes'];
$this->max_packet = min($remaining / 5, $this->max_packet);
}
}
else if ($this->type == 'apc' && function_exists('apc_sma_info')) {
$stats = apc_sma_info();
$this->max_packet = min($stats['avail_mem'] / 5, $this->max_packet);
if ($stats = apc_sma_info()) {
$this->max_packet = min($stats['avail_mem'] / 5, $this->max_packet);
}
}
}

@ -773,6 +773,20 @@ class rcube_db
return $this->last_result = $this->dbh->rollBack();
}
/**
* Terminate database connection.
*/
public function closeConnection()
{
$this->db_connected = false;
$this->db_index = 0;
// release statement and connection resources
$this->last_result = null;
$this->dbh = null;
$this->dbhs = array();
}
/**
* Formats input so it can be safely used in a query
*

@ -601,4 +601,18 @@ class rcube_db_oracle extends rcube_db
return $this->last_result = $this->dbh->rollBack();
}
/**
* Terminate database connection.
*/
public function closeConnection()
{
// release statement and close connection(s)
$this->last_result = null;
foreach ($this->dbhs as $dbh) {
oci_close($dbh);
}
parent::closeConnection();
}
}

@ -204,7 +204,9 @@ class rcube_imap extends rcube_storage
*/
public function close()
{
$this->connect_done = false;
$this->conn->closeConnection();
if ($this->mcache) {
$this->mcache->close();
}

Loading…
Cancel
Save