AccessControl Security Framework for Zope

7.3 · active · verified Thu Apr 16

AccessControl is the foundational security framework for the Zope application server, providing core components for authentication, authorization, and permission management within Zope Object Database (ZODB) applications. It defines security policies, user management interfaces, and permission checking mechanisms. The current version is 7.3, and it follows the release cadence of the wider Zope ecosystem, with stable updates aligning with Zope 5+ development.

Common errors

Warnings

Install

Imports

Quickstart

This quickstart demonstrates how to set a security manager and check permissions using AccessControl. As AccessControl is deeply integrated with Zope, this example uses mock objects to simulate a Zope environment and show the core API (`setSecurityManager`, `getSecurityManager`, `checkPermission`). In a live Zope application, the Zope server handles the lifecycle and instantiation of these security components.

import os
from AccessControl.SecurityManagement import setSecurityManager, getSecurityManager
from AccessControl.User import UnrestrictedUser
from AccessControl.Permissions import view as ViewPermission

# 1. Define a mock Security Manager and User for demonstration
# In a real Zope app, these would be provided by the Zope environment.
class MockUser(UnrestrictedUser):
    def __init__(self, id, password, roles, domains, permissions=None):
        super().__init__(id, password, roles, domains)
        self._permissions = permissions if permissions is not None else {}

    def getRoles(self):
        return self._roles

    def has_permission(self, permission_name, context):
        # Simplified check: Manager role allows everything, otherwise check specific permissions.
        if 'Manager' in self.getRoles():
            return True
        return permission_name in self._permissions.get(context.__class__.__name__, [])

class MockSecurityManager:
    def __init__(self, user):
        self._user = user

    def getUser(self):
        return self._user

    def checkPermission(self, permission_name, context_object):
        # In a real Zope app, this involves complex role/permission mappings.
        return self._user.has_permission(permission_name, context_object)

    def validate(self, granted_roles, context_object, permission_name):
        # Simplified for demonstration. Real method involves deep Zope security context.
        return self._user.has_permission(permission_name, context_object)

# 2. Define a mock context object that can be secured
class Document:
    def __init__(self, name):
        self.name = name
    def __repr__(self):
        return f"<Document: {self.name}>"

# 3. Create mock users with different roles and permissions
admin_user = MockUser('admin', 'pwd', ['Manager'], 'all', permissions={'Document': [ViewPermission, 'Edit']})
editor_user = MockUser('editor', 'pwd', ['Editor'], 'local', permissions={'Document': ['Edit']})
viewer_user = MockUser('viewer', 'pwd', ['Viewer'], 'local', permissions={'Document': [ViewPermission]})

# 4. Create a document to test permissions against
my_document = Document("Secret Report")

print("--- Admin User Context ---")
setSecurityManager(MockSecurityManager(admin_user))
sm = getSecurityManager()
current_user = sm.getUser()
print(f"Current User: {current_user.getUserName()} (Roles: {current_user.getRoles()})")
print(f"Can '{ViewPermission}' on {my_document}? {sm.checkPermission(ViewPermission, my_document)}")
print(f"Can 'Edit' on {my_document}? {sm.checkPermission('Edit', my_document)}")

print("\n--- Viewer User Context ---")
setSecurityManager(MockSecurityManager(viewer_user))
sm = getSecurityManager()
current_user = sm.getUser()
print(f"Current User: {current_user.getUserName()} (Roles: {current_user.getRoles()})")
print(f"Can '{ViewPermission}' on {my_document}? {sm.checkPermission(ViewPermission, my_document)}")
print(f"Can 'Edit' on {my_document}? {sm.checkPermission('Edit', my_document)}")

print("\n--- Editor User Context ---")
setSecurityManager(MockSecurityManager(editor_user))
sm = getSecurityManager()
current_user = sm.getUser()
print(f"Current User: {current_user.getUserName()} (Roles: {current_user.getRoles()})")
print(f"Can '{ViewPermission}' on {my_document}? {sm.checkPermission(ViewPermission, my_document)}")
print(f"Can 'Edit' on {my_document}? {sm.checkPermission('Edit', my_document)}")

# In a real Zope app, you might restore the default security manager or a different one
# setSecurityManager(None) # Clears the thread-local manager

view raw JSON →