def __init__(self, defaults=None, tags=None, presentation_slots=()): """ """ self._defaults = {} if defaults is None else defaults self._loader = TagLoader(tags) self._presentationSlots = {self.CONTENT} | set(presentation_slots) self._renderers = {}
def traceback(self, request, tag): """ Render all the frames in the wrapped L{Failure<twisted.python.failure.Failure>}'s traceback stack, replacing C{tag}. """ return _StackElement(TagLoader(tag), self.failure.frames)
def frames(self, request, tag): """ Render the list of frames in this L{_StackElement}, replacing C{tag}. """ return [ _FrameElement(TagLoader(tag.clone()), frame) for frame in self.stackFrames ]
def mydecorator(method): loader = TagLoader(tags) @modified("plating route renderer", method, routing) @bindable @inlineCallbacks def mymethod(instance: Any, request: IRequest, *args: Any, **kw: Any) -> Any: data = yield _call(instance, method, request, *args, **kw) if _should_return_json(request): json_data = self._defaults.copy() json_data.update(data) for ignored in self._presentationSlots: json_data.pop(ignored, None) text_type = "json" ready = yield resolveDeferredObjects(json_data) result = dumps(ready) else: data[self.CONTENT] = loader.load() text_type = "html" result = self._elementify(instance, data) request.setHeader( b"content-type", ("text/{format}; charset=utf-8".format( format=text_type).encode("charmap")), ) returnValue(result) return method
def customFormRender(self, form): # type: (RenderableForm) -> Any """ Include just the glue necessary for CSRF protection and let the application render the rest of the form. """ return Element(loader=TagLoader(tags.html(tags.body(form.glue()))))
class TagLoaderTests(FlattenTestCase): """ Tests for L{TagLoader}. """ def setUp(self): self.loader = TagLoader(tags.i('test')) def test_interface(self): """ An instance of L{TagLoader} provides L{ITemplateLoader}. """ self.assertTrue(verifyObject(ITemplateLoader, self.loader)) def test_loadsList(self): """ L{TagLoader.load} returns a list, per L{ITemplateLoader}. """ self.assertIsInstance(self.loader.load(), list) def test_flatten(self): """ L{TagLoader} can be used in an L{Element}, and flattens as the tag used to construct the L{TagLoader} would flatten. """ e = Element(self.loader) self.assertFlattensImmediately(e, '<i>test</i>')
def test_sourceFragmentElement(self): """ L{_SourceFragmentElement} renders source lines at and around the line number indicated by a frame object. """ element = _SourceFragmentElement( TagLoader( tags.div(tags.span(render="lineNumber"), tags.span(render="sourceLine"), render="sourceLines")), self.frame) source = [ u' \N{NO-BREAK SPACE} \N{NO-BREAK SPACE}message = ' u'"This is a problem"', u' \N{NO-BREAK SPACE} \N{NO-BREAK SPACE}raise Exception(message)', u'# Figure out the line number from which the exception will be ' u'raised.', ] d = flattenString(None, element) d.addCallback( self.assertEqual, ''.join([ '<div class="snippet%sLine"><span>%d</span><span>%s</span>' '</div>' % (["", "Highlight"][lineNumber == 1], self.base + lineNumber, (u" \N{NO-BREAK SPACE}" * 4 + sourceLine).encode('utf-8')) for (lineNumber, sourceLine) in enumerate(source) ])) return d
class TagLoaderTests(FlattenTestCase): """ Tests for L{TagLoader}. """ def setUp(self): self.loader = TagLoader(tags.i('test')) def test_interface(self): """ An instance of L{TagLoader} provides L{ITemplateLoader}. """ self.assertTrue(verifyObject(ITemplateLoader, self.loader)) def test_loadsList(self): """ L{TagLoader.load} returns a list, per L{ITemplateLoader}. """ self.assertIsInstance(self.loader.load(), list) def test_flatten(self): """ L{TagLoader} can be used in an L{Element}, and flattens as the tag used to construct the L{TagLoader} would flatten. """ e = Element(self.loader) self.assertFlattensImmediately(e, b'<i>test</i>')
def render(): child = Elem() for _ in xrange(20): child = Elem([child]) root = TagLoader([child] * 10).load() out = BytesIO() flatten(None, root, out.write)
def mydecorator(method): loader = TagLoader(tags) @modified("plating route renderer", method, routing) @bindable @inlineCallbacks def mymethod(instance, request, *args, **kw): data = yield _call(instance, method, request, *args, **kw) if _should_return_json(request): json_data = self._defaults.copy() json_data.update(data) for ignored in self._presentationSlots: json_data.pop(ignored, None) text_type = u'json' result = json_serialize(json_data) else: data[self.CONTENT] = loader.load() text_type = u'html' result = self._elementify(instance, data) request.setHeader(b'content-type', (u'text/{format}; charset=utf-8'.format( format=text_type).encode("charmap"))) returnValue(result) return method
def rows(self, request, tag): return [ TableRow( TagLoader(tag), self.docgetter, self.ob, child) for child in self.children]
def __init__(self, defaults=None, tags=None, presentation_slots=frozenset()): """ """ self._defaults = {} if defaults is None else defaults self._loader = TagLoader(tags) self._presentation_slots = {self.CONTENT} | set(presentation_slots)
def test_failureElementValue(self): """ The I{value} renderer of L{FailureElement} renders the value's exception value. """ element = FailureElement(self.failure, TagLoader(tags.span(render="value"))) d = flattenString(None, element) d.addCallback(self.assertEqual, b"<span>This is a problem</span>") return d
def cascadeRenderer(self, form: RenderableForm) -> RenderableForm: class CustomElement(Element): @renderer def customize(self, request: IRequest, tag: Any) -> Any: return tag("customized") form.validationErrors[form._form.fields[0]] = ValidationError( message=(tags.div(class_="checkme", render="customize"))) return CustomElement(loader=TagLoader(form))
def __init__(self, name: str, text: str): super().__init__(name=name, text=text) if self.is_empty(): self._dom: Optional[minidom.Document] = None self._version = -1 self._loader: ITemplateLoader = TagLoader(tags.transparent) else: self._dom = parse_xml(self.text) self._version = self._extract_version(self._dom, self.name) self._loader = XMLString(self._dom.toxml())
def test_failureElementType(self): """ The I{type} renderer of L{FailureElement} renders the failure's exception type. """ element = FailureElement(self.failure, TagLoader(tags.span(render="type"))) d = flattenString(None, element) d.addCallback(self.assertEqual, "<span>exceptions.Exception</span>") return d
def test_frameElementLineNumber(self): """ The I{lineNumber} renderer of L{_FrameElement} renders the line number associated with the frame object used to initialize the L{_FrameElement}. """ element = _FrameElement(TagLoader(tags.span(render="lineNumber")), self.frame) d = flattenString(None, element) d.addCallback(self.assertEqual, b"<span>%d</span>" % (self.base + 1, )) return d
def menu_elements(self, request, tag): for el in self.menuData: link = el.lower() cls_active = '' if el == 'cohen3': link = 'home' cls_active += 'active' tag.fillSlots(menu_id=f'but-{link}') tag.fillSlots(menu_class=f'{cls_active}') tag.fillSlots(menu_click=f'openTab(\'{link}\', this)') yield MenuItemElement(TagLoader(tag), el)
def test_frameElementFunction(self): """ The I{function} renderer of L{_FrameElement} renders the line number associated with the frame object used to initialize the L{_FrameElement}. """ element = _FrameElement(TagLoader(tags.span(render="function")), self.frame) d = flattenString(None, element) d.addCallback(self.assertEqual, b"<span>lineNumberProbeAlsoBroken</span>") return d
def __init__(self, slot_data, preloaded): """ @param slot_data: A dictionary mapping names to values. @param preloaded: The pre-loaded data. """ self.slot_data = slot_data super(PlatedElement, self).__init__( loader=TagLoader(preloaded.fillSlots( **{k: _extra_types(v) for k, v in slot_data.items()} )) )
def test_failureElementType(self): """ The I{type} renderer of L{FailureElement} renders the failure's exception type. """ element = FailureElement(self.failure, TagLoader(tags.span(render="type"))) d = flattenString(None, element) if _PY3: exc = b"builtins.Exception" else: exc = b"exceptions.Exception" d.addCallback(self.assertEqual, b"<span>" + exc + b"</span>") return d
def defaultValidationFailureHandler( instance, # type: Optional[object] request, # type: IRequest fieldValues, # type: FieldValues ): # type: (...) -> Element """ This is the default validation failure handler, which will be used by form handlers (i.e. any routes which use L{klein.Requirer} to require a field) in the case of any input validation failure when no other validation failure handler is registered via L{Form.onValidationFailureFor}. Its behavior is to simply return an HTML rendering of the form object, which includes inline information about fields which failed to validate. @param instance: The instance associated with the router that the form handler was handled on. @type instance: L{object} @param request: The request including the form submission. @type request: L{twisted.web.iweb.IRequest} @return: Any object acceptable from a Klein route. """ session = request.getComponent(ISession) # type: ignore[misc] request.setResponseCode(400) enctype = ( ( request.getHeader(b"content-type") or RenderableForm.ENCTYPE_URL_ENCODED.encode("ascii") ) .split(b";")[0] .decode("charmap") ) renderable = RenderableForm( fieldValues.form, session, "/".join( segment.decode("utf-8", errors="replace") for segment in request.prepath ), request.method, enctype, "utf-8", fieldValues.prevalidationValues, fieldValues.validationErrors, ) return Element(TagLoader(renderable))
def __init__(self, slot_data, preloaded, boundInstance, presentationSlots, renderers): """ @param slot_data: A dictionary mapping names to values. @param preloaded: The pre-loaded data. """ self.slot_data = slot_data self._boundInstance = boundInstance self._presentationSlots = presentationSlots self._renderers = renderers super(PlatedElement, self).__init__(loader=TagLoader( preloaded.fillSlots( **{k: _extra_types(v) for k, v in slot_data.items()})))
def test_frameElementFilename(self): """ The I{filename} renderer of L{_FrameElement} renders the filename associated with the frame object used to initialize the L{_FrameElement}. """ element = _FrameElement(TagLoader(tags.span(render="filename")), self.frame) d = flattenString(None, element) d.addCallback( # __file__ differs depending on whether an up-to-date .pyc file # already existed. self.assertEqual, b"<span>" + networkString(__file__.rstrip('c')) + b"</span>") return d
def sourceLines(self, request, tag): """ Render the source line indicated by C{self.frame} and several surrounding lines. The active line will be given a I{class} of C{"snippetHighlightLine"}. Other lines will be given a I{class} of C{"snippetLine"}. """ for (lineNumber, sourceLine) in self._getSourceLines(): newTag = tag.clone() if lineNumber == self.frame[2]: cssClass = "snippetHighlightLine" else: cssClass = "snippetLine" loader = TagLoader(newTag(**{"class": cssClass})) yield _SourceLineElement(loader, lineNumber, sourceLine)
def test_sourceLineElement(self): """ L{_SourceLineElement} renders a source line and line number. """ element = _SourceLineElement( TagLoader(tags.div( tags.span(render="lineNumber"), tags.span(render="sourceLine"))), 50, " print 'hello'") d = flattenString(None, element) expected = ( u"<div><span>50</span><span>" u" \N{NO-BREAK SPACE} \N{NO-BREAK SPACE}print 'hello'</span></div>") d.addCallback( self.assertEqual, expected.encode('utf-8')) return d
def test_serializedAttributeWithTransparentTagWithRenderer(self): """ Like L{test_serializedAttributeWithTransparentTag}, but when the attribute is rendered by a renderer on an element. """ class WithRenderer(Element): def __init__(self, value, loader): self.value = value super(WithRenderer, self).__init__(loader) @renderer def stuff(self, request, tag): return self.value toss = [] self.checkAttributeSanitization( lambda value: toss.append(value) or tags.transparent(render="stuff"), lambda tag: WithRenderer(toss.pop(), TagLoader(tag)) )
def mydecorator(method): loader = TagLoader(content_template) @routing @wraps(method) def mymethod(request, *args, **kw): data = method(request, *args, **kw) if _should_return_json(request): json_data = self._defaults.copy() json_data.update(data) for ignored in self._presentation_slots: json_data.pop(ignored, None) request.setHeader(b'content-type', b'text/json; charset=utf-8') return json_serialize(json_data) else: request.setHeader(b'content-type', b'text/html; charset=utf-8') data[self.CONTENT] = loader.load() return self._elementify(data) return method
def test_sourceFragmentElement(self): """ L{_SourceFragmentElement} renders source lines at and around the line number indicated by a frame object. """ element = _SourceFragmentElement( TagLoader( tags.div( tags.span(render="lineNumber"), tags.span(render="sourceLine"), render="sourceLines", )), self.frame, ) source = [ " \N{NO-BREAK SPACE} \N{NO-BREAK SPACE}message = " '"This is a problem"', " \N{NO-BREAK SPACE} \N{NO-BREAK SPACE}raise Exception(message)", "", ] d = flattenString(None, element) stringToCheckFor = "" for (lineNumber, sourceLine) in enumerate(source): template = '<div class="snippet{}Line"><span>{}</span><span>{}</span></div>' if lineNumber <= 1: stringToCheckFor += template.format( ["", "Highlight"][lineNumber == 1], self.base + lineNumber, (" \N{NO-BREAK SPACE}" * 4 + sourceLine), ) else: stringToCheckFor += template.format("", self.base + lineNumber, ("" + sourceLine)) bytesToCheckFor = stringToCheckFor.encode("utf8") d.addCallback(self.assertEqual, bytesToCheckFor) return d
def source(self, request, tag): """ Render the source code surrounding the line this frame references, replacing C{tag}. """ return _SourceFragmentElement(TagLoader(tag), self.frame)
def setUp(self): self.loader = TagLoader(tags.i('test'))
def widgets(self, request, tag): for widget in self.widgetData: yield WidgetElement(TagLoader(tag), widget)
class Plating(object): """ A L{Plating} is a container which can be used to generate HTML from data. Its name is derived both from tem-I{plating} and I{chrome plating}. """ CONTENT = "klein:plating:content" def __init__(self, defaults=None, tags=None, presentation_slots=frozenset()): """ """ self._defaults = {} if defaults is None else defaults self._loader = TagLoader(tags) self._presentation_slots = {self.CONTENT} | set(presentation_slots) def routed(self, routing, content_template): """ """ @wraps(routing) def mydecorator(method): loader = TagLoader(content_template) @routing @wraps(method) def mymethod(request, *args, **kw): data = method(request, *args, **kw) if _should_return_json(request): json_data = self._defaults.copy() json_data.update(data) for ignored in self._presentation_slots: json_data.pop(ignored, None) request.setHeader(b'content-type', b'text/json; charset=utf-8') return json_serialize(json_data) else: request.setHeader(b'content-type', b'text/html; charset=utf-8') data[self.CONTENT] = loader.load() return self._elementify(data) return method return mydecorator def _elementify(self, to_fill_with): """ """ slot_data = self._defaults.copy() slot_data.update(to_fill_with) [loaded] = self._loader.load() loaded = loaded.clone() return PlatedElement(slot_data=slot_data, preloaded=loaded) def widgeted(self, function): """ """ @wraps(function) def wrapper(*a, **k): data = function(*a, **k) return self._elementify(data) wrapper.__name__ += ".widget" function.widget = wrapper return function