11.. module :: hyperpython
22
3- ==========
4- Templating
5- ==========
6-
7- The goal of ``hyperpython `` is to replace a lot of work that would traditionally
8- be done with a template engine such as Jinja2 by Python code that generates HTML
9- fragments. Templating languages are obviously more efficient than pure Python for
10- string interpolation, and should work better for simple cases. For long documents,
11- however, templating can be very repetitive. HTML is a structured format and we
12- eliminate duplication by composing simple functions and using other standard
13- techniques in Software Engineering.
14-
15- It is becoming increasingly common in the Javascript world to use more
16- structured approaches to generate HTML code (or direct creation of DOM/virtual DOM nodes).
17- React was probably the library that popularized this idea. As they elegantly put,
18- "Templates separate technologies, not concerns". The point being that it is
19- better to generate DOM nodes in Javascript instead of choosing a deliberately
20- underpowered language that has a that poorly communicates with your data
21- sources created in Javascript. The same lesson can be applied to Python on
22- the server side.
23-
24- For those afraid of putting too much logic on templates, we recognize that
25- Hyperpython doesn't prevent anyone from shooting itself on the foot, but neither
26- does any minimally powerful templating language. The discipline we should exercise
27- is to keep business logic separate from view logic. Our advice is:
28- *break your code in small pieces and compose those pieces in simple and predictable ways *.
29- Incidentally, this is a good advice for any piece of code ;).
30-
31- Let us dive in!
3+ ========
4+ Tutorial
5+ ========
326
337A simple example
348================
@@ -55,17 +29,17 @@ actions (this is a random example taken from Bootstrap website).
5529 </ul >
5630 </div >
5731
58- Of course we could translate this directly into Hyperpython code by calling the
59- corresponding ``div() ``'s , ``button() ``'s , etc. But first, let us break up this
60- mess into smaller pieces.
32+ Of course we could translate this directly into Hyperpython by calling the
33+ corresponding ``div() ``, ``button() ``, etc functions . But first, let us break
34+ up this mess into smaller pieces.
6135
6236.. code-block :: python
6337
6438 from hyperpython import button, div, p, ul, li, span, a, classes
6539
6640 def menu_button (name , caret = True , class_ = None , ** kwargs ):
6741 if caret:
68- children = [name, ' ' , span(caret)]
42+ children = [name, ' ' , span(' caret' )]
6943 else :
7044 children = [name]
7145
@@ -129,8 +103,8 @@ Look how nice it is now :)
129103How does it work?
130104=================
131105
132- Hyperpython HTML syntax is just regular Python wrapped in a HTML-wannabe DSL.
133- How does it work?
106+ Hyperpython syntax is just regular Python wrapped in a HTML-wannabe DSL. How
107+ does it work?
134108
135109Take the example:
136110
@@ -143,8 +117,8 @@ Take the example:
143117 ]
144118
145119 In Hyperpython, we can declare attributes as keyword arguments and children as a
146- index access. This clever abuse of Python syntax is good to creating expressive
147- representations of HTML documents. Under the hood, Python call div() and
120+ index access. This clever abuse of Python syntax is good for creating expressive
121+ representations of HTML documents. Under the hood, Python calls div() and
148122generates an :class: `Element ` instance. Indexing is used to insert the given
149123elements as children and then return the tag itself as a result. We encourage
150124using this syntax only during element creation in order to avoid confusion.
@@ -167,10 +141,9 @@ Tag functions also accept a few alternative signatures:
167141 Children can also be passed as a keyword argument.
168142 This generates ``<h1 class="foo">title</h1> ``.
169143
170- In HTML, tag attributes are all stringly typed. This is far from ideal and can
171- be easily fixed since we are representing HTML from a more rigorously typed
172- language. Hyperpython does the following coercions when interpreting
173- attributes:
144+ In HTML, all tag attributes are all stringly typed. This is far from ideal and can
145+ be easily fixed since we are representing HTML from a typed language.
146+ Hyperpython does the following coercions when interpreting attributes:
174147
175148"class" attribute:
176149 Hyperpython expects a list of strings. If a single string is given, it is
@@ -190,24 +163,22 @@ Imperative interface
190163We encourage users to adopt the declarative API and generally treat tags
191164as immutable structures. Hyperpython does not enforce immutability and actually
192165offers some APIs to change data structures inplace. Once a tag is created, it
193- is possible to change it's attributes dictionary and list of children. We
194- encourage to use the appropriate method instead of manipulating those data
195- structures directly.
166+ is possible to change it's attributes dictionary and list of children. There
167+ are also a few methods designed to manipulate Hyperpython data structures.
196168
197169>>> elem = div(' foo' , class_ = ' elem' )
198170>>> elem.add_child(' bar' )
199171>>> print (elem)
200172<div class="elem">foobar</div>
201173
202- Similarly to the children property, attributes are also exposed :
174+ Attributes are also exposed in the .attrs dictionary :
203175
204176>>> elem.attrs[' data-answer' ] = 42
205177>>> elem.attrs.keys()
206178dict_keys(['class', 'data-answer'])
207179
208- Manipulating the list of classes and the element id also introduces specialized
209- methods and attributes. The ``.id `` and ``.classes `` attributes expose those
210- two properties.
180+ The "class" and "id" attributes are also exposed directly from the tag object
181+ since they are used so often:
211182
212183>>> elem = div(' foo' , class_ = ' class' , id = ' id' )
213184>>> elem.id, elem.classes
0 commit comments