fixed Storage copy
This commit is contained in:
@@ -1 +1 @@
|
|||||||
Version 2.0.9 (2012-09-30 08:37:19) dev
|
Version 2.0.9 (2012-09-30 13:19:56) dev
|
||||||
|
|||||||
+35
-38
@@ -488,7 +488,7 @@ if 'google' in DRIVERS:
|
|||||||
|
|
||||||
class ConnectionPool(object):
|
class ConnectionPool(object):
|
||||||
|
|
||||||
pools = {}
|
POOLS = {}
|
||||||
check_active_connection = True
|
check_active_connection = True
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
@@ -497,36 +497,31 @@ class ConnectionPool(object):
|
|||||||
|
|
||||||
# ## this allows gluon to commit/rollback all dbs in this thread
|
# ## this allows gluon to commit/rollback all dbs in this thread
|
||||||
|
|
||||||
@staticmethod
|
def close(self,action='commit',really=True):
|
||||||
def recycle_connection(adapter,action):
|
|
||||||
if action:
|
if action:
|
||||||
if callable(action):
|
if callable(action):
|
||||||
action(adapter)
|
action(self)
|
||||||
else:
|
else:
|
||||||
getattr(adapter, action)()
|
getattr(self, action)()
|
||||||
# ## if you want pools, recycle this connection
|
# ## if you want pools, recycle this connection
|
||||||
really = True
|
if self.pool_size:
|
||||||
if adapter.pool_size:
|
|
||||||
GLOBAL_LOCKER.acquire()
|
GLOBAL_LOCKER.acquire()
|
||||||
pool = ConnectionPool.pools[adapter.uri]
|
pool = ConnectionPool.POOLS[self.uri]
|
||||||
if len(pool) < adapter.pool_size:
|
if len(pool) < self.pool_size:
|
||||||
pool.append(adapter.connection)
|
pool.append(self.connection)
|
||||||
really = False
|
really = False
|
||||||
GLOBAL_LOCKER.release()
|
GLOBAL_LOCKER.release()
|
||||||
if really:
|
if really:
|
||||||
getattr(adapter, 'close')()
|
self.close_connection()
|
||||||
|
self.connection = None
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def close_all_instances(action):
|
def close_all_instances(action):
|
||||||
""" to close cleanly databases in a multithreaded environment """
|
""" to close cleanly databases in a multithreaded environment """
|
||||||
dbs = getattr(THREAD_LOCAL,'db_instances',{}).items()
|
dbs = getattr(THREAD_LOCAL,'db_instances',{}).items()
|
||||||
for singleton_code, db in dbs:
|
for singleton_code, db in dbs:
|
||||||
try:
|
if hasattr(db,'_adapter'):
|
||||||
adapter = db._adapter
|
db._adapter.close(action)
|
||||||
except AttributeError:
|
|
||||||
pass
|
|
||||||
else:
|
|
||||||
ConnectionPool.recycle_connection(adapter,action)
|
|
||||||
del THREAD_LOCAL.db_instances[singleton_code]
|
del THREAD_LOCAL.db_instances[singleton_code]
|
||||||
if callable(action):
|
if callable(action):
|
||||||
action(None)
|
action(None)
|
||||||
@@ -544,13 +539,7 @@ class ConnectionPool(object):
|
|||||||
""" this it is suppoed to be overloaded by adtapters"""
|
""" this it is suppoed to be overloaded by adtapters"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def reconnect(self):
|
def pool_connection(self, f=None, cursor=True):
|
||||||
""" allows a thread to re-connect to server or re-pool """
|
|
||||||
ConnectionPool.recycle_connection(self,False) ### WHY?
|
|
||||||
self.pool_connection(self._connection_function)
|
|
||||||
self.after_connection()
|
|
||||||
|
|
||||||
def pool_connection(self, f, cursor=True):
|
|
||||||
"""
|
"""
|
||||||
this function defines: self.connection and self.cursor
|
this function defines: self.connection and self.cursor
|
||||||
(iff cursor is True)
|
(iff cursor is True)
|
||||||
@@ -558,19 +547,25 @@ class ConnectionPool(object):
|
|||||||
if the connection is not active (closed by db server) it will loop
|
if the connection is not active (closed by db server) it will loop
|
||||||
if not self.pool_size or no active connections in pool makes a new one
|
if not self.pool_size or no active connections in pool makes a new one
|
||||||
"""
|
"""
|
||||||
pools = ConnectionPool.pools
|
if getattr(self,'connection',None) != None:
|
||||||
self._connection_function = f
|
return
|
||||||
|
if not f is None:
|
||||||
|
self._connection_function = f
|
||||||
|
else:
|
||||||
|
f = self._connection_function
|
||||||
|
|
||||||
if not self.pool_size:
|
if not self.pool_size:
|
||||||
self.connection = f()
|
self.connection = f()
|
||||||
self.cursor = cursor and self.connection.cursor()
|
self.cursor = cursor and self.connection.cursor()
|
||||||
else:
|
else:
|
||||||
uri = self.uri
|
uri = self.uri
|
||||||
|
POOLS = ConnectionPool.POOLS
|
||||||
while True:
|
while True:
|
||||||
GLOBAL_LOCKER.acquire()
|
GLOBAL_LOCKER.acquire()
|
||||||
if not uri in pools:
|
if not uri in POOLS:
|
||||||
pools[uri] = []
|
POOLS[uri] = []
|
||||||
if pools[uri]:
|
if POOLS[uri]:
|
||||||
self.connection = pools[uri].pop()
|
self.connection = POOLS[uri].pop()
|
||||||
GLOBAL_LOCKER.release()
|
GLOBAL_LOCKER.release()
|
||||||
self.cursor = cursor and self.connection.cursor()
|
self.cursor = cursor and self.connection.cursor()
|
||||||
try:
|
try:
|
||||||
@@ -584,6 +579,8 @@ class ConnectionPool(object):
|
|||||||
self.connection = f()
|
self.connection = f()
|
||||||
self.cursor = cursor and self.connection.cursor()
|
self.cursor = cursor and self.connection.cursor()
|
||||||
break
|
break
|
||||||
|
self.after_connection()
|
||||||
|
|
||||||
|
|
||||||
###################################################################################
|
###################################################################################
|
||||||
# this is a generic adapter that does nothing; all others are derived from this one
|
# this is a generic adapter that does nothing; all others are derived from this one
|
||||||
@@ -1638,7 +1635,7 @@ class BaseAdapter(ConnectionPool):
|
|||||||
def rollback(self):
|
def rollback(self):
|
||||||
return self.connection.rollback()
|
return self.connection.rollback()
|
||||||
|
|
||||||
def close(self):
|
def close_connection(self):
|
||||||
return self.connection.close()
|
return self.connection.close()
|
||||||
|
|
||||||
def distributed_transaction_begin(self, key):
|
def distributed_transaction_begin(self, key):
|
||||||
@@ -3968,7 +3965,7 @@ class DatabaseStoredFile:
|
|||||||
def write(self,data):
|
def write(self,data):
|
||||||
self.data += data
|
self.data += data
|
||||||
|
|
||||||
def close(self):
|
def close_connection(self):
|
||||||
self.db.executesql("DELETE FROM web2py_filesystem WHERE path='%s'" \
|
self.db.executesql("DELETE FROM web2py_filesystem WHERE path='%s'" \
|
||||||
% self.filename)
|
% self.filename)
|
||||||
query = "INSERT INTO web2py_filesystem(path,content) VALUES ('%s','%s')"\
|
query = "INSERT INTO web2py_filesystem(path,content) VALUES ('%s','%s')"\
|
||||||
@@ -4154,7 +4151,7 @@ class NoSQLAdapter(BaseAdapter):
|
|||||||
"""
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def close(self):
|
def close_connection(self):
|
||||||
"""
|
"""
|
||||||
remember: no transactions on many NoSQL
|
remember: no transactions on many NoSQL
|
||||||
"""
|
"""
|
||||||
@@ -5526,7 +5523,7 @@ class IMAPAdapter(NoSQLAdapter):
|
|||||||
closing
|
closing
|
||||||
|
|
||||||
"""
|
"""
|
||||||
pools = ConnectionPool.pools
|
POOLS = ConnectionPool.POOLS
|
||||||
if not self.pool_size:
|
if not self.pool_size:
|
||||||
self.connection = f()
|
self.connection = f()
|
||||||
self.cursor = cursor and self.connection.cursor()
|
self.cursor = cursor and self.connection.cursor()
|
||||||
@@ -5534,10 +5531,10 @@ class IMAPAdapter(NoSQLAdapter):
|
|||||||
uri = self.uri
|
uri = self.uri
|
||||||
while True:
|
while True:
|
||||||
GLOBAL_LOCKER.acquire()
|
GLOBAL_LOCKER.acquire()
|
||||||
if not uri in pools:
|
if not uri in POOLS:
|
||||||
pools[uri] = []
|
POOLS[uri] = []
|
||||||
if pools[uri]:
|
if POOLS[uri]:
|
||||||
self.connection = pools[uri].pop()
|
self.connection = POOLS[uri].pop()
|
||||||
GLOBAL_LOCKER.release()
|
GLOBAL_LOCKER.release()
|
||||||
self.cursor = cursor and self.connection.cursor()
|
self.cursor = cursor and self.connection.cursor()
|
||||||
if self.cursor and self.check_active_connection:
|
if self.cursor and self.check_active_connection:
|
||||||
|
|||||||
+2
-1
@@ -46,7 +46,8 @@ class Storage(dict):
|
|||||||
__repr__ = lambda self: '<Storage %s>' % dict.__repr__(self)
|
__repr__ = lambda self: '<Storage %s>' % dict.__repr__(self)
|
||||||
# http://stackoverflow.com/questions/5247250/why-does-pickle-getstate-accept-as-a-return-value-the-very-instance-it-requi
|
# http://stackoverflow.com/questions/5247250/why-does-pickle-getstate-accept-as-a-return-value-the-very-instance-it-requi
|
||||||
__getstate__ = lambda self: None
|
__getstate__ = lambda self: None
|
||||||
# __reduce_ex__ = None
|
__copy__ = lambda self: Storage(self)
|
||||||
|
|
||||||
|
|
||||||
def getlist(self,key):
|
def getlist(self,key):
|
||||||
"""
|
"""
|
||||||
|
|||||||
Reference in New Issue
Block a user