Upgrade to Pro — share decks privately, control downloads, hide ads and more …

PyConZA 2014: "The elephant in the web application" by Iwan Vosloo

Pycon ZA
October 02, 2014

PyConZA 2014: "The elephant in the web application" by Iwan Vosloo

In this talk, I'd like to convince you that developing a web application today is an unnecessarily cumbersome and error prone task. It is time for web frameworks to evolve and become more like graphical user interface (GUI) frameworks: these provide abstractions called "windows" or "widgets" that let a programmer write an application using terms that describe what is being built, with less (if any) focus on the underlying technologies needed to accomplish drawing these items on a screen.

A web application programmer (in contrast to a GUI programmer) needs to know quite a few different technologies and a fair bit of effort is required to orchestrate these tools into achieving an end result: a template language, HTML, HTTP, CSS, JavaScript, etc. Reusing something substantial is especially difficult, which means in a sizeable web application the same dragons need to be fought several times over. If a programmer has to constantly deal with all this subject matter, it takes focus away from what actually needs to be built: the application itself.

Why are we putting up with having to know HTML and similar low-level technologies? Is it an elephant in the room? Something we pretend not to see, yet we accept the burden of having to work around it?

I will show you what it takes to build a web application; what repetitive tasks there are and what a programmer needs to be aware of. I hope to convince you that there's a better way, and that what was perhaps an idealistic dream a decade ago can now be done - not only by our own fully-featured Python web framework (Reahl), but also by a small number of others beyond the realm of Python.

Pycon ZA

October 02, 2014
Tweet

More Decks by Pycon ZA

Other Decks in Programming

Transcript

  1. Overview • The typical web framework • What you’d have

    to learn • Cognitive load • Lessons from the GUI • Our vision in context
  2. Framework duties def func(code code co) code code code code

    code code GET /some/url map url to some code 1 HTML Template <html> <body> </body> </html> 2 read from a database 3 merge data with template 4 respond final HTML The typical web framework
  3. User input GET /some/url HTML <form> POST /formurl REDIRECT GET

    /result/url HTML Name: Save Hello John ! The typical web framework
  4. Input Validation POST /formurl REDIRECT GET /result/url HTML Name: Save

    validate form input render form with error messages validate before POSTing Name is required The typical web framework
  5. Other stuff • Internationalisation (i18n) • Static files • ORM

    (or other persistence) • Migration • Development tools The typical web framework
  6. What you’d have to learn • Basic tools • Best

    practice • Recurring problems • Platform quirks
  7. Server-side framework @app.route('/') def show_entries(): db = get_db() cur =

    db.execute('select * from addresses') entries = cur.fetchall() return render_template('show_entries.html', addresses=entries) What you’d have to learn | Basic tools
  8. Template language {% block body %} {% from "_formhelpers.html" import

    render_field %} <form action="{{ url_for('index') }}" method="post" class="add-entry"> <dl>{{ render_field(form.name) }} {{ render_field(form.email_address) }}</dl> <p><input type="submit” value="Add"> </form> <ul class="entries"> {% for address in addresses %} <li><h2>{{ address.name }}</h2> {{ address.email_address|safe }} {% endfor %} </ul> {% endblock %} What you’d have to learn | Basic tools
  9. <html> <body> <form action="/add" method="post" class="add-entry"> <dl><dt><label for="name">Name</label></dt> <dd><input id="name"

    name="name" type="text" value=""></dd> <dt><label for="email">Email Address</label></dt> <dd><input id="email" name="email" type="text" value=""></dd> </dl> <p><input type="submit” value="Add"> </form> <ul class="entries"> <li><h2>John doe</h2>[email protected] </ul> </body> </html> HTML What you’d have to learn | Basic tools
  10. CSS ul.reahl-menu > li > a { display: inline-block; }

    ul.reahl-menu > li { display: inline-block; zoom:1; *display:inline; position: relative; } ul.reahl-menu li > a { color: #fff; background: #bf8130; } <ul class=”reahl-menu”> <li class=”active”> <a href=”xxx”>Item 1</a> <li><a href=”yyy”>Item 2</a> </ul> Item 1 Item 2 What you’d have to learn | Basic tools
  11. JavaScript & friends Your email [email protected] click inside input type

    some- thing What you’d have to learn | Basic tools
  12. JavaScript & friends var input = $("input"); var label =

    $("label"); input .bind("focus", function(){ if ( $(this).val() == "" ) { label.attr('hidden', 'true'); }}) .bind("blur", function(){ if ( $(this).val() == "" ) { label.removeAttr('hidden'); }}); if ( input.val() == "" ) { label.removeAttr('hidden'); } else {label.attr('hidden', 'true');} <span class="labelover"> <label>Your email</label> <span><input type="text"/></span> </span> .labelover {position: relative;} .labelover > label { cursor: text; position: absolute; bottom: 0; left: 0; z-index:1; } What you’d have to learn | Basic tools
  13. Graceful degradation Hello World! Hello World! JS Hello World! Hello

    World! CSS JS What you’d have to learn | Best practices
  14. More best practices • Crawlability • Bookmarkable URLs • Device

    independence • Fluid layout • Security tricks • ... What you’d have to learn | Best practices Hello World!
  15. Concurrency aaa bbb ccc X X X aaa bbb ccc

    X X X aaa bbb ccc aaa ccc ? What you’d have to learn | Recurring issues
  16. Other recurring issues • Internationalisation done differently • Users with

    unequal access to UIs • Different options for validation • Re-use of complicated UI elements • Handling of database transactions • ... What you’d have to learn | Recurring issues
  17. What you end up with js 1 template template css

    python template python jq plugin Cognitive load
  18. Instead GUIs give you... • Resizable fonts • Windows with

    title bars • Controls in those title bars • Menus • Buttons, Inputs and Events Lessons from the GUI
  19. Python only, nothing else needed class MyPage(TwoColumnPage): def __init__(self, view):

    super(MyPage, self).__init__(view, style='basic') tabbed_panel = self.main.add_child(TabbedPanel(view, 'mytabbedpanel')) tab1_contents = P.factory(text='A paragraph to give content to the first tab.') tabbed_panel.add_tab(Tab(view, 'Tab 1', '1', tab1_contents)) tab2_contents = P.factory(text='And another ... to give content to the second tab.') tabbed_panel.add_tab(Tab(view, 'Tab 2', '2', tab2_contents)) tab3_contents = P.factory(text='Something else on the third tab.') tabbed_panel.add_tab(Tab(view, 'Tab 3', '3', tab3_contents)) Lessons from the GUI
  20. Python only, nothing else needed class MyPage(TwoColumnPage): def __init__(self, view):

    super(MyPage, self).__init__(view, style='basic') tabbed_panel = self.main.add_child(TabbedPanel(view, 'mytabbedpanel')) tab1_contents = P.factory(text='A paragraph to give content to the first tab.') tabbed_panel.add_tab(Tab(view, 'Tab 1', '1', tab1_contents)) tab2_contents = P.factory(text='And another ... to give content to the second tab.') tabbed_panel.add_tab(Tab(view, 'Tab 2', '2', tab2_contents)) tab3_contents = P.factory(text='Something else on the third tab.') tabbed_panel.add_tab(Tab(view, 'Tab 3', '3', tab3_contents)) Lessons from the GUI See this running at: http://www.reahl.org/examples/tabbedpanel/ More examples at: http://www.reahl.org/docs/3.0/features/
  21. Python Others dream too GWT Wt Echo Wicket Tosca Widgets

    reahl Java C++ Our vision in context