[Checkins] SVN: zodbcode/trunk/ Get ready for a release that seems
to be compatible with ZODB 3.8.
Stephan Richter
srichter at cosmos.phy.tufts.edu
Wed Oct 10 12:23:56 EDT 2007
Log message for revision 80804:
Get ready for a release that seems to be compatible with ZODB 3.8.
Changed:
A zodbcode/trunk/CHANGES.txt
A zodbcode/trunk/README.txt
U zodbcode/trunk/setup.py
_U zodbcode/trunk/src/
U zodbcode/trunk/src/zodbcode/module.txt
-=-
Added: zodbcode/trunk/CHANGES.txt
===================================================================
--- zodbcode/trunk/CHANGES.txt (rev 0)
+++ zodbcode/trunk/CHANGES.txt 2007-10-10 16:23:55 UTC (rev 80804)
@@ -0,0 +1,18 @@
+=======
+CHANGES
+=======
+
+3.4.0b2 (2007-10-10)
+--------------------
+
+- Adjust code to work with latest version of ZODB (3.8).
+
+- Converted ``module.txt`` to REST from STX.
+
+- Improved package meta-data.
+
+
+3.4.0b1 (2007-??-10)
+--------------------
+
+- Initial release independent of the main Zope tree.
Property changes on: zodbcode/trunk/CHANGES.txt
___________________________________________________________________
Name: svn:eol-style
+ native
Added: zodbcode/trunk/README.txt
===================================================================
--- zodbcode/trunk/README.txt (rev 0)
+++ zodbcode/trunk/README.txt 2007-10-10 16:23:55 UTC (rev 80804)
@@ -0,0 +1,3 @@
+The package seeks to allow Python code to be stored in the ZODB. The main
+benefits are that this code can then be easily transferred to other servers
+and be changed at run time.
Property changes on: zodbcode/trunk/README.txt
___________________________________________________________________
Name: svn:eol-style
+ native
Modified: zodbcode/trunk/setup.py
===================================================================
--- zodbcode/trunk/setup.py 2007-10-10 15:14:49 UTC (rev 80803)
+++ zodbcode/trunk/setup.py 2007-10-10 16:23:55 UTC (rev 80804)
@@ -1,6 +1,6 @@
##############################################################################
#
-# Copyright (c) 2004 Zope Corporation and Contributors.
+# Copyright (c) 2007 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
@@ -15,21 +15,47 @@
$Id$
"""
-
+import os
from setuptools import setup, find_packages, Extension
-setup(name='zodbcode',
- version='3.4.0b1',
- url='http://svn.zope.org/zodbcode',
- author='Zope Corporation and Contributors',
- author_email='zope3-dev at zope.org',
+def read(*rnames):
+ return open(os.path.join(os.path.dirname(__file__), *rnames)).read()
- packages=find_packages('src'),
- package_dir = {'': 'src'},
- include_package_data = True,
- install_requires = ['ZODB3',
- 'zope.interface'],
- zip_safe = False,
- )
-
+setup (
+ name='zodbcode',
+ version='3.4.0b2',
+ author='Zope Corporation and Contributors',
+ author_email='zope3-dev at zope.org',
+ description = "Allows Python code to live in the ZODB",
+ long_description=(
+ read('README.txt')
+ + '\n\n' +
+ 'Detailed Documentation\n' +
+ '**********************\n\n' +
+ read('src', 'zodbcode', 'module.txt') +
+ + '\n\n' +
+ read('CHANGES.txt')
+ ),
+ license = "ZPL 2.1",
+ keywords = "zodb persistent code",
+ classifiers = [
+ 'Development Status :: 5 - Production/Stable',
+ 'Environment :: Web Environment',
+ 'Intended Audience :: Developers',
+ 'License :: OSI Approved :: Zope Public License',
+ 'Programming Language :: Python',
+ 'Natural Language :: English',
+ 'Operating System :: OS Independent',
+ 'Topic :: Internet :: WWW/HTTP',
+ 'Framework :: Zope3'],
+ url = 'http://cheeseshop.python.org/pypi/zodbcode',
+ packages = find_packages('src'),
+ include_package_data = True,
+ package_dir = {'':'src'},
+ namespace_packages = ['z3c'],
+ install_requires = [
+ 'ZODB3',
+ 'zope.interface'],
+ zip_safe = False,
+ )
Property changes on: zodbcode/trunk/src
___________________________________________________________________
Name: svn:ignore
+ zodbcode.egg-info
Modified: zodbcode/trunk/src/zodbcode/module.txt
===================================================================
--- zodbcode/trunk/src/zodbcode/module.txt 2007-10-10 15:14:49 UTC (rev 80803)
+++ zodbcode/trunk/src/zodbcode/module.txt 2007-10-10 16:23:55 UTC (rev 80804)
@@ -1,316 +1,300 @@
+==================
Persistent Modules
+==================
- Document Overview
+Document Overview
+-----------------
- This document seeks to capture technical information about
- persistent modules to guide and document their design.
+This document seeks to capture technical information about persistent modules
+to guide and document their design.
- Goals
+Goals
+-----
- These goals largely come from Zope 3. It would be worth while
- considering other applications.
+These goals largely come from Zope 3. It would be worth while considering
+other applications.
- - Persistent modules are used to support management of software
- using the ZODB.
+- Persistent modules are used to support management of software using the
+ ZODB.
- - Software can be updated using network
- clients, such as web browsers and file-synchonozation tools.
+- Software can be updated using network clients, such as web browsers and
+ file-synchonozation tools.
- - Application-server clusters can be updated
- transactionally without requiring server restarts.
+- Application-server clusters can be updated transactionally without requiring
+ server restarts.
- - Persistent modules leverage a familiar model, modules, for
- managing Python software.
+- Persistent modules leverage a familiar model, modules, for managing Python
+ software.
- - Persistent modules can be synchronized to a file-system using
- the Zope file-system synchronization framework. Persistent
- modules are synchronized for purposes including:
+- Persistent modules can be synchronized to a file-system using the Zope
+ file-system synchronization framework. Persistent modules are synchronized
+ for purposes including:
- o Use of traditional tools such as editors and code-analysis
- tools
+ o Use of traditional tools such as editors and code-analysis tools
- o Revision control
+ o Revision control
- Ideally, the file-system representation would consist of a
- Python source file.
+ Ideally, the file-system representation would consist of a Python source
+ file.
- Use cases
+Use cases
+---------
- - Create classes and functions that implement Zope 3 components.
-
- o Utility, Adapter, View, and service classes and factories.
+- Create classes and functions that implement Zope 3 components.
- o Content components, which are typically persistent and/or
- pickleable.
+ o Utility, Adapter, View, and service classes and factories.
- - Define interfaces, including schema
+ o Content components, which are typically persistent and/or
+ pickleable.
- - Import classes, functions, and interfaces from other modules.
+- Define interfaces, including schema
- - Import classes, functions, and interfaces from other persistent
- objects. For example, an adapter registration object might have
- a direct reference to a persistent-module-defined class.
+- Import classes, functions, and interfaces from other modules.
- - Change module source
+- Import classes, functions, and interfaces from other persistent objects. For
+ example, an adapter registration object might have a direct reference to a
+ persistent-module-defined class.
- - Changes are reflected in module state
+- Change module source
- - Changes are reflected in objects imported into other modules.
+ - Changes are reflected in module state
- - Synchronize modules with a file-system representation.
+ - Changes are reflected in objects imported into other modules.
- Edge cases
+- Synchronize modules with a file-system representation.
- ???
+Edge cases
+----------
- Fundamental dilema
+ ???
- Python modules were not designed to change at run time. The
- source of a Python module normally doesn't change while a Python
- program is running. There is a crude reload tool that allows
- modules to be manually reloaded to handle source changes.
+Fundamental dilema
+------------------
- Python modules contain mutable state. A module has a dictionary
- that may be mutated by application code. It may contain mutable
- data that is modified at run time. This is typeically used to
- implement global registries.
+Python modules were not designed to change at run time. The source of a
+Python module normally doesn't change while a Python program is running.
+There is a crude reload tool that allows modules to be manually reloaded to
+handle source changes.
- When a module is reloaded, it is reexecuted with a dictionary that
- includes the results of the previous execution.
+Python modules contain mutable state. A module has a dictionary that may be
+mutated by application code. It may contain mutable data that is modified at
+run time. This is typeically used to implement global registries.
- Programs using the ZODB may be said to have logical lifetimes that
- exceed the lifetimes of individual processes. In addition, the
- program might exist as multiple individual processes with
- overlapping run-times.
+When a module is reloaded, it is reexecuted with a dictionary that includes
+the results of the previous execution.
- The lifetime of a persistent program is long enough that it is
- likely that module source code will change during the life time
- of the program.
+Programs using the ZODB may be said to have logical lifetimes that exceed the
+lifetimes of individual processes. In addition, the program might exist as
+multiple individual processes with overlapping run-times.
- Issues
+The lifetime of a persistent program is long enough that it is likely that
+module source code will change during the life time of the program.
- - Should the state of a module be represented soley by the module
- source?
+Issues
+------
- Consider the possibilities:
+Should the state of a module be represented soley by the module source?
- A. Module state is represented soley by it's source.
+Consider the possibilities:
- - This would be a departure from the behavior of standard
- Python modules. Standard Python modules retain a module
- dictionary that is not overwritten by reloads. Python
- modules may be mutated from outside and may contain mutable
- data structures that are modified at run time.
+A. Module state is represented soley by it's source.
- OTOH, a regular module's state is not persistent or shared
- accross processes.
+- This would be a departure from the behavior of standard Python modules.
+ Standard Python modules retain a module dictionary that is not overwritten
+ by reloads. Python modules may be mutated from outside and may contain
+ mutable data structures that are modified at run time.
- For standard Python modules, one could view the module
- source as an expression of the initial state of the
- module. (This isn't quite right either, since some modules
- are written in such a way that they anticipate module
- reloads.)
+ OTOH, a regular module's state is not persistent or shared accross
+ processes.
- - Deleting variables from a module's source that have been
- imported by other modules or objects will cause the imported
- values to become disconnected from the module's source.
- Even if the variables are added back later, the
- previously-imported values will be disconnected.
+ For standard Python modules, one could view the module source as an
+ expression of the initial state of the module. (This isn't quite right
+ either, since some modules are written in such a way that they anticipate
+ module reloads.)
- It is tempting to introduce a data structure to record
- imports make from a module. For example, suppose module M1
- imports X from M2. It's tempting to record that fact in M2,
- so that we disallow M2 to be removed or to be changed in
- such a way that M2 no-longer defines X. Unfortunately, that
- would introduce state that isn't captured by my M2's source.
+- Deleting variables from a module's source that have been imported by other
+ modules or objects will cause the imported values to become disconnected
+ from the module's source. Even if the variables are added back later, the
+ previously-imported values will be disconnected.
- - Persistent modules could only be used for software. You
- wouldn't be able to use them to store mutable data, such as
- registries or counters, that are updated outside of the
- execution of the module source.
-
- B. Module state isn't represented soley by it's source.
+ It is tempting to introduce a data structure to record imports make from a
+ module. For example, suppose module M1 imports X from M2. It's tempting to
+ record that fact in M2, so that we disallow M2 to be removed or to be
+ changed in such a way that M2 no-longer defines X. Unfortunately, that
+ would introduce state that isn't captured by my M2's source.
- - It would become possible to allow mutable data, such as
- registries in persistent modules.
+- Persistent modules could only be used for software. You wouldn't be able to
+ use them to store mutable data, such as registries or counters, that are
+ updated outside of the execution of the module source.
- - It could be very difficult to see what a module's state is.
- If a module contained mutable data, you'd need some way to
- get to that data so you could inspect and manipulate it.
+B. Module state isn't represented soley by it's source.
- - When a module is synchronized to the file system, you'd need
- to syncronize it's source and you'd also need to synchronize it's
- contents in some way. Synchronization of the contents could
- be done using an XML pickle, but management of the data
- using file-system-based tools would be cumbersome.
+ - It would become possible to allow mutable data, such as registries in
+ persistent modules.
- You'd end up with data duplicated between the two
- representations. It would be cumbersome to manage the
- duplicated data in a consistent way.
+ - It could be very difficult to see what a module's state is. If a module
+ contained mutable data, you'd need some way to get to that data so you
+ could inspect and manipulate it.
- C. Module state is represented soley by it's source, but allow
- additional meta data.
+ - When a module is synchronized to the file system, you'd need to syncronize
+ it's source and you'd also need to synchronize it's contents in some
+ way. Synchronization of the contents could be done using an XML pickle, but
+ management of the data using file-system-based tools would be cumbersome.
- This is the same as option A, except we support meta-data
- management. The meta data could include dependency
- information. We'd keep track of external usage (import) of
- module variables to influence whether deletion of the module
- or defined variables is allowed, or whether to issue warnings
- when variables are deleted.
+ You'd end up with data duplicated between the two representations. It
+ would be cumbersome to manage the duplicated data in a consistent way.
- Note that the management of the meta data need not be the
- responsibility of the module. This could be done via some
- application-defined facility, in which case, the module
- facility would need to provide an api for implimenting hooks
- for managing this information.
+C. Module state is represented soley by it's source, but allow additional meta
+ data.
- Special cases
+ This is the same as option A, except we support meta-data management. The
+ meta data could include dependency information. We'd keep track of external
+ usage (import) of module variables to influence whether deletion of the
+ module or defined variables is allowed, or whether to issue warnings when
+ variables are deleted.
- This section contains examples that may introduce challenges for
- persistent modules or that might motivate or highlight issues
- described above,
+ Note that the management of the meta data need not be the responsibility of
+ the module. This could be done via some application-defined facility, in
+ which case, the module facility would need to provide an api for
+ implimenting hooks for managing this information.
- - Persistent classes
+Special cases
+-------------
- Persistent classes include data that are not represented by the
- class sources. A class caches slot definitions inherited from
- base classes. This is information that is only indirectly
- represented by it's source. Similarly, a class manages a
- collection of it's subclasses. This allows a class to
- invalidate cached slots in subclasses when a new slot definition
- is assigned (via a setattr). The cached slots and collection of
- subclasses is not part of a persistent class' state. It isn't
- saved in the database, but is recomputed when the class is
- loaded into memory or when it's subclasses are loaded into memory.
+This section contains examples that may introduce challenges for persistent
+modules or that might motivate or highlight issues described above,
- Consider two persistent modules, M1, which defines class C1,
- and M2, which defines class C2. C2 subclasses C1. C1 defines a
- __getitem__ slot, which is inherited and cached by C2.
+- Persistent classes
- Suppose we have a process, P1, which has M1 and M2 in memory.
- C2 in P1 has a (cached) __getitem__ slot filled with the
- definition inherited from C1 in P1. C1 in P1 has C2 in it's
- collection of subclasses. In P1, we modify M1, by editing and
- recompiling its source. When we recompile M1's source, we'll
- update the state of C1 by calling it's __setstate__ method,
- passing the new class dictionary. The __setstate__ method will,
- in turn, use setattr to assign the values from the new
- dictionary. If we set a slot attribute, the __setattribute__
- method in C1 will notify each of it's subclasses that the slot
- has changed. Now, suppose that we've added a __len__ slot
- definition when we modified the source. When we set the __len__
- attribute in C1, C2 will be notified that there is a new slot
- definition for __len__.
+ Persistent classes include data that are not represented by the class
+ sources. A class caches slot definitions inherited from base classes. This
+ is information that is only indirectly represented by it's source.
+ Similarly, a class manages a collection of it's subclasses. This allows a
+ class to invalidate cached slots in subclasses when a new slot definition is
+ assigned (via a setattr). The cached slots and collection of subclasses is
+ not part of a persistent class' state. It isn't saved in the database, but
+ is recomputed when the class is loaded into memory or when it's subclasses
+ are loaded into memory.
- Suppose we have a process P2, which also has M1 and M2 loaded
- into memory. As in P1, C2 in P2 caches the __getitem__ slot and
- C1 in P2 has C2 in P2 in it's collection of subclasses. Now,
- when M1 in P1 is modified and the corresponding transaction is
- committed, an invalidation for M1 and all of the persistent
- objects it defines, including C1, is sent to all other
- processes. When P2 gets the invalidation for C1, it invalidates
- C1. It happens that persistent classes are not allowed to be
- ghosts. When a persistent class is invalidated, it immediately
- reloads it's state, rather than converting itself into a
- ghost. When C2's state is reloaded in P2, we assign it's
- attributes from the new class dictionary. When we assign slots,
- we notify it's subclasses, including C2 in P2.
+ Consider two persistent modules, M1, which defines class C1, and M2, which
+ defines class C2. C2 subclasses C1. C1 defines a __getitem__ slot, which
+ is inherited and cached by C2.
- Suppose we have a process P3, that only has M1 in memory. In
- P3, M2 is not in memory, nor are any of it's subobjects. In P3,
- C2 is not in the collection of subclasses of C1, because C2 is
- not in memory and the collection of subclasses is volatile data
- for C1. When we modify C1 in P1 and commit the transaction, the
- state of C1 in P3 will be updated, but the state of C2 is not
- affected in P3, because it's not in memory.
+ Suppose we have a process, P1, which has M1 and M2 in memory. C2 in P1 has
+ a (cached) __getitem__ slot filled with the definition inherited from C1 in
+ P1. C1 in P1 has C2 in it's collection of subclasses. In P1, we modify M1,
+ by editing and recompiling its source. When we recompile M1's source, we'll
+ update the state of C1 by calling it's __setstate__ method, passing the new
+ class dictionary. The __setstate__ method will, in turn, use setattr to
+ assign the values from the new dictionary. If we set a slot attribute, the
+ __setattribute__ method in C1 will notify each of it's subclasses that the
+ slot has changed. Now, suppose that we've added a __len__ slot definition
+ when we modified the source. When we set the __len__ attribute in C1, C2
+ will be notified that there is a new slot definition for __len__.
- Finally, consider a process, P4 that has M2, but not M1 in
- memory. M2 is not a ghost, so C2 is in memory. Now, since C2 is
- in memory, C1 must be in memory, even though M1 is not in
- memory, because C2 has a reference to C1. Further, C1 cannot
- be a ghost, because persistent classes are not allowed to be
- ghosts. When we commit the transation in P1 that updates M1, an
- invalidation for C1 is sent to P4 and C1 is updated. When C1 is
- updated, it's subclasses (in P4), including C2 are notified, so
- that their cached slot definitions are updated.
+ Suppose we have a process P2, which also has M1 and M2 loaded into memory.
+ As in P1, C2 in P2 caches the __getitem__ slot and C1 in P2 has C2 in P2 in
+ it's collection of subclasses. Now, when M1 in P1 is modified and the
+ corresponding transaction is committed, an invalidation for M1 and all of
+ the persistent objects it defines, including C1, is sent to all other
+ processes. When P2 gets the invalidation for C1, it invalidates C1. It
+ happens that persistent classes are not allowed to be ghosts. When a
+ persistent class is invalidated, it immediately reloads it's state, rather
+ than converting itself into a ghost. When C2's state is reloaded in P2, we
+ assign it's attributes from the new class dictionary. When we assign slots,
+ we notify it's subclasses, including C2 in P2.
- When we modify M1, all copies in memory of C1 and C2 are updated
- properly, even though the data they cache is not cached
- persistently. This works, and only works, because persistent
- classes are never ghosts. If a class could be a ghost, then
- invalidating it would have not effect and non-ghost dependent
- classes would not be updated.
+ Suppose we have a process P3, that only has M1 in memory. In P3, M2 is not
+ in memory, nor are any of it's subobjects. In P3, C2 is not in the
+ collection of subclasses of C1, because C2 is not in memory and the
+ collection of subclasses is volatile data for C1. When we modify C1 in P1
+ and commit the transaction, the state of C1 in P3 will be updated, but the
+ state of C2 is not affected in P3, because it's not in memory.
- - Persistent interfaces
+ Finally, consider a process, P4 that has M2, but not M1 in memory. M2 is
+ not a ghost, so C2 is in memory. Now, since C2 is in memory, C1 must be in
+ memory, even though M1 is not in memory, because C2 has a reference to C1.
+ Further, C1 cannot be a ghost, because persistent classes are not allowed to
+ be ghosts. When we commit the transation in P1 that updates M1, an
+ invalidation for C1 is sent to P4 and C1 is updated. When C1 is updated,
+ it's subclasses (in P4), including C2 are notified, so that their cached
+ slot definitions are updated.
- Like classes, Zope interfaces cache certain information. An
- interface maintains a set of all of the interfaces that it
- extends. In addition, interfaces maintain a collection of all
- of their sub-interfaces. The collection of subinterfaces is
- used to notify sub=interfaces when an interface changes.
+ When we modify M1, all copies in memory of C1 and C2 are updated properly,
+ even though the data they cache is not cached persistently. This works, and
+ only works, because persistent classes are never ghosts. If a class could
+ be a ghost, then invalidating it would have not effect and non-ghost
+ dependent classes would not be updated.
- (Interfaces are a special case of a more general class of
- objects, called "specifications", that include both interfaces
- and interface declareations. Similar caching is performed for
- other specifications and related data structures. To simplify
- the discussion, however, we'll limit ourselves to interfaces.)
+- Persistent interfaces
- When designing persistent interfaces, we have alternative
- approaches to consider:
+ Like classes, Zope interfaces cache certain information. An interface
+ maintains a set of all of the interfaces that it extends. In addition,
+ interfaces maintain a collection of all of their sub-interfaces. The
+ collection of subinterfaces is used to notify sub=interfaces when an
+ interface changes.
- A. We could take the same approach as that taken with persistent
- classes. We would not save cached data persistently. We
- would compute it as objects are moved into memory.
+ (Interfaces are a special case of a more general class of objects, called
+ "specifications", that include both interfaces and interface declareations.
+ Similar caching is performed for other specifications and related data
+ structures. To simplify the discussion, however, we'll limit ourselves to
+ interfaces.)
- To take this approach, we'd need to also make persistent
- interfaces non-ghostifiable. This is necessary to properly
- propigate object changes.
+ When designing persistent interfaces, we have alternative approaches to
+ consider:
- One could argue that non-ghostifiability if classes is a
- necessary wart forced on us by details of Python classes that
- are beyond our control, and that we should avoid creating new
- kinds of objects that require non-ghostifiability.
+ A. We could take the same approach as that taken with persistent classes.
+ We would not save cached data persistently. We would compute it as
+ objects are moved into memory.
- B. We could store the cached data persistently. For example, we
- could store the set of extended interfaces and the set of
- subinterfaces in persistent dictionaries.
+ To take this approach, we'd need to also make persistent interfaces
+ non-ghostifiable. This is necessary to properly propigate object
+ changes.
- A significant disadvantage of this approach is that
- persistent interfaces would accumulate state is that not
- refelcted in their source code, however, it's worth noting
- that, while the dependency and cache data cannot be derived
- from a single module source, it *can* be derived from the
- sources of all of the modules in the system. We can
- implement persistent interface in such a way that execution
- of module code causes all dependcies among module-defined
- interfaces to be recomputed correctly.
+ One could argue that non-ghostifiability if classes is a necessary wart
+ forced on us by details of Python classes that are beyond our control,
+ and that we should avoid creating new kinds of objects that require
+ non-ghostifiability.
- (This is, to me, Jim, an interesting case: state that can be
- computed during deserialization from other serialized
- state. This should not be surprising, as we are essentially
- talking about cached data used for optimization purposes.)
+ B. We could store the cached data persistently. For example, we could store
+ the set of extended interfaces and the set of subinterfaces in persistent
+ dictionaries.
- Proposals
+ A significant disadvantage of this approach is that persistent interfaces
+ would accumulate state is that not refelcted in their source code,
+ however, it's worth noting that, while the dependency and cache data
+ cannot be derived from a single module source, it *can* be derived from
+ the sources of all of the modules in the system. We can implement
+ persistent interface in such a way that execution of module code causes
+ all dependcies among module-defined interfaces to be recomputed
+ correctly.
- - A module's state must be reprersented, directly or indirectly,
- by it's source. The state may also include information, such as
- caching data, that is derivable from it's source-represented
- state.
+ (This is, to me, Jim, an interesting case: state that can be computed
+ during deserialization from other serialized state. This should not be
+ surprising, as we are essentially talking about cached data used for
+ optimization purposes.)
- It is unclear if or how we will enforce this. Perhaps it will
- be just a guideline. The module-synchronization adapters used
- in Zope will only synchronize the module source. If a module
- defines state that is not represented by or derivable from it's
- source, then that data will be lost in synchronization. Of
- course, applications that don't use the synchronization
- framework would be unaffected by this limitation. Alternatively,
- one could develop custom module-synchronization adapters that
- handled extra module data, however, development of such adapters
- will be outside the scope of the Zope project.
+Proposals
+---------
- Notes
+- A module's state must be reprersented, directly or indirectly, by it's
+ source. The state may also include information, such as caching data, that
+ is derivable from it's source-represented state.
- - When we invalidate a persistent class, we need to delete all of
- the attributes defined by it's old dictionary that are not
- defined by the new class dictionary.
-
+ It is unclear if or how we will enforce this. Perhaps it will be just a
+ guideline. The module-synchronization adapters used in Zope will only
+ synchronize the module source. If a module defines state that is not
+ represented by or derivable from it's source, then that data will be lost in
+ synchronization. Of course, applications that don't use the synchronization
+ framework would be unaffected by this limitation. Alternatively, one could
+ develop custom module-synchronization adapters that handled extra module
+ data, however, development of such adapters will be outside the scope of the
+ Zope project.
+
+Notes
+-----
+
+- When we invalidate a persistent class, we need to delete all of the
+ attributes defined by it's old dictionary that are not defined by the new
+ class dictionary.
+
More information about the Checkins
mailing list