My understanding (and the way we use it when monkey patching for instance) is that whenevery you apply new security to a class, you create a new ClassSecurityInfo on it. It only defines "new stuff" to do. The real synthesized security is still stored in __ac_permissions__.

Yes, your understanding matches what I know now. Part of my earlier diagnosis was wrong, the behavior of class_init has not changed between Zope 2.7 and Zope 2.8, just the behavior of Archetypes.

What Archetypes seems to do is to generate a new ClassSecurityInfo during the call to registerType, which does not contain "added" information, but information about every single method on the class. It does try to look at the already existing __ac_permissions__ to make sure already set permissions don't get stomped, but when a name is declared private or public it will not be part of __ac_permissions__ and Archetypes will gladly stomp all over it.

I have applied a patch locally (and submitted it on the Archetypes bug tracker on that seems to solve the problem. I honestly don't know if there are other dangerous consequences because the way Archetypes works is just really dark magic which I don't want to get into too far. Basically, at the point where it tries to find already- set permissions, I am also trying to find a name "<method>__roles__" to determine if something has already been declared private or public, and then re-declare it private or public on the ClassSecurityInfo object that Archetypes creates:

Index: Archetypes/
--- Archetypes/  (revision 6167)
+++ Archetypes/  (working copy)
@@ -103,6 +103,8 @@

         perm = _modes[mode]['security']
         perm = getattr(field, perm, None)
+        method__roles__ = getattr(klass, '%s__roles__' % methodName, 0)
         # Check copied from SecurityInfo to avoid stomping over
         # existing permissions.
         if security.names.get(methodName, perm) != perm:
@@ -112,6 +114,10 @@
                  'permission declared is the correct one and '
                  'has preference over the permission declared '
                  'on the field.' % methodName)
+        elif method__roles__ is None:
+            security.declarePublic(methodName)
+        elif method__roles__ == ():
+            security.declarePrivate(methodName)
             security.declareProtected(perm, methodName)


Zope-Dev maillist  -
**  No cross posts or HTML encoding!  **
(Related lists - )

Reply via email to