Skip to content

Instantly share code, notes, and snippets.

@mmerickel
Created February 5, 2015 22:18
Show Gist options
  • Save mmerickel/926c8437b5224b281376 to your computer and use it in GitHub Desktop.
Save mmerickel/926c8437b5224b281376 to your computer and use it in GitHub Desktop.
pyramid view lookup patch
diff --git a/pyramid/router.py b/pyramid/router.py
index ba4f85b..a11e556 100644
--- a/pyramid/router.py
+++ b/pyramid/router.py
@@ -1,10 +1,12 @@
from zope.interface import (
implementer,
providedBy,
+ Interface,
)
from pyramid.interfaces import (
IDebugLogger,
+ IMultiView,
IRequest,
IRequestExtensions,
IRootFactory,
@@ -12,6 +14,7 @@ from pyramid.interfaces import (
IRouter,
IRequestFactory,
IRoutesMapper,
+ ISecuredView,
ITraverser,
IView,
IViewClassifier,
@@ -138,9 +141,10 @@ class Router(object):
# find a view callable
context_iface = providedBy(context)
- view_callable = adapters.lookup(
- (IViewClassifier, request.request_iface, context_iface),
- IView, name=view_name, default=None)
+ views_iter = get_views(
+ adapters, request.request_iface, context_iface, view_name)
+
+ view_callable = next(views_iter, None)
# invoke the view callable
if view_callable is None:
@@ -164,14 +168,7 @@ class Router(object):
except PredicateMismatch:
# look for other views that meet the predicate
# criteria
- for iface in context_iface.__sro__[1:]:
- previous_view_callable = view_callable
- view_callable = adapters.lookup(
- (IViewClassifier, request.request_iface, iface),
- IView, name=view_name, default=None)
- # intermediate bases may lookup same view_callable
- if view_callable is previous_view_callable:
- continue
+ for view_callable in views_iter:
if view_callable is not None:
try:
response = view_callable(context, request)
@@ -242,3 +239,12 @@ class Router(object):
response = self.invoke_subrequest(request, use_tweens=True)
return response(request.environ, start_response)
+def get_views(adapters, request_iface, context_iface, view_name):
+ for iface in context_iface.__sro__:
+ for view_type in (IView, ISecuredView, IMultiView):
+ for req_type in request_iface.__sro__:
+ view_callable = adapters.registered(
+ (IViewClassifier, req_type, iface),
+ view_type, name=view_name)
+ if view_callable is not None:
+ yield view_callable
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment