[Zope3-checkins] CVS: Zope3/src/zope/app/presentation -
pagefolder.py:1.1 pagefolder.zcml:1.1 zpt.py:1.1 zpt.zcml:1.1
configure.zcml:1.3 presentation.py:1.3 tests.py:NONE
Stephan Richter
srichter at cosmos.phy.tufts.edu
Thu Mar 11 05:19:07 EST 2004
Update of /cvs-repository/Zope3/src/zope/app/presentation
In directory cvs.zope.org:/tmp/cvs-serv8352/src/zope/app/presentation
Modified Files:
configure.zcml presentation.py
Added Files:
pagefolder.py pagefolder.zcml zpt.py zpt.zcml
Removed Files:
tests.py
Log Message:
Moved Page Folder and it Page Templates into zope.app.presentation.
=== Added File Zope3/src/zope/app/presentation/pagefolder.py ===
##############################################################################
#
# Copyright (c) 2002 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.0 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE.
#
##############################################################################
"""Page Folders
Page folders support easy creation and registration of page views
using folders of templates.
$Id: pagefolder.py,v 1.1 2004/03/11 10:18:36 srichter Exp $
"""
from zope.interface import Interface, implements
from zope.schema import BytesLine, Bool, Field
from zope.app.component.interfacefield import InterfaceField
from zope.app.security.permission import PermissionField
from zope.app.container.btree import BTreeContainer
from zope.fssync.server.entryadapter import ObjectEntryAdapter, AttrMapping
from zope.app.interfaces.services.registration import ActiveStatus
from zope.app.interfaces.services.registration import IRegistrationManager
from zope.app.interfaces.services.registration \
import IRegistrationManagerContainer
from zope.app.interfaces.services.registration import RegisteredStatus
from zope.app.interfaces.services.registration import UnregisteredStatus
from zope.app.interfaces.services.registration import IRegisterable
from zope.app.container.constraints import ItemTypePrecondition
from zope.app.presentation import PageRegistration
from zope.app.services.registration import RegistrationManagerContainer
from zope.app.container.constraints import ContainerTypesConstraint
from zpt import IZPTTemplate
from zope.app.traversing import getPath
from zope.proxy import removeAllProxies
from zope.publisher.interfaces.browser import IBrowserRequest
from zope.app.container.interfaces import IContainer
from zope.app.interfaces.file import IDirectoryFactory
from zope.fssync.server.interfaces import IObjectDirectory
from zope.app.interfaces.services.registration import \
IRegistrationManagerContainer
class IPageFolderInfo(Interface):
"""Default registration information for page folders
This information is used to configure the pages in the folder.
"""
required = InterfaceField(
title = u"For interface",
description = u"The interface of the objects being viewed",
required = True,
)
factoryName = BytesLine(
title=u"The dotted name of a factory for creating the view",
required = False,
)
layer = BytesLine(
title = u"Layer",
description = u"The skin layer the view is registered for",
required = False,
min_length = 1,
default = "default",
)
permission = PermissionField(
title=u"Permission",
description=u"The permission required to use the view",
required = True,
)
apply = Bool(
title=u"Apply changes to existing pages",
required = True,
)
class IPageFolder(IPageFolderInfo, IContainer, IRegistrationManagerContainer):
def applyDefaults(self):
"""Apply the default configuration to the already-registered pages.
"""
def __setitem__(name, template):
"""Add a template to the folder
"""
__setitem__.precondition = ItemTypePrecondition(IZPTTemplate)
__parent__ = Field(
constraint = ContainerTypesConstraint(IRegistrationManagerContainer))
class PageFolder(RegistrationManagerContainer, BTreeContainer):
implements(IPageFolder)
requestType = IBrowserRequest
layer = "default"
description = ''
title = ''
factoryName = None
attribute = None
template = None
apply = True
########################################################
# The logic for managing registrations is handled by the
# decorator class below.
########################################################
def __setitem__(self, name, object):
if (IRegistrationManager.providedBy(object) or
IZPTTemplate.providedBy(object)):
super(PageFolder, self).__setitem__(name, object)
else:
raise TypeError("Can only add templates", object)
# If a template is added, we need to configure it too.
if IZPTTemplate.providedBy(object):
template = self[name]
template = getPath(template)
registration = PageRegistration(
required=self.required,
name=name,
permission=self.permission,
factoryName=self.factoryName,
template=template,
layer=self.layer,
)
registrations = self.getRegistrationManager()
id = registrations.addRegistration(registration)
registration = registrations[id]
registration.status = ActiveStatus
def applyDefaults(self):
"""Apply the default configuration to the already-registered pages.
"""
rm = self.getRegistrationManager()
for name in rm:
registration = rm[name]
status = registration.status
if status == ActiveStatus:
registration.status = RegisteredStatus
registration.status = UnregisteredStatus
# Cheat and set required and layer even though they're
# read-only. This is ok since the registration is now not
# registered.
registration.required = removeAllProxies(self.required)
registration.factoryName = self.factoryName
registration.layer = self.layer
registration.permission = self.permission
# Now restore the registration status
registration.status = status
_attrNames = (
'factoryName',
'required',
'layer',
'permission',
)
class PageFolderAdapter(ObjectEntryAdapter):
"""ObjectFile adapter for PageFolder objects."""
implements(IObjectDirectory)
def contents(self):
return self.context.items()
def extra(self):
return AttrMapping(self.context, _attrNames)
class PageFolderFactory:
implements(IDirectoryFactory)
def __init__(self, context):
self.context = context
def __call__(self, name):
return PageFolder()
# XXX Backward compatibility. This is needed to support old pickles.
ViewPackage = PageFolder
import sys
sys.modules['zope.app.services.viewpackage'
] = sys.modules['zope.app.presentation.pagefolder']
=== Added File Zope3/src/zope/app/presentation/pagefolder.zcml ===
<configure
xmlns="http://namespaces.zope.org/zope"
xmlns:event="http://namespaces.zope.org/event"
xmlns:fssync="http://namespaces.zope.org/fssync"
>
<!-- Page Folder -->
<content class=".pagefolder.PageFolder">
<factory
id = "zope.app.presentation.pagefolder.PageFolder"
title = "View Folder"
/>
<require
permission="zope.View"
interface="zope.app.container.interfaces.IReadContainer" />
<require
permission="zope.ManageServices"
interface="zope.app.container.interfaces.IWriteContainer
.pagefolder.IPageFolderInfo"
set_schema=".pagefolder.IPageFolderInfo"
attributes="getRegistrationManager applyDefaults"
/>
<implements
interface="zope.app.interfaces.annotation.IAttributeAnnotatable" />
</content>
<adapter
for=".pagefolder.IPageFolder"
provides="zope.app.interfaces.file.IFileFactory"
factory=".zpt.ZPTFactory"
permission="zope.ManageServices"
/>
<adapter
for="zope.app.interfaces.services.folder.ISiteManagementFolder"
provides="zope.app.interfaces.file.IDirectoryFactory"
factory=".pagefolder.PageFolderFactory"
permission="zope.ManageContent"
/>
<fssync:adapter
class=".pagefolder.PageFolder"
factory=".pagefolder.PageFolderAdapter"
/>
</configure>
=== Added File Zope3/src/zope/app/presentation/zpt.py ===
##############################################################################
#
# Copyright (c) 2002 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.0 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE.
#
##############################################################################
"""
$Id: zpt.py,v 1.1 2004/03/11 10:18:36 srichter Exp $
"""
import re
from zope.security.proxy import ProxyFactory
from persistent import Persistent
from zope.interface import Interface, implements
from zope.schema import Text, BytesLine, Bool
from zope.app.container.contained import Contained
from zope.app.interfaces.services.registration import IRegisterable
from zope.app.index.interfaces.text import ISearchableText
from zope.fssync.server.entryadapter import ObjectEntryAdapter, AttrMapping
from zope.fssync.server.interfaces import IObjectFile
from zope.app.interfaces.file import IReadFile, IWriteFile, IFileFactory
from zope.app.pagetemplate.engine import AppPT
from zope.pagetemplate.pagetemplate import PageTemplate
class IZPTInfo(Interface):
"""ZPT Template configuration information
"""
contentType = BytesLine(
title=u'Content type of generated output',
required=True,
default='text/html'
)
source = Text(
title=u"Source",
description=u"""The source of the page template.""",
required=True)
expand = Bool(
title=u"Expand macros",
)
class IZPTTemplate(IZPTInfo, IRegisterable):
"""ZPT Templates for use in views"""
def render(context, request, *args, **kw):
"""Render the page template.
The context argument is bound to the top-level 'context'
variable. The request argument is bound to the top-level
'request' variable. The positional arguments are bound to the
'args' variable and the keyword arguments are bound to the
'options' variable.
"""
class ZPTTemplate(AppPT, PageTemplate, Persistent, Contained):
implements(IZPTTemplate)
contentType = 'text/html'
expand = False
usage = u''
source = property(
# get
lambda self: self.read(),
# set
lambda self, text: self.pt_edit(text.encode('utf-8'), self.contentType)
)
def pt_getContext(self, view, **_kw):
# instance is a View component
namespace = super(ZPTTemplate, self).pt_getContext(**_kw)
namespace['view'] = view
namespace['request'] = view.request
namespace['context'] = view.context
return namespace
def render(self, view, *args, **keywords):
if args:
args = ProxyFactory(args)
if self.usage:
if "template_usage" not in keywords:
kw = {'template_usage': self.usage}
kw.update(keywords)
keywords = kw
kw = ProxyFactory(keywords)
namespace = self.pt_getContext(view, args=args, options=kw)
return self.pt_render(namespace)
# Adapter for ISearchableText
tag = re.compile(r"<[^>]+>")
class SearchableText:
implements(ISearchableText)
__used_for__ = IZPTTemplate
def __init__(self, page):
self.page = page
def getSearchableText(self):
text = self.page.source
if isinstance(text, str):
text = unicode(self.page.source, 'utf-8')
# else:
# text was already Unicode, which happens, but unclear how it
# gets converted to Unicode since the ZPTPage stores UTF-8 as
# an 8-bit string.
if self.page.contentType.startswith('text/html'):
text = tag.sub('', text)
return [text]
# Adapters for file-system emulation
class ReadFile:
implements(IReadFile)
def __init__(self, context):
self.context = context
def read(self):
return self.context.source
def size(self):
return len(self.context.source)
class WriteFile:
implements(IWriteFile)
def __init__(self, context):
self.context = context
def write(self, data):
self.context.source = data
class ZPTFactory:
implements(IFileFactory)
def __init__(self, context):
self.context = context
def __call__(self, name, content_type, data):
r = ZPTTemplate()
r.source = data
return r
class ZPTPageAdapter(ObjectEntryAdapter):
"""ObjectFile adapter for ZPTTemplate objects."""
implements(IObjectFile)
def getBody(self):
return self.context.source
def setBody(self, data):
# Convert the data to Unicode, since that's what ZPTTemplate
# wants; it's normally read from a file so it'll be bytes.
# XXX This will die if it's not ASCII. Guess encoding???
self.context.source = unicode(data)
def extra(self):
return AttrMapping(self.context, ('contentType', 'expand'))
=== Added File Zope3/src/zope/app/presentation/zpt.zcml ===
<configure
xmlns="http://namespaces.zope.org/zope"
xmlns:event="http://namespaces.zope.org/event"
xmlns:fssync="http://namespaces.zope.org/fssync"
>
<!-- Page Templates -->
<content class=".zpt.ZPTTemplate">
<factory
title="ZPT Template"
description="Page Template"
/>
<require
permission="zope.View"
attributes="__call__"
/>
<require
permission="zope.ManageServices"
interface=".zpt.IZPTTemplate"
set_schema=".zpt.IZPTTemplate"
/>
<implements
interface="zope.app.interfaces.annotation.IAttributeAnnotatable"
/>
</content>
<adapter
for=".zpt.IZPTTemplate"
provides="zope.app.interfaces.file.IReadFile"
factory=".zpt.ReadFile"
permission="zope.ManageServices"
/>
<adapter
for=".zpt.IZPTTemplate"
provides="zope.app.interfaces.file.IWriteFile"
factory=".zpt.WriteFile"
permission="zope.ManageServices"
/>
<!-- Filesystem synchronization support -->
<fssync:adapter
class=".zpt.ZPTTemplate"
factory=".zpt.ZPTPageAdapter"
/>
</configure>
=== Zope3/src/zope/app/presentation/configure.zcml 1.2 => 1.3 ===
--- Zope3/src/zope/app/presentation/configure.zcml:1.2 Tue Mar 9 08:36:33 2004
+++ Zope3/src/zope/app/presentation/configure.zcml Thu Mar 11 05:18:36 2004
@@ -43,6 +43,9 @@
alias="zope.app.services.presentation"
/>
+<include file="pagefolder.zcml" />
+<include file="zpt.zcml" />
+
<include package=".browser" />
</configure>
=== Zope3/src/zope/app/presentation/presentation.py 1.2 => 1.3 ===
--- Zope3/src/zope/app/presentation/presentation.py:1.2 Tue Mar 9 11:34:31 2004
+++ Zope3/src/zope/app/presentation/presentation.py Thu Mar 11 05:18:36 2004
@@ -15,12 +15,12 @@
$Id$
"""
-
+import persistent.dict
from zope.app import zapi
from zope.app.i18n import ZopeMessageIDFactory as _
from zope.component.presentation import IDefaultViewName
from zope.security.checker import NamesChecker, ProxyFactory
-import persistent.dict
+
import zope.app.component.interfacefield
import zope.app.component.nextservice
import zope.app.container.contained
@@ -30,7 +30,6 @@
import zope.app.services.field
import zope.app.interfaces.services.interface
import zope.app.adapter
-import zope.app.services.zpt
import zope.component.interfaces
import zope.configuration.exceptions
import zope.interface
=== Removed File Zope3/src/zope/app/presentation/tests.py ===
More information about the Zope3-Checkins
mailing list