[Checkins] SVN: grok/trunk/ Use grokcore.view.
Philipp von Weitershausen
philikon at philikon.de
Thu Aug 7 18:01:17 EDT 2008
Log message for revision 89512:
Use grokcore.view.
Changed:
U grok/trunk/setup.py
U grok/trunk/src/grok/__init__.py
U grok/trunk/src/grok/components.py
U grok/trunk/src/grok/configure.zcml
U grok/trunk/src/grok/interfaces.py
U grok/trunk/src/grok/meta.py
U grok/trunk/src/grok/meta.zcml
D grok/trunk/src/grok/templatereg.py
U grok/trunk/src/grok/testing.py
U grok/trunk/src/grok/tests/zcml/directivepackage.py
U grok/trunk/src/grok/util.py
U grok/trunk/versions.cfg
-=-
Modified: grok/trunk/setup.py
===================================================================
--- grok/trunk/setup.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/setup.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -38,6 +38,7 @@
'martian >= 0.10',
'grokcore.component >= 1.5',
'grokcore.security',
+ 'grokcore.view',
'simplejson',
'pytz',
'ZODB3',
Modified: grok/trunk/src/grok/__init__.py
===================================================================
--- grok/trunk/src/grok/__init__.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/__init__.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -29,6 +29,14 @@
from grokcore.security import Public
from grokcore.security import require
+from grokcore.view import PageTemplate
+from grokcore.view import PageTemplateFile
+from grokcore.view import layer
+from grokcore.view import template
+from grokcore.view import templatedir
+from grokcore.view import skin
+from grokcore.view import url
+
from zope.event import notify
from zope.app.component.hooks import getSite
from zope.lifecycleevent import (
@@ -47,7 +55,7 @@
from grok.components import Model, View
from grok.components import XMLRPC, REST, JSON
-from grok.components import PageTemplate, PageTemplateFile, Traverser
+from grok.components import Traverser
from grok.components import Container, OrderedContainer
from grok.components import Site, LocalUtility, Annotation
from grok.components import Application, Form, AddForm, EditForm, DisplayForm
@@ -57,17 +65,16 @@
from grok.interfaces import IRESTSkinType
from grok.components import ViewletManager, Viewlet
-from grok.directive import (
- template, templatedir, local_utility, permissions, site,
- layer, viewletmanager, view, traversable, order, skin)
+from grok.directive import (local_utility, permissions, site,
+ viewletmanager, view, traversable, order)
+from grok.formlib import action, AutoFields, Fields
+
+
# BBB These two functions are meant for test fixtures and should be
# imported from grok.testing, not from grok.
from grok.testing import grok, grok_component
-from grok.formlib import action, AutoFields, Fields
-from grok.util import url
-
# Our __init__ provides the grok API directly so using 'import grok' is enough.
from grok.interfaces import IGrokAPI
from zope.interface import moduleProvides
Modified: grok/trunk/src/grok/components.py
===================================================================
--- grok/trunk/src/grok/components.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/components.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -13,7 +13,6 @@
##############################################################################
"""Grok components"""
-import sys
import os
import persistent
import datetime
@@ -32,15 +31,10 @@
from zope.publisher.interfaces.browser import IBrowserPublisher
from zope.publisher.interfaces.http import IHTTPRequest
from zope.publisher.publish import mapply
-from zope.pagetemplate import pagetemplate, pagetemplatefile
from zope.formlib import form
from zope.annotation.interfaces import IAttributeAnnotatable
-from zope.app.pagetemplate.engine import TrustedAppPT
from zope.app.publisher.browser import getDefaultViewName
-from zope.app.publisher.browser import directoryresource
-from zope.app.publisher.browser.pagetemplateresource import \
- PageTemplateResourceFactory
from zope.app.container.btree import BTreeContainer
from zope.app.container.contained import Contained
from zope.app.container.interfaces import IReadContainer, IObjectAddedEvent
@@ -57,6 +51,7 @@
import z3c.flashmessage.interfaces
import martian.util
+import grokcore.view
from grok import interfaces, formlib, util
@@ -138,95 +133,9 @@
pass
-class ViewBase(object):
- def __init__(self, context, request):
- self.context = context
- self.request = request
-
-class View(BrowserPage):
+class View(grokcore.view.View):
interface.implements(interfaces.IGrokView)
- def __init__(self, context, request):
- super(View, self).__init__(context, request)
- self.__name__ = self.__view_name__
- self.static = component.queryAdapter(
- self.request,
- interface.Interface,
- name=self.module_info.package_dotted_name
- )
-
- @property
- def response(self):
- return self.request.response
-
- def __call__(self):
- mapply(self.update, (), self.request)
- if self.request.response.getStatus() in (302, 303):
- # A redirect was triggered somewhere in update(). Don't
- # continue rendering the template or doing anything else.
- return
-
- template = getattr(self, 'template', None)
- if template is not None:
- return self._render_template()
- return mapply(self.render, (), self.request)
-
- def _render_template(self):
- return self.template.render(self)
-
- def default_namespace(self):
- namespace = {}
- namespace['context'] = self.context
- namespace['request'] = self.request
- namespace['static'] = self.static
- namespace['view'] = self
- return namespace
-
- def namespace(self):
- return {}
-
- def __getitem__(self, key):
- # This is BBB code for Zope page templates only:
- if not isinstance(self.template, PageTemplate):
- raise AttributeError("View has no item %s" % key)
-
- value = self.template._template.macros[key]
- # When this deprecation is done with, this whole __getitem__ can
- # be removed.
- warnings.warn("Calling macros directly on the view is deprecated. "
- "Please use context/@@viewname/macros/macroname\n"
- "View %r, macro %s" % (self, key),
- DeprecationWarning, 1)
- return value
-
-
- def url(self, obj=None, name=None, data=None):
- """Return string for the URL based on the obj and name. The data
- argument is used to form a CGI query string.
- """
- if isinstance(obj, basestring):
- if name is not None:
- raise TypeError(
- 'url() takes either obj argument, obj, string arguments, '
- 'or string argument')
- name = obj
- obj = None
-
- if name is None and obj is None:
- # create URL to view itself
- obj = self
- elif name is not None and obj is None:
- # create URL to view on context
- obj = self.context
-
- if data is None:
- data = {}
- else:
- if not isinstance(data, dict):
- raise TypeError('url() data argument must be a dict.')
-
- return util.url(self.request, obj, name, data=data)
-
def application_url(self, name=None):
obj = self.context
while obj is not None:
@@ -235,12 +144,6 @@
obj = obj.__parent__
raise ValueError("No application found.")
- def redirect(self, url):
- return self.request.response.redirect(url)
-
- def update(self):
- pass
-
def flash(self, message, type='message'):
source = component.getUtility(
z3c.flashmessage.interfaces.IMessageSource, name='session')
@@ -283,139 +186,6 @@
return simplejson.dumps(method_result)
-class BaseTemplate(object):
- """Any sort of page template"""
-
- interface.implements(interfaces.ITemplate)
-
- __grok_name__ = ''
- __grok_location__ = ''
-
- def __repr__(self):
- return '<%s template in %s>' % (self.__grok_name__,
- self.__grok_location__)
-
- def _annotateGrokInfo(self, name, location):
- self.__grok_name__ = name
- self.__grok_location__ = location
-
- def _initFactory(self, factory):
- pass
-
-
-class GrokTemplate(BaseTemplate):
- """A slightly more advanced page template
-
- This provides most of what a page template needs and is a good base for
- writing your own page template"""
-
- def __init__(self, string=None, filename=None, _prefix=None):
-
- # __grok_module__ is needed to make defined_locally() return True for
- # inline templates
- # XXX unfortunately using caller_module means that care must be taken
- # when GrokTemplate is subclassed. You can not do a super().__init__
- # for example.
- self.__grok_module__ = martian.util.caller_module()
-
- if not (string is None) ^ (filename is None):
- raise AssertionError(
- "You must pass in template or filename, but not both.")
-
- if string:
- self.setFromString(string)
- else:
- if _prefix is None:
- module = sys.modules[self.__grok_module__]
- _prefix = os.path.dirname(module.__file__)
- self.setFromFilename(filename, _prefix)
-
- def __repr__(self):
- return '<%s template in %s>' % (self.__grok_name__,
- self.__grok_location__)
-
- def _annotateGrokInfo(self, name, location):
- self.__grok_name__ = name
- self.__grok_location__ = location
-
- def _initFactory(self, factory):
- pass
-
- def namespace(self, view):
- # By default use the namespaces that are defined as the
- # default by the view implementation.
- return view.default_namespace()
-
- def getNamespace(self, view):
- namespace = self.namespace(view)
- namespace.update(view.namespace())
- return namespace
-
-class TrustedPageTemplate(TrustedAppPT, pagetemplate.PageTemplate):
- pass
-
-class TrustedFilePageTemplate(TrustedAppPT, pagetemplatefile.PageTemplateFile):
- pass
-
-class PageTemplate(GrokTemplate):
-
- def setFromString(self, string):
- zpt = TrustedPageTemplate()
- if martian.util.not_unicode_or_ascii(string):
- raise ValueError("Invalid page template. Page templates must be "
- "unicode or ASCII.")
- zpt.write(string)
- self._template = zpt
-
- def setFromFilename(self, filename, _prefix=None):
- self._template = TrustedFilePageTemplate(filename, _prefix)
-
- def _initFactory(self, factory):
- factory.macros = self._template.macros
-
- def render(self, view):
- namespace = self.getNamespace(view)
- template = self._template
- namespace.update(template.pt_getContext())
- return template.pt_render(namespace)
-
-class PageTemplateFile(PageTemplate):
- # For BBB
- def __init__(self, filename, _prefix=None):
- self.__grok_module__ = martian.util.caller_module()
- if _prefix is None:
- module = sys.modules[self.__grok_module__]
- _prefix = os.path.dirname(module.__file__)
- self.setFromFilename(filename, _prefix)
-
-class DirectoryResource(directoryresource.DirectoryResource):
- # We subclass this, because we want to override the default factories for
- # the resources so that .pt and .html do not get created as page
- # templates
-
- resource_factories = {}
- for type, factory in (directoryresource.DirectoryResource.
- resource_factories.items()):
- if factory is PageTemplateResourceFactory:
- continue
- resource_factories[type] = factory
-
-
-class DirectoryResourceFactory(object):
- # We need this to allow hooking up our own GrokDirectoryResource
- # and to set the checker to None (until we have our own checker)
-
- def __init__(self, path, name):
- # XXX we're not sure about the checker=None here
- self.__dir = directoryresource.Directory(path, None, name)
- self.__name = name
-
- def __call__(self, request):
- resource = DirectoryResource(self.__dir, request)
- resource.__name__ = self.__name
- return resource
-
-
class Traverser(object):
interface.implements(IBrowserPublisher)
@@ -491,10 +261,10 @@
return self.context.get(name)
-default_form_template = PageTemplateFile(os.path.join(
+default_form_template = grokcore.view.PageTemplateFile(os.path.join(
'templates', 'default_edit_form.pt'))
default_form_template.__grok_name__ = 'default_edit_form'
-default_display_template = PageTemplateFile(os.path.join(
+default_display_template = grokcore.view.PageTemplateFile(os.path.join(
'templates', 'default_display_form.pt'))
default_display_template.__grok_name__ = 'default_display_form'
Modified: grok/trunk/src/grok/configure.zcml
===================================================================
--- grok/trunk/src/grok/configure.zcml 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/configure.zcml 2008-08-07 22:01:16 UTC (rev 89512)
@@ -27,6 +27,8 @@
<include package="zope.app.renderer" />
<include package="zope.app.session" />
+ <include package="grokcore.view" />
+
<securityPolicy
component="zope.securitypolicy.zopepolicy.ZopeSecurityPolicy" />
@@ -78,7 +80,4 @@
<!-- need to grok this for some basic REST support -->
<grok:grok package=".rest" />
- <!-- ZPT support -->
- <grok:grok package=".templatereg" />
-
</configure>
Modified: grok/trunk/src/grok/interfaces.py
===================================================================
--- grok/trunk/src/grok/interfaces.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/interfaces.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -14,13 +14,13 @@
"""Grok interfaces
"""
from zope import interface, schema
-from zope.publisher.interfaces.browser import IBrowserPage, IBrowserView
from zope.formlib.interfaces import reConstraint
from zope.interface.interfaces import IInterface
from zope.viewlet.interfaces import IViewletManager as IViewletManagerBase
from zope.app.container.interfaces import IContainer as IContainerBase
import grokcore.component.interfaces
+import grokcore.view.interfaces
# Expose interfaces from grok.interfaces as well:
from grokcore.component.interfaces import IContext
@@ -240,76 +240,9 @@
IBrowserRequest = interface.Attribute('Browser request interface')
IDefaultBrowserLayer = interface.Attribute('Default layer for browser views.')
-class IGrokView(IBrowserPage, IBrowserView):
+class IGrokView(grokcore.view.interfaces.IGrokView):
"""Grok views all provide this interface."""
- context = interface.Attribute('context', "Object that the view presents.")
-
- request = interface.Attribute('request', "Request that the view was looked"
- "up with.")
-
- response = interface.Attribute('response', "Response object that is "
- "associated with the current request.")
-
- static = interface.Attribute('static', "Directory resource containing "
- "the static files of the view's package.")
-
- def redirect(url):
- """Redirect to given URL"""
-
- def url(obj=None, name=None, data=None):
- """Construct URL.
-
- If no arguments given, construct URL to view itself.
-
- If only obj argument is given, construct URL to obj.
-
- If only name is given as the first argument, construct URL
- to context/name.
-
- If both object and name arguments are supplied, construct
- URL to obj/name.
-
- Optionally pass a 'data' keyword argument which gets added to the URL
- as a cgi query string.
- """
-
- def default_namespace():
- """Returns a dictionary of namespaces that the template
- implementation expects to always be available.
-
- This method is *not* intended to be overridden by application
- developers.
- """
-
- def namespace():
- """Returns a dictionary that is injected in the template
- namespace in addition to the default namespace.
-
- This method *is* intended to be overridden by the application
- developer.
- """
-
- def update(**kw):
- """This method is meant to be implemented by grok.View
- subclasses. It will be called *before* the view's associated
- template is rendered and can be used to pre-compute values
- for the template.
-
- update() can take arbitrary keyword parameters which will be
- filled in from the request (in that case they *must* be
- present in the request)."""
-
- def render(**kw):
- """A view can either be rendered by an associated template, or
- it can implement this method to render itself from Python.
- This is useful if the view's output isn't XML/HTML but
- something computed in Python (plain text, PDF, etc.)
-
- render() can take arbitrary keyword parameters which will be
- filled in from the request (in that case they *must* be
- present in the request)."""
-
def application_url(name=None):
"""Return the URL of the closest application object in the
hierarchy or the URL of a named object (``name`` parameter)
Modified: grok/trunk/src/grok/meta.py
===================================================================
--- grok/trunk/src/grok/meta.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/meta.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -13,15 +13,11 @@
##############################################################################
"""Grokkers for the various components."""
-import os
-
import zope.component.interface
from zope import interface, component
-from zope.interface.interface import InterfaceClass
from zope.publisher.interfaces.browser import (IDefaultBrowserLayer,
IBrowserRequest,
- IBrowserPublisher,
- IBrowserSkinType)
+ IBrowserPublisher)
from zope.publisher.interfaces.http import IHTTPRequest
from zope.publisher.interfaces.xmlrpc import IXMLRPCRequest
@@ -48,7 +44,7 @@
from martian import util
import grok
-from grok import components, formlib, templatereg
+from grok import components, formlib
from grok.util import make_checker
from grok.interfaces import IRESTSkinType
from grok.interfaces import IViewletManager as IGrokViewletManager
@@ -143,79 +139,25 @@
return True
-class ViewGrokker(martian.ClassGrokker):
- martian.component(grok.View)
+class FormGrokker(martian.ClassGrokker):
+ martian.component(components.GrokForm)
martian.directive(grok.context)
- martian.directive(grok.layer, default=IDefaultBrowserLayer)
- martian.directive(grok.name, get_default=default_view_name)
- martian.directive(grok.require, name='permission')
- def grok(self, name, factory, module_info, **kw):
- # Need to store the module info object on the view class so that it
- # can look up the 'static' resource directory.
- factory.module_info = module_info
- return super(ViewGrokker, self).grok(name, factory, module_info, **kw)
+ def execute(self, factory, config, context, **kw):
+ # Set up form_fields from context class if they haven't been
+ # configured manually already.
+ if getattr(factory, 'form_fields', None) is None:
+ factory.form_fields = formlib.get_auto_fields(context)
- def execute(self, factory, config, context, layer, name, permission, **kw):
- if util.check_subclass(factory, components.GrokForm):
- # setup form_fields from context class if we've encountered a form
- if getattr(factory, 'form_fields', None) is None:
- factory.form_fields = formlib.get_auto_fields(context)
-
- if not getattr(factory.render, 'base_method', False):
- raise GrokError(
- "It is not allowed to specify a custom 'render' "
- "method for form %r. Forms either use the default "
- "template or a custom-supplied one." % factory,
- factory)
-
- # find templates
- templates = factory.module_info.getAnnotation('grok.templates', None)
- if templates is not None:
- config.action(
- discriminator=None,
- callable=self.checkTemplates,
- args=(templates, factory.module_info, factory)
- )
-
- # safety belt: make sure that the programmer didn't use
- # @grok.require on any of the view's methods.
- methods = util.methods_from_class(factory)
- for method in methods:
- if grok.require.bind().get(method) is not None:
- raise GrokError('The @grok.require decorator is used for '
- 'method %r in view %r. It may only be used '
- 'for XML-RPC methods.'
- % (method.__name__, factory), factory)
-
- # __view_name__ is needed to support IAbsoluteURL on views
- factory.__view_name__ = name
- adapts = (context, layer)
-
- config.action(
- discriminator=('adapter', adapts, interface.Interface, name),
- callable=component.provideAdapter,
- args=(factory, adapts, interface.Interface, name),
- )
-
- config.action(
- discriminator=('protectName', factory, '__call__'),
- callable=make_checker,
- args=(factory, factory, permission),
- )
-
+ if not getattr(factory.render, 'base_method', False):
+ raise GrokError(
+ "It is not allowed to specify a custom 'render' "
+ "method for form %r. Forms either use the default "
+ "template or a custom-supplied one." % factory,
+ factory)
return True
- def checkTemplates(self, templates, module_info, factory):
- def has_render(factory):
- return (getattr(factory, 'render', None) and
- not util.check_subclass(factory, grok.components.GrokForm))
- def has_no_render(factory):
- return not getattr(factory, 'render', None)
- templates.checkTemplates(module_info, factory, 'view',
- has_render, has_no_render)
-
class JSONGrokker(martian.MethodGrokker):
martian.component(grok.JSON)
martian.directive(grok.context)
@@ -260,109 +202,6 @@
return True
-class TemplateGrokker(martian.GlobalGrokker):
- # this needs to happen before any other grokkers execute that use
- # the template registry
- martian.priority(1001)
-
- def grok(self, name, module, module_info, config, **kw):
- module.__grok_templates__ = templatereg.TemplateRegistry()
- return True
-
-
-class ModulePageTemplateGrokker(martian.InstanceGrokker):
- martian.component(grok.components.BaseTemplate)
- # this needs to happen before any other grokkers execute that actually
- # use the templates
- martian.priority(1000)
-
- def grok(self, name, instance, module_info, config, **kw):
- templates = module_info.getAnnotation('grok.templates', None)
- if templates is None:
- return False
- config.action(
- discriminator=None,
- callable=templates.register,
- args=(name, instance)
- )
- config.action(
- discriminator=None,
- callable=instance._annotateGrokInfo,
- args=(name, module_info.dotted_name)
- )
- return True
-
-
-class FilesystemPageTemplateGrokker(martian.GlobalGrokker):
- # do this early on, but after ModulePageTemplateGrokker, as
- # findFilesystem depends on module-level templates to be
- # already grokked for error reporting
- martian.priority(999)
-
- def grok(self, name, module, module_info, config, **kw):
- templates = module_info.getAnnotation('grok.templates', None)
- if templates is None:
- return False
- config.action(
- discriminator=None,
- callable=templates.findFilesystem,
- args=(module_info,)
- )
- return True
-
-
-class UnassociatedTemplatesGrokker(martian.GlobalGrokker):
- martian.priority(-1001)
-
- def grok(self, name, module, module_info, config, **kw):
- templates = module_info.getAnnotation('grok.templates', None)
- if templates is None:
- return False
-
- config.action(
- discriminator=None,
- callable=templates.checkUnassociated,
- args=(module_info,)
- )
- return True
-
-
-class StaticResourcesGrokker(martian.GlobalGrokker):
-
- def grok(self, name, module, module_info, config, **kw):
- # we're only interested in static resources if this module
- # happens to be a package
- if not module_info.isPackage():
- return False
-
- resource_path = module_info.getResourcePath('static')
- if os.path.isdir(resource_path):
- static_module = module_info.getSubModuleInfo('static')
- if static_module is not None:
- if static_module.isPackage():
- raise GrokError(
- "The 'static' resource directory must not "
- "be a python package.",
- module_info.getModule())
- else:
- raise GrokError(
- "A package can not contain both a 'static' "
- "resource directory and a module named "
- "'static.py'", module_info.getModule())
-
- resource_factory = components.DirectoryResourceFactory(
- resource_path, module_info.dotted_name)
- adapts = (IDefaultBrowserLayer,)
- provides = interface.Interface
- name = module_info.dotted_name
- config.action(
- discriminator=('adapter', adapts, provides, name),
- callable=component.provideAdapter,
- args=(resource_factory, adapts, provides, name),
- )
- return True
-
-
class SiteGrokker(martian.ClassGrokker):
martian.component(grok.Site)
martian.priority(500)
@@ -609,35 +448,6 @@
return intids
-_skin_not_used = object()
-
-class SkinInterfaceDirectiveGrokker(martian.InstanceGrokker):
- martian.component(InterfaceClass)
-
- def grok(self, name, interface, module_info, config, **kw):
- skin = grok.skin.bind(default=_skin_not_used).get(interface)
- if skin is _skin_not_used:
- # The skin directive is not actually used on the found interface.
- return False
-
- if not interface.extends(IBrowserRequest):
- # For layers it is required to extend IBrowserRequest.
- raise GrokError(
- "The grok.skin() directive is used on interface %r. "
- "However, %r does not extend IBrowserRequest which is "
- "required for interfaces that are used as layers and are to "
- "be registered as a skin."
- % (interface.__identifier__, interface.__identifier__),
- interface
- )
- config.action(
- discriminator=('utility', IBrowserSkinType, skin),
- callable=zope.component.interface.provideInterface,
- args=(skin, interface, IBrowserSkinType)
- )
- return True
-
-
class RESTProtocolGrokker(martian.ClassGrokker):
martian.component(grok.RESTProtocol)
martian.directive(grok.layer, default=IBrowserRequest)
Modified: grok/trunk/src/grok/meta.zcml
===================================================================
--- grok/trunk/src/grok/meta.zcml 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/meta.zcml 2008-08-07 22:01:16 UTC (rev 89512)
@@ -8,6 +8,7 @@
<!-- Load the grokkers -->
<include package="grokcore.component" file="meta.zcml" />
<include package="grokcore.security" file="meta.zcml" />
+ <include package="grokcore.view" file="meta.zcml" />
<grok:grok package=".meta" />
</configure>
Deleted: grok/trunk/src/grok/templatereg.py
===================================================================
--- grok/trunk/src/grok/templatereg.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/templatereg.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -1,131 +0,0 @@
-from martian.error import GrokError
-from martian import util
-
-import os
-import zope.component
-import grok
-import warnings
-
-class TemplateRegistry(object):
-
- def __init__(self):
- self._reg = {}
-
- def register(self, name, template):
- self._reg[name] = dict(template=template, associated=False)
-
- def markAssociated(self, name):
- self._reg[name]['associated'] = True
-
- def get(self, name):
- entry = self._reg.get(name)
- if entry is None:
- return None
- return entry['template']
-
- def findFilesystem(self, module_info):
- template_dir_name = grok.templatedir.bind().get(
- module=module_info.getModule())
- if template_dir_name is None:
- template_dir_name = module_info.name + '_templates'
-
- template_dir = module_info.getResourcePath(template_dir_name)
-
- if not os.path.isdir(template_dir):
- return
-
- if module_info.isPackage():
- return
-
- for template_file in os.listdir(template_dir):
- if template_file.startswith('.') or template_file.endswith('~'):
- continue
-
- template_name, extension = os.path.splitext(template_file)
- extension = extension[1:] # Get rid of the leading dot.
- template_factory = zope.component.queryUtility(
- grok.interfaces.ITemplateFileFactory,
- name=extension)
-
- if template_factory is None:
- # Warning when importing files. This should be
- # allowed because people may be using editors that generate
- # '.bak' files and such.
- warnings.warn("File '%s' has an unrecognized extension in "
- "directory '%s'" %
- (template_file, template_dir), UserWarning, 2)
- continue
-
- inline_template = self.get(template_name)
- if inline_template:
- raise GrokError("Conflicting templates found for name '%s' "
- "in module %r, either inline and in template "
- "directory '%s', or two templates with the "
- "same name and different extensions."
- % (template_name, module_info.getModule(),
- template_dir), inline_template)
-
- template = template_factory(template_file, template_dir)
- template_path = os.path.join(template_dir, template_file)
- template._annotateGrokInfo(template_name, template_path)
-
- self.register(template_name, template)
-
- def listUnassociated(self):
- for name, entry in self._reg.iteritems():
- if not entry['associated']:
- yield name
-
- def checkUnassociated(self, module_info):
- unassociated = list(self.listUnassociated())
- if unassociated:
- msg = (
- "Found the following unassociated template(s) when "
- "grokking %r: %s. Define view classes inheriting "
- "from grok.View to enable the template(s)." % (
- module_info.dotted_name, ', '.join(unassociated)))
- warnings.warn(msg, UserWarning, 1)
-
- def checkTemplates(self, module_info, factory, component_name,
- has_render, has_no_render):
- factory_name = factory.__name__.lower()
- template_name = grok.template.bind().get(factory)
- if template_name is None:
- template_name = factory_name
-
- if factory_name != template_name:
- # grok.template is being used
-
- if self.get(factory_name):
- raise GrokError("Multiple possible templates for %s %r. It "
- "uses grok.template('%s'), but there is also "
- "a template called '%s'."
- % (component_name, factory, template_name,
- factory_name), factory)
- template = self.get(template_name)
- if template is not None:
- if has_render(factory):
- # we do not accept render and template both for a view
- # (unless it's a form, they happen to have render.
- raise GrokError(
- "Multiple possible ways to render %s %r. "
- "It has both a 'render' method as well as "
- "an associated template." %
- (component_name, factory), factory)
- self.markAssociated(template_name)
- factory.template = template
- template._initFactory(factory)
- else:
- if has_no_render(factory):
- # we do not accept a view without any way to render it
- raise GrokError("%s %r has no associated template or "
- "'render' method." %
- (component_name.title(), factory), factory)
-
-class PageTemplateFileFactory(grok.GlobalUtility):
-
- grok.implements(grok.interfaces.ITemplateFileFactory)
- grok.name('pt')
-
- def __call__(self, filename, _prefix=None):
- return grok.components.PageTemplate(filename=filename, _prefix=_prefix)
Modified: grok/trunk/src/grok/testing.py
===================================================================
--- grok/trunk/src/grok/testing.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/testing.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -43,8 +43,9 @@
config = ConfigurationMachine()
zcml.do_grok('grokcore.component.meta', config)
zcml.do_grok('grokcore.security.meta', config)
+ zcml.do_grok('grokcore.view.meta', config)
+ zcml.do_grok('grokcore.view.templatereg', config)
zcml.do_grok('grok.meta', config)
- zcml.do_grok('grok.templatereg', config)
zcml.do_grok(module_name, config)
config.execute_actions()
Modified: grok/trunk/src/grok/tests/zcml/directivepackage.py
===================================================================
--- grok/trunk/src/grok/tests/zcml/directivepackage.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/tests/zcml/directivepackage.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -1,16 +1,16 @@
"""
>>> import grok
>>> from zope.configuration import xmlconfig
- >>> context = xmlconfig.file('meta.zcml', grok)
>>> ignored = xmlconfig.string('''
... <configure
... xmlns="http://namespaces.zope.org/zope"
... xmlns:grok="http://namespaces.zope.org/grok"
... >
- ... <grok:grok package="grok.templatereg"/>
+ ... <include package="grok" file="meta.zcml" />
+ ... <grok:grok package="grokcore.view.templatereg" />
... <grok:grok package="grok.tests.zcml.stoneage"/>
- ... </configure>''', context=context)
+ ... </configure>''')
>>> from grok.tests.zcml.stoneage.cave import Cave
>>> from grok.tests.zcml.stoneage.hunt.mammoth import Mammoth
Modified: grok/trunk/src/grok/util.py
===================================================================
--- grok/trunk/src/grok/util.py 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/src/grok/util.py 2008-08-07 22:01:16 UTC (rev 89512)
@@ -13,14 +13,9 @@
##############################################################################
"""Grok utility functions.
"""
-import urllib
-
import grok
import zope.location.location
-from zope import component
from zope import interface
-from zope.traversing.browser.interfaces import IAbsoluteURL
-from zope.traversing.browser.absoluteurl import _safe as SAFE_URL_CHARACTERS
from zope.security.checker import NamesChecker, defineChecker
from grokcore.security.util import check_permission
@@ -41,20 +36,6 @@
checker = NamesChecker(method_names, permission)
defineChecker(view_factory, checker)
-def url(request, obj, name=None, data={}):
- url = component.getMultiAdapter((obj, request), IAbsoluteURL)()
- if name is not None:
- url += '/' + urllib.quote(name.encode('utf-8'), SAFE_URL_CHARACTERS)
- if data:
- for k,v in data.items():
- if isinstance(v, unicode):
- data[k] = v.encode('utf-8')
- if isinstance(v, (list, set, tuple)):
- data[k] = [isinstance(item, unicode) and item.encode('utf-8')
- or item for item in v]
- url += '?' + urllib.urlencode(data, doseq=True)
- return url
-
def safely_locate_maybe(obj, parent, name):
"""Set an object's __parent__ (and __name__) if the object's
__parent__ attribute doesn't exist yet or is None.
Modified: grok/trunk/versions.cfg
===================================================================
--- grok/trunk/versions.cfg 2008-08-07 21:38:03 UTC (rev 89511)
+++ grok/trunk/versions.cfg 2008-08-07 22:01:16 UTC (rev 89512)
@@ -7,6 +7,7 @@
docutils = 0.4
grokcore.component = 1.5.1
grokcore.security = 1.0
+grokcore.view = 1.0
martian = 0.10
mechanize = 0.1.7b
pytz = 2007k
More information about the Checkins
mailing list