[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
r6682 - in trunk: gnue-appserver/src gnue-common/src/datasources gnue-co
From: |
johannes |
Subject: |
r6682 - in trunk: gnue-appserver/src gnue-common/src/datasources gnue-common/src/datasources/drivers/Base gnue-common/src/datasources/drivers/Base/Schema/Creation gnue-common/src/datasources/drivers/DBSIG2 gnue-common/src/datasources/drivers/appserver/appserver gnue-common/src/schema/scripter gnue-forms/src |
Date: |
Tue, 16 Nov 2004 09:13:09 -0600 (CST) |
Author: johannes
Date: 2004-11-16 09:13:08 -0600 (Tue, 16 Nov 2004)
New Revision: 6682
Modified:
trunk/gnue-appserver/src/data.py
trunk/gnue-appserver/src/geasList.py
trunk/gnue-appserver/src/geasSession.py
trunk/gnue-common/src/datasources/GConnections.py
trunk/gnue-common/src/datasources/GDataSource.py
trunk/gnue-common/src/datasources/drivers/Base/Connection.py
trunk/gnue-common/src/datasources/drivers/Base/ResultSet.py
trunk/gnue-common/src/datasources/drivers/Base/Schema/Creation/Creation.py
trunk/gnue-common/src/datasources/drivers/DBSIG2/Connection.py
trunk/gnue-common/src/datasources/drivers/appserver/appserver/Connection.py
trunk/gnue-common/src/schema/scripter/Scripter.py
trunk/gnue-forms/src/GFClient.py
Log:
Fixed some memory leaks and connections now really get closed after form is
closed
Modified: trunk/gnue-appserver/src/data.py
===================================================================
--- trunk/gnue-appserver/src/data.py 2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-appserver/src/data.py 2004-11-16 15:13:08 UTC (rev 6682)
@@ -607,10 +607,17 @@
# not yet cached, need to load from database
resultSet = _find (self.__connections, self.__database, table, row,
uncachedFields)
- if resultSet.current is None:
- return None
- r = record (self.__cache, self.__connections, self.__database, table,
row)
- r._fill (None, uncachedFields, resultSet.current)
+ try:
+ if resultSet.current is None:
+ return None
+
+ r = record (self.__cache, self.__connections, self.__database, table,
+ row)
+ r._fill (None, uncachedFields, resultSet.current)
+
+ finally:
+ resultSet.close ()
+
return r
# ---------------------------------------------------------------------------
@@ -632,13 +639,17 @@
resultSet = _createEmptyResultSet (self.__connections,
self.__database,
table, fields.keys ())
- resultSet.insertRecord ()
+ try:
+ resultSet.insertRecord ()
- for (field, value) in fields.items ():
- resultSet.current.setField (field, value)
+ for (field, value) in fields.items ():
+ resultSet.current.setField (field, value)
- resultSet.post ()
+ resultSet.post ()
+ finally:
+ resultSet.close ()
+
self.__inserted = []
self.__confirmedInserts = []
@@ -654,11 +665,15 @@
resultSet = _find (self.__connections, self.__database, table, row,
[u'gnue_id'] + fields.keys ())
- for (field, value) in fields.items ():
- resultSet.current.setField (field, value)
+ try:
+ for (field, value) in fields.items ():
+ resultSet.current.setField (field, value)
- resultSet.post ()
+ resultSet.post ()
+ finally:
+ resultSet.close ()
+
# perform all deletes
for (table, row) in self.__deleted:
# TODO: gnue-common should provide a method for deleting a record
@@ -666,9 +681,13 @@
# temporary resultSet for every record we delete
resultSet = _find (self.__connections, self.__database, table, row,
[u'gnue_id'])
- resultSet.current.delete ()
- resultSet.post ()
+ try:
+ resultSet.current.delete ()
+ resultSet.post ()
+ finally:
+ resultSet.close ()
+
self.__deleted = []
self.__confirmedDeletes = []
@@ -853,6 +872,23 @@
else:
return self.__buildRecords ()
+
+ # ---------------------------------------------------------------------------
+ # Close the record set
+ # ---------------------------------------------------------------------------
+
+ def close (self):
+ """
+ This function closes a record set which is no longer needed. It closes the
+ underlying result set and clears it's cache.
+ """
+
+ if self.__resultSet is not None:
+ self.__resultSet.close ()
+ self.__resultSet = None
+ self.__cache.clear ()
+
+
# =============================================================================
# Record class
# =============================================================================
@@ -926,13 +962,18 @@
# Not found in cache, so get it from the db
resultSet = _find (self.__connections, self.__database, self.__table,
self.__row, [field])
- if resultSet.current is not None:
- value = resultSet.current [field]
- self.__cache.write (self.__table, self.__row, field, value, 0)
- return value
- else:
- return None
+ try:
+ if resultSet.current is not None:
+ value = resultSet.current [field]
+ self.__cache.write (self.__table, self.__row, field, value, 0)
+ return value
+ else:
+ return None
+ finally:
+ resultSet.close ()
+
+
# ---------------------------------------------------------------------------
# Put the value for a field
# ---------------------------------------------------------------------------
@@ -1054,6 +1095,11 @@
c.commit ()
print 'Ok'
+ print 'closing record set ...',
+ rs.close ()
+ print 'Ok'
+
+
print 'connection.query for previously inserted record ...',
content = {None: (u'address_person', None, None, [u'address_name'])}
rs = c.query (content,
@@ -1107,6 +1153,10 @@
c.commit ()
print 'Ok'
+ print 'closing result set ...',
+ rs.close ()
+ print 'Ok'
+
print 'check if the record is really gone now ...',
content = {None: (u'address_person', None, None, [u'address_name'])}
rs = c.query (content,
@@ -1117,6 +1167,10 @@
raise Exception
print 'Ok'
+ print 'closing result set ...',
+ rs.close ()
+ print 'Ok'
+
print 'connection.close ...',
c.close ()
print 'Ok'
Modified: trunk/gnue-appserver/src/geasList.py
===================================================================
--- trunk/gnue-appserver/src/geasList.py 2004-11-16 11:05:10 UTC (rev
6681)
+++ trunk/gnue-appserver/src/geasList.py 2004-11-16 15:13:08 UTC (rev
6682)
@@ -47,11 +47,22 @@
self.__isComplete = False
self.__dsSorting = dsSort # sorted by datasource
self.__asSorting = asSort # additional sortorder of this list
+ self.__isClosed = False
+
+
+ # ---------------------------------------------------------------------------
+ # Call the apropriate fillup function
+ # ---------------------------------------------------------------------------
+
+ def __fillupFunc (self, count):
+ """
+ """
+
if len (self.__asSorting):
- self.__fillup = self.__fillupSorted
+ return self.__fillupSorted (count)
else:
- self.__fillup = self.__fillupUnsorted
+ return self.__fillupUnsorted (count)
# ---------------------------------------------------------------------------
@@ -155,6 +166,8 @@
return instance
else:
+ self.__recordset.close ()
+ self.__isClosed = True
return None
@@ -196,7 +209,7 @@
This function returns the number of instances available in this list.
"""
if self.__condition is not None:
- self.__fillup (0)
+ self.__fillupFunc (0)
return len (self.__instances)
else:
return self.__recordset.count ()
@@ -213,9 +226,9 @@
"""
if start < 0:
- self.__fillup (0)
+ self.__fillupFunc (0)
else:
- self.__fillup (start + count)
+ self.__fillupFunc (start + count)
result = []
for pos in range (start, min (start + count, len (self.__instances))):
@@ -224,3 +237,18 @@
return result
+ # ---------------------------------------------------------------------------
+ # Close the list instance
+ # ---------------------------------------------------------------------------
+
+ def close (self):
+ """
+ This function closes the list by freeing all references and resources
+ maintained by the list.
+ """
+
+ if not self.__isClosed:
+ self.__recordset.close ()
+
+ self.__instances = []
+ self.__unsorted = []
Modified: trunk/gnue-appserver/src/geasSession.py
===================================================================
--- trunk/gnue-appserver/src/geasSession.py 2004-11-16 11:05:10 UTC (rev
6681)
+++ trunk/gnue-appserver/src/geasSession.py 2004-11-16 15:13:08 UTC (rev
6682)
@@ -91,7 +91,7 @@
# Initalize
# ---------------------------------------------------------------------------
- def __init__ (self, connections, authAdapter, sm, id, params):
+ def __init__ (self, connections, authAdapter, sm, sid, params):
self.loggedIn = 0
self.connections = connections
@@ -108,7 +108,7 @@
self.__operation = None
self.sm = sm # The session manager
- self.id = id # The session id
+ self.id = sid # The session id
self.parameters = params
self.locale = params.get ('language')
self.user = None
@@ -254,10 +254,25 @@
if self.locale:
i18n.setcurrentlocale (self.locale)
+ for item in self.__lists.values ():
+ item.close ()
+
+ self.__lists = {}
+ self.__listcount = 0
+ self.__dirtyInstances = {}
+ self.filters = {}
+
# FIXME: should the authAdapter be contacted?
self.__connection.close ()
self.loggedIn = 0
+ self.__connection = None
+ self.__operation = None
+
+ self.sm = None
+ self.parameters = None
+
+
# ---------------------------------------------------------------------------
# Commit the active transaction
# ---------------------------------------------------------------------------
Modified: trunk/gnue-common/src/datasources/GConnections.py
===================================================================
--- trunk/gnue-common/src/datasources/GConnections.py 2004-11-16 11:05:10 UTC
(rev 6681)
+++ trunk/gnue-common/src/datasources/GConnections.py 2004-11-16 15:13:08 UTC
(rev 6682)
@@ -275,12 +275,6 @@
conn.introspector = behavior (conn)
- # Create the schema creator instance
- if hasattr (conn, 'defaultCreator'):
- conn.schemaCreator = conn.defaultCreator (conn, conn.introspector)
- else:
- conn.schemaCreator = None
-
if login:
self.loginToConnection (conn)
@@ -479,6 +473,7 @@
connection.__connected = True
+
def getAuthenticatedUser(self, connection=None):
try:
if connection == None:
@@ -510,5 +505,9 @@
This function closes all open connections.
"""
for connection in self._openConnections.values():
- connection.close()
+ connection.close ()
+
+ if self._authenticatedUsers.has_key (connection):
+ del self._authenticatedUsers [connection]
+
self._openConnections = {}
Modified: trunk/gnue-common/src/datasources/GDataSource.py
===================================================================
--- trunk/gnue-common/src/datasources/GDataSource.py 2004-11-16 11:05:10 UTC
(rev 6681)
+++ trunk/gnue-common/src/datasources/GDataSource.py 2004-11-16 15:13:08 UTC
(rev 6682)
@@ -690,7 +690,7 @@
return self._dataObject._connection.introspector
def getSchemaCreator (self):
- return self._dataObject._connection.schemaCreator
+ return self._dataObject._connection.getSchemaCreator ()
# =============================================================================
Modified: trunk/gnue-common/src/datasources/drivers/Base/Connection.py
===================================================================
--- trunk/gnue-common/src/datasources/drivers/Base/Connection.py
2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-common/src/datasources/drivers/Base/Connection.py
2004-11-16 15:13:08 UTC (rev 6682)
@@ -70,6 +70,22 @@
# ---------------------------------------------------------------------------
+ # Create a new instance of the associated schema creator
+ # ---------------------------------------------------------------------------
+
+ def getSchemaCreator (self):
+ """
+ This function creates a new instance of the schema creator associated with
+ this driver or None if no creator is available.
+ """
+
+ if hasattr (self, 'defaultCreator') and self.defaultCreator:
+ return self.defaultCreator (self)
+ else:
+ return None
+
+
+ # ---------------------------------------------------------------------------
# update the schema definition
# ---------------------------------------------------------------------------
@@ -89,118 +105,123 @@
result = ([], [], [])
- if self.schemaCreator is None:
+ schemaCreator = self.getSchemaCreator ()
+
+ if schemaCreator is None:
return result
- workingSet = copy.copy (definition)
- constraintSet = {}
+ try:
+ workingSet = copy.copy (definition)
+ constraintSet = {}
- # before any actions are performed, validate the given definitions
- for table in definition:
- self.schemaCreator.validate (table)
+ # before any actions are performed, validate the given definitions
+ for table in definition:
+ schemaCreator.validate (table)
- # in a first run we remove all constraint definitions from the tables, so
- # we can add or alter all tables without having troubles with order of
- # occurence.
- for table in workingSet:
- # Do we have already a table with that name?
- res = self.introspector.find (name = table ['name'])
+ # in a first run we remove all constraint definitions from the tables, so
+ # we can add or alter all tables without having troubles with order of
+ # occurence.
+ for table in workingSet:
+ # Do we have already a table with that name?
+ res = self.introspector.find (name = table ['name'])
- if res is not None:
- method = self.schemaCreator.modifyTable
- # Please note: we keep existingFields sequence in all lowercase
- existingFields = [f.name.lower () for f in res [0].fields ()]
+ if res is not None:
+ method = schemaCreator.modifyTable
+ # Please note: we keep existingFields sequence in all lowercase
+ existingFields = [f.name.lower () for f in res [0].fields ()]
- # keep only new fields
- keep = []
- for field in table ['fields']:
- if not field ['name'].lower () in existingFields:
- keep.append (field)
+ # keep only new fields
+ keep = []
+ for field in table ['fields']:
+ if not field ['name'].lower () in existingFields:
+ keep.append (field)
- table ['fields'] = keep
+ table ['fields'] = keep
- # on updates of a table we cannot use a primary key
- if table.has_key ('primarykey'):
- del table ['primarykey']
+ # on updates of a table we cannot use a primary key
+ if table.has_key ('primarykey'):
+ del table ['primarykey']
+
+ # keep modified or new indices only
+ if table.has_key ('indices'):
+ keep = []
- # keep modified or new indices only
- if table.has_key ('indices'):
- keep = []
+ # if driver supports index-introspection we'll use it
+ if hasattr (res [0], 'indices'):
+ for index in table ['indices']:
+ oldIndex = None
+ for (name, value) in res [0].indices.items ():
+ if name.lower () == index ['name'].lower ():
+ oldIndex = value
- # if driver supports index-introspection we'll use it
- if hasattr (res [0], 'indices'):
- for index in table ['indices']:
- oldIndex = None
- for (name, value) in res [0].indices.items ():
- if name.lower () == index ['name'].lower ():
- oldIndex = value
+ if oldIndex is None:
+ keep.append (index)
+ else:
+ old = [f.lower () for f in oldIndex ['fields']]
+ new = [f.lower () for f in index ['fields']]
- if oldIndex is None:
- keep.append (index)
- else:
- old = [f.lower () for f in oldIndex ['fields']]
- new = [f.lower () for f in index ['fields']]
+ if oldIndex ['unique'] != index ['unique'] or old != new:
- if oldIndex ['unique'] != index ['unique'] or old != new:
+ # make sure the backend has a possibility to remove the old
+ # index before changing it
+ if not table.has_key ('old_indices'):
+ table ['old_indices'] = []
+ table ['old_indices'].append (index ['name'])
- # make sure the backend has a possibility to remove the old
- # index before changing it
- if not table.has_key ('old_indices'):
- table ['old_indices'] = []
- table ['old_indices'].append (index ['name'])
+ keep.append (index)
+ else:
+ # if no index-introspection available we only keep an index, if
it
+ # has new fields
+ for index in table ['indices']:
+ for field in index ['fields']:
+ if not field.lower () in existingFields:
+ # make sure the backend has a possibility to remove the old
+ # index before changing it
+ if not table.has_key ('old_indices'):
+ table ['old_indices'] = []
+ table ['old_indices'].append (index ['name'])
- keep.append (index)
- else:
- # if no index-introspection available we only keep an index, if it
- # has new fields
- for index in table ['indices']:
- for field in index ['fields']:
- if not field.lower () in existingFields:
- # make sure the backend has a possibility to remove the old
- # index before changing it
- if not table.has_key ('old_indices'):
- table ['old_indices'] = []
- table ['old_indices'].append (index ['name'])
+ keep.append (index)
+ break
- keep.append (index)
- break
+ table ['indices'] = keep
- table ['indices'] = keep
+ # we create a constraint on a table update only if it contains new
+ # fields
+ if table.has_key ('constraints'):
+ keep = []
- # we create a constraint on a table update only if it contains new
- # fields
- if table.has_key ('constraints'):
- keep = []
+ for constraint in table ['constraints']:
+ for field in constraint ['fields']:
+ if not field.lower () in existingFields:
+ keep.append (constraint)
+ break
- for constraint in table ['constraints']:
- for field in constraint ['fields']:
- if not field.lower () in existingFields:
- keep.append (constraint)
- break
+ table ['constraints'] = keep
- table ['constraints'] = keep
+ else:
+ method = schemaCreator.createTable
- else:
- method = self.schemaCreator.createTable
-
- if table.has_key ('constraints'):
- constraintSet [table ['name']] = {'name': table ['name'],
+ if table.has_key ('constraints'):
+ constraintSet [table ['name']] = {'name': table ['name'],
'constraints': table ['constraints']}
- del table ['constraints']
+ del table ['constraints']
- # before we execute the planned action, have a look if there's still work
- # to be done
- perform = table.has_key ('fields') and len (table ['fields'])
- perform = perform or table.has_key ('primarykey')
- perform = perform or (table.has_key ('indices') and \
- len (table ['indices']))
+ # before we execute the planned action, have a look if there's still
+ # work to be done
+ perform = table.has_key ('fields') and len (table ['fields'])
+ perform = perform or table.has_key ('primarykey')
+ perform = perform or (table.has_key ('indices') and \
+ len (table ['indices']))
- if perform:
- self.schemaCreator.mergeTuple (result, method (table, codeOnly))
+ if perform:
+ schemaCreator.mergeTuple (result, method (table, codeOnly))
- # on the second run we process all constraints
- for table in constraintSet.values ():
- self.schemaCreator.mergeTuple (result,
- self.schemaCreator.createTable (table, codeOnly))
+ # on the second run we process all constraints
+ for table in constraintSet.values ():
+ schemaCreator.mergeTuple (result,
+ schemaCreator.createTable (table, codeOnly))
+ return result
- return result
+ finally:
+ schemaCreator.close ()
Modified: trunk/gnue-common/src/datasources/drivers/Base/ResultSet.py
===================================================================
--- trunk/gnue-common/src/datasources/drivers/Base/ResultSet.py 2004-11-16
11:05:10 UTC (rev 6681)
+++ trunk/gnue-common/src/datasources/drivers/Base/ResultSet.py 2004-11-16
15:13:08 UTC (rev 6682)
@@ -222,7 +222,24 @@
self.__notifyListeners ()
return self.current
+ # ---------------------------------------------------------------------------
+ # Close the result set
+ # ---------------------------------------------------------------------------
+ def close (self):
+ """
+ This function should be closed, if a result set is no longer needed. It
+ breaks up reference cycles so garbage collection can do it's job.
+ """
+
+ for item in self._cachedRecords:
+ item._parent = None
+
+ self._dataObject = None
+ self._cachedRecords = []
+ self.__listeners = []
+
+
def duplicateRecord(self, exclude=(), include=()):
current = self.current
inserted = self.insertRecord()
Modified:
trunk/gnue-common/src/datasources/drivers/Base/Schema/Creation/Creation.py
===================================================================
--- trunk/gnue-common/src/datasources/drivers/Base/Schema/Creation/Creation.py
2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-common/src/datasources/drivers/Base/Schema/Creation/Creation.py
2004-11-16 15:13:08 UTC (rev 6682)
@@ -329,7 +329,20 @@
self._validateConstraint (tableName, constraint)
+ # ---------------------------------------------------------------------------
+ # Make sure to release all references
+ # ---------------------------------------------------------------------------
+ def close (self):
+ """
+ This function releases all circular references held by the creator instance
+ """
+
+ self.introspector = None
+ self.connection = None
+ self.lookup = {}
+
+
# ---------------------------------------------------------------------------
# Call the appropriate method for a type-transformation
# ---------------------------------------------------------------------------
Modified: trunk/gnue-common/src/datasources/drivers/DBSIG2/Connection.py
===================================================================
--- trunk/gnue-common/src/datasources/drivers/DBSIG2/Connection.py
2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-common/src/datasources/drivers/DBSIG2/Connection.py
2004-11-16 15:13:08 UTC (rev 6682)
@@ -100,7 +100,8 @@
"""
Close the DBSIG2 Connection.
"""
- self.native.close()
+ if hasattr (self, 'native') and self.native is not None:
+ self.native.close ()
def _beginTransaction(self):
Modified:
trunk/gnue-common/src/datasources/drivers/appserver/appserver/Connection.py
===================================================================
--- trunk/gnue-common/src/datasources/drivers/appserver/appserver/Connection.py
2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-common/src/datasources/drivers/appserver/appserver/Connection.py
2004-11-16 15:13:08 UTC (rev 6682)
@@ -144,7 +144,8 @@
# ---------------------------------------------------------------------------
def close (self):
- self._sm.close (self._sess_id, False)
+ if self._sm is not None:
+ self._sm.close (self._sess_id, False)
# Can be removed after the call to _dataConnection.cursor() is removed from
# the Base driver
@@ -206,7 +207,6 @@
break
if not found:
- print "shit"
raise Exceptions.LoginError, \
u_("'%(value)s' is not a valid filter-value for '%(filter)s'") \
% {'value': value,
Modified: trunk/gnue-common/src/schema/scripter/Scripter.py
===================================================================
--- trunk/gnue-common/src/schema/scripter/Scripter.py 2004-11-16 11:05:10 UTC
(rev 6681)
+++ trunk/gnue-common/src/schema/scripter/Scripter.py 2004-11-16 15:13:08 UTC
(rev 6682)
@@ -140,9 +140,14 @@
self.verifyDataKeys ()
if self.OPTIONS ['createdb']:
- if self.connection.schemaCreator is not None:
- self.connection.schemaCreator.createDatabase ()
+ creator = self.connection.getSchemaCreator ()
+ if creator is not None:
+ try:
+ creator.createDatabase ()
+ finally:
+ creator.close ()
+
if self.__doSchema:
self.executeAndGenerateCode ()
Modified: trunk/gnue-forms/src/GFClient.py
===================================================================
--- trunk/gnue-forms/src/GFClient.py 2004-11-16 11:05:10 UTC (rev 6681)
+++ trunk/gnue-forms/src/GFClient.py 2004-11-16 15:13:08 UTC (rev 6682)
@@ -158,7 +158,9 @@
instance.addDialogs ()
instance.activate ()
+ self.getConnectionManager ().closeAll ()
+
# ---------------------------------------------------------------------------
# List all available user interfaces
# ---------------------------------------------------------------------------
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- r6682 - in trunk: gnue-appserver/src gnue-common/src/datasources gnue-common/src/datasources/drivers/Base gnue-common/src/datasources/drivers/Base/Schema/Creation gnue-common/src/datasources/drivers/DBSIG2 gnue-common/src/datasources/drivers/appserver/appserver gnue-common/src/schema/scripter gnue-forms/src,
johannes <=