Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Scala & Lift (JEEConf 2012)

3,730 views

Published on

'Elevate your webapps with Scala & Lift', as presented on JEEConf 2012, Kiev, Ukraine

Also see: http://branchandbound.net/blog/conferences/2012/05/jeeconf-tripreport/

Published in: Technology
  • Be the first to comment

Scala & Lift (JEEConf 2012)

  1. 1. Elevate your webapps with Scala & Lift @Sander_Mak
  2. 2. AboutCoding at Writing Blog @ branchandbound.net Speaking
  3. 3. What should awebframeworkdo?
  4. 4. Webframeworks should... Provide templating Show dynamic content Handle user input Abstract from request/response cycle? Be highly interactive?Preferably: concise, performant, secure
  5. 5. Webframeworks should... Provide templatingLift is view-first Templates pure HTML5 or XHTMLEmbed and surround to compose default.html with: <lift:bind name=”content” />signup.html with:<lift:surround with=”default” name=”content”> <form> ... signup form ... </form><lift:surround />
  6. 6. Webframeworks should... Show dynamic contentPure templates: no code intemplates Problem?
  7. 7. Webframeworks should... Show dynamic contentPure templates: no code intemplates Problem?
  8. 8. Webframeworks should... Show dynamic contentSnippets transform DOM to DOM NodeSeq => NodeSeqGuarantee: well-formedness,sanitizedUse {request, session, database}state
  9. 9. Webframeworks should... Show dynamic content Snippet Viewclass IndexSnippet { .. surrounding html .. def date(in: NodeSeq): NodeSeq = <lift:indexSnippet.date> Helpers.bind("b", in, <div>Current date: "date" -> new Date()) <b:date> 10:00:00 1/1/2012} </b:date> </div> </lift:indexSnippet.date>
  10. 10. Webframeworks should... Show dynamic content ‘Operators’ and implicit conversions: “date”.->(new Date()) results in a tuple: (“date”, new Date()) Snippet Viewclass IndexSnippet { .. surrounding html .. def date(in: NodeSeq): NodeSeq = <lift:indexSnippet.date> Helpers.bind("b", in, <div>Current date: "date" -> new Date()) <b:date> 10:00:00 1/1/2012} </b:date> </div> </lift:indexSnippet.date>
  11. 11. Webframeworks should... Show dynamic content Snippet (CSS binding) Viewclass CssSnippet { .. surrounding html .. <div class="lift:cssSnippet.date"> def date: NodeSeq => NodeSeq = Current date: "#date" #> currentDate <span id="date">10:00:00 1/1/2012</span>} </div> .. surrounding html ..
  12. 12. Webframeworks should... Show dynamic content Constructs a function NodeSeq => NodeSeq Snippet (CSS binding) Viewclass CssSnippet { .. surrounding html .. <div class="lift:cssSnippet.date"> def date: NodeSeq => NodeSeq = Current date: "#date" #> currentDate <span id="date">10:00:00 1/1/2012</span>} </div> .. surrounding html ..
  13. 13. Webframeworks should... Show dynamic content Implicit conversion from String to ToCssBindPromoter Snippet (CSS binding) Viewclass CssSnippet { .. surrounding html .. <div class="lift:cssSnippet.date"> def date: NodeSeq => NodeSeq = Current date: "#date" #> currentDate <span id="date">10:00:00 1/1/2012</span>} </div> .. surrounding html ..
  14. 14. Webframeworks should... Show dynamic content With HTML5 may also be data-lift=”cssSnippet.date” Snippet (CSS binding) Viewclass CssSnippet { .. surrounding html .. <div class="lift:cssSnippet.date"> def date: NodeSeq => NodeSeq = Current date: "#date" #> currentDate <span id="date">10:00:00 1/1/2012</span>} </div> .. surrounding html ..
  15. 15. Webframeworks should... Show dynamic contentNo MVC: MenuSnippetView <=> Snippet NewsSnippetMany <=> Many FormSnippet
  16. 16. Webframeworks should... Handle user input Add server-side behavior to DOM ... with snippets Behavior captured in closures ... managed by Lift, executed aftersubmit Plain and Ajax requests unified Primarily stateful!
  17. 17. Webframeworks should... Handle user input Snippet Viewclass FormSnippet { def nameForm = { .. surrounding html .. var name = "" <form method="POST" def processForm() = class="lift:FormSnippet.nameForm"> println(name) <input id="nameField" type="text"/> "#nameField" #> <input id="submitButton" type="submit"/> SHtml.text(name, name = _) </form> & "#submitButton" #> .. surrounding html .. SHtml.submit("Click", processForm) }}
  18. 18. Webframeworks should... Handle user input Method within method: Snippet View references name in outer scopeclass FormSnippet { def nameForm = { .. surrounding html .. var name = "" <form method="POST" def processForm() = class="lift:FormSnippet.nameForm"> println(name) <input id="nameField" type="text"/> "#nameField" #> <input id="submitButton" type="submit"/> SHtml.text(name, name = _) </form> & "#submitButton" #> .. surrounding html .. SHtml.submit("Click", processForm) }}
  19. 19. Webframeworks should... Handle user input Equivalent to: (inputName: String) => name = inputName Snippet View Closure in shorthand formatclass FormSnippet { def nameForm = { .. surrounding html .. var name = "" <form method="POST" def processForm() = class="lift:FormSnippet.nameForm"> println(name) <input id="nameField" type="text"/> "#nameField" #> <input id="submitButton" type="submit"/> SHtml.text(name, name = _) </form> & "#submitButton" #> .. surrounding html .. SHtml.submit("Click", processForm) }}
  20. 20. Webframeworks should... Handle user input Combine 2 CSS transforms into single aggregated transformation Snippet View def &(other: CssSel): CssSelclass FormSnippet { def nameForm = { .. surrounding html .. var name = "" <form method="POST" def processForm() = class="lift:FormSnippet.nameForm"> println(name) <input id="nameField" type="text"/> "#nameField" #> <input id="submitButton" type="submit"/> SHtml.text(name, name = _) </form> & "#submitButton" #> .. surrounding html .. SHtml.submit("Click", processForm) }}
  21. 21. Webframeworks should... Handle user input SHtml components: powerful but low- level abstractions:LiftScreen Wizard Declarative Multipage wizards forms Backbutton Validation support Strongly typed ‘Conversations’
  22. 22. Webframeworks should...
  23. 23. Comet‘Reverse Ajax’ or ‘server push’Realtime webapps How to model this?
  24. 24. Comet... with actors! Asynchronous Mailbox serializes processing Lightweight Event-driven execution Local state Behavior mailbox
  25. 25. Comet ... with actors! Asynchronous Mailbox serializes processing Lightweight Event-driven execution Local state Send message to actor: Behavioractor ! MyMessage(“payload”) mailbox
  26. 26. Comet Chat demo setup Actor ChatServerCometActor CometActor CometActor ChatClient ChatClient ChatClient ... Browser Browser Browser ...
  27. 27. Scala + Lift =Abstraction
  28. 28. Scala + Lift = Abstraction Wiring UI:Functional/reactive programming
  29. 29. Scala + Lift = AbstractionOther abstractions: Mapper (ORM) Record (NoSQL) REST Helper (sync/async) Javascript & JSON DSL
  30. 30. Lift vs PlayPowertool vs Polished product
  31. 31. Who uses Lift?
  32. 32. Wrapping upDesigner friendly, logic free viewsConcise; leverages ScalaComet/Ajax integration second to noneMature framework with great communityRelatively steep learning curveDocumentation slowly improvingStateful, but no session replication
  33. 33. QuestionsCode @ bit.ly/jeeconf-lift branchandbound.ne @Sander_Mak

×