Lift Framework!


     Winston!
Topics!

•    Coding	
  Monk/Winston	
  
•    View	
  First	
  v.s.	
  MVC	
  
•    Version	
  Assump9ons	
  &	
  Configura9ons	
  
•    Template	
  –	
  snippet	
  &	
  value	
  binding	
  
•    Javascript	
  from	
  LiE	
  
•    Ajax	
  &	
  Coment	
  
•    Fast	
  &	
  Easy	
  API	
  
•    My	
  Love	
  &	
  Pain	
  with	
  LiE	
  

                                                             2!
Slide and Sample Project!

•  hMp://engineering.fliptop.com/2012/08/25/	
  




                                                  3!
Coding Monk/Winston!

•  Love	
  wine/Learning	
  Whiskey	
  
•  Love	
  scala/java,	
  python,	
  liE,	
  django	
  
•  Struts	
  -­‐>	
  Struts	
  2	
  -­‐>	
  Spring	
  -­‐>	
  django	
  -­‐>	
  rails	
  -­‐>	
  
   liE	
  
•  Wish	
  List:	
  big	
  data/data	
  mining/machine	
  
   learning,	
  the	
  architecture	
  and	
  algorithm	
  
•  Having	
  a	
  lot	
  of	
  fun	
  at	
  fliptop	
  



                                                                                                    4!
The problem with MVC!

•  MVC	
  Architecture	
  Graph	
  
•  Because	
  complex	
  HTML	
  pages	
  rarely	
  contain	
  a	
  
   dominant	
  piece	
  of	
  logic...	
  a	
  single	
  controller...	
  
   but	
  contain	
  many	
  different	
  components.	
  	
  
•  We	
  end	
  up	
  pu]ng	
  a	
  lot	
  of	
  logic	
  into	
  a	
  single	
  
   controller	
  and	
  view.	
  	
  




                                                                                    5!
The problem with MVC!




                        6!
A Giant Controller!




                      7!
Lift!

•  you	
  define	
  the	
  collec9on	
  of	
  components	
  to	
  be	
  
   rendered	
  in	
  the	
  resul9ng	
  HTML	
  page	
  in	
  the	
  
   view.	
  
•  Simple	
  and	
  Clear	
  




                                                                          8!
Lift!




        9!
Lift!




        10!
Assumptions!

•  Use	
  maven	
  to	
  set	
  up	
  LiE	
  
•  Use	
  XHTML	
  liE,	
  not	
  HTML5	
  liE	
  
•  HTML5	
  StyleSnippet:	
  



•  XHTML	
  Style	
  Snippet:	
  




                                                     11!
Start Up a lift project!

mvn	
  archetype:generate	
  	
  
	
  -­‐DarchetypeGroupId=net.liEweb	
  	
  
	
  -­‐DarchetypeAr9factId=liE-­‐archetype-­‐basic_2.8.1	
  	
  
	
  -­‐DarchetypeVersion=2.3	
  	
  
	
  -­‐DarchetypeRepository=hMp://scala-­‐tools.org/repo-­‐
        releases	
  	
  
	
  -­‐DremoteRepositories=hMp://scala-­‐tools.org/repo-­‐
        releases	
  	
  
	
  -­‐DgroupId=com.fliptop.liE	
  	
  
	
  -­‐Dar9factId=fliptop_rocks	
  	
  
	
  -­‐Dversion=1.0	
  
                                                                    12!
Project Structure!




                     13!
Run it!!

•  mvn	
  jeMy:run	
  
•  hMp://localhost:8080	
  

•  You	
  now	
  got	
  ProtoUser	
  Module	
  (we	
  won’t	
  
   cover	
  today)	
  with	
  AddUserMenusAEer	
  set	
  up	
  
   for	
  you.	
  
   (More	
  on	
  ProtoUser:	
  	
  
   hMp://blog.thegodcode.net/post/141132296/
   super-­‐quick-­‐start-­‐with-­‐liEs-­‐protouser)	
  

                                                                  14!
Boot.scala!

•  No	
  xml	
  configura9on!	
  Pure	
  code!!	
  

•  LiERules	
  
•  DB,	
  Proper9es	
  and	
  Run	
  modes	
  
•  SiteMap:	
  
   –  Menu	
  
   –  Access	
  Control	
  



                                                     15!
Create a page!

•  Set	
  up	
  a	
  path	
  in	
  Boot.scala	
  
•  Create	
  an	
  HTML	
  page	
  in	
  webapp	
  or	
  a	
  view	
  
   class	
  in	
  class	
  folder.	
  
•  Fill	
  in	
  the	
  snippets	
  if	
  using	
  HTML	
  pages.	
  

•  Request	
  Rou9ng:	
  
    –  Template	
  -­‐>	
  View	
  
    –  We	
  are	
  using	
  Template,	
  not	
  view	
  


                                                                         16!
Snippet 101!

•  snippet101.html	
  
   <liE:surround	
  with="default"	
  at="content”>	
  
   	
   	
  <liE:SnippetExp.snipprt101/>	
  
   </liE:surround>	
  
•  SnippetExp.scala	
  
   class	
  SnippetExp	
  {	
  
   	
   	
  def	
  snipprt101:NodeSeq	
  =	
  	
  
   	
   	
   	
  <div>This	
  is	
  a	
  very	
  bad	
  prac9ce!!</div>	
  
   }	
  

                                                                              17!
Bad Practice!

•  A	
  lot	
  of	
  HTML	
  in	
  a	
  snippet	
  code	
  
   class	
  SnippetExp	
  {	
  
    	
   	
  def	
  thisIsBad:NodeSeq	
  =	
  {	
  
    	
   	
   	
  val	
  goodCode	
  =	
  false	
  
    	
   	
   	
  val	
  badCode	
  =	
  if(goodCode)	
  “not	
  at	
  all”	
  
   	
   	
   	
  else	
  “bad	
  prac9ce,	
  HTML	
  in	
  snippet!!”	
  
    	
   	
   	
  <div>{badCode}</div>	
  
    	
   	
  }	
  
   }	
  

                                                                                  18!
Complex Snippet: data binding!

•  simple_form.html	
  
   <liE:surround	
  with="default"	
  at="content”>	
  
   	
  <liE:SnippetExp.bindingExample	
  
   form="POST”>	
  
   	
   	
  <p>Do	
  Something	
  with	
  your	
  email:</p>	
  
   	
   	
  <p><entry:email/></p>	
  
   	
   	
  <p><entry:submit/></p>	
  
   	
  </liE:SnippetExp.bindingExample>	
  
   </liE:surround>	
  

                                                                   19!
A Simple Form Snippet!

def	
  bindingExample(xhtml:NodeSeq):NodeSeq	
  =	
  {	
  
      	
  var	
  email	
  =	
  ""	
  
      	
  def	
  process	
  (){	
  
      	
   	
  print("The	
  email	
  is:	
  "	
  +	
  email)	
  
      	
  }	
  
      	
  bind("entry",	
  xhtml,	
  
      	
  	
  “email”	
  -­‐>	
  SHtml.text(email,	
  email	
  =	
  _,	
  
           	
  "id”>"email"),	
  
      	
  	
  	
  "submit"	
  -­‐>	
  SHtml.submit("search",	
  process))	
  
}	
  
                                                                                20!
Recursive Binding!

•  Rendering	
  a	
  list	
  or	
  a	
  table	
  
•  recursive_binding.html	
  
<liE:SnippetExp.recursiveBinding>	
  
   	
  <table>	
  
   	
  	
  	
   	
  <entry:lis9tem>	
  
   	
  	
  	
  	
  	
  <tr>	
  
   	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  <td><item:name/></td><td><item:email/></td>	
  
   	
  	
  	
  	
  	
  </tr>	
  
   	
   	
  </entry:lis9tem>	
  
   	
  </table>	
  
</liE:SnippetExp.recursiveBinding>	
  
                                                                                             21!
Recursive Binding!

def	
  recursiveBinding(xhtml:NodeSeq):NodeSeq	
  =	
  {	
  
              	
  val	
  theList	
  =	
  new	
  ListBuffer[(String,	
  String)]	
  
              	
  theList	
  +=	
  new	
  Tuple2("robbie@fliptop.com",	
  "Robbie	
  Cheng")	
  
              	
  theList	
  +=	
  new	
  Tuple2("winston@fliptop.com",	
  "Winston	
  Chen")	
  
              	
  bind("entry",	
  xhtml,	
  "lis9tem"	
  -­‐>	
  theList.toList.flatMap(	
  
              	
   	
   	
  item	
  =>	
  {	
  
              	
   	
   	
        	
  bind("item",	
  chooseTemplate("entry","lis9tem",	
  xhtml),	
  	
  
              	
   	
   	
        	
        	
  "email"	
  -­‐>	
  item._1,	
  
              	
   	
   	
        	
        	
  "name"	
  -­‐>	
  item._2	
  
              	
   	
   	
        	
  )	
  
              	
   	
   	
  }	
  
              	
   	
  )	
  
              	
  )	
  
	
  	
  }	
  
                                                                                                             22!
Javascript Integration!

•    Javascript	
  expressions	
  and	
  statements	
  
•    Javascript	
  forms	
  
•    Ajax	
  
•    Comet	
  (Long	
  pulling)	
  




                                                          23!
Javascript Expressions/Statements!

•  The	
  magic	
  Call	
  func9on	
  
<script>	
  
func9on	
  this_is_an_alert_triggered_by_liE_call(){	
  
      	
  alert("This	
  is	
  an	
  alert	
  triggered	
  by	
  liE	
  call()!!")	
  
}	
  
</script>	
  
<liE:JsSnippetExp.call>	
  
<input	
  id="buMon"	
  type="buMon"	
  value="Click	
  me"	
  />	
  
</liE:JsSnippetExp.call>	
  
Snippet:	
  
def	
  call	
  =	
  	
  
      	
  	
  	
  "#buMon	
  [onclick]"	
  #>	
  JE.Call
          ("this_is_an_alert_triggered_by_liE_call",	
  "").toJsCmd	
  
                                                                                         24!
Json Forms!

•  Let’s	
  look	
  at	
  the	
  code	
  directly:	
  JsSnippetExp	
  




                                                                         25!
Ajax!

•  Template:	
  
<liE:JsSnippetExp.ajaxBuMon>	
  
   	
  <item:buMon/>	
  
</liE:JsSnippetExp.ajaxBuMon>	
  
<div	
  id="ajaxb"></div>	
  
•  Snippet:	
  
def	
  updateText	
  =	
  SetHtml("ajaxb",	
  Text("Fliptop	
  is	
  a	
  great	
  
       company!!"))	
  
def	
  ajaxBuMon(xhtml:NodeSeq):NodeSeq	
  =	
  bind("item",	
  
       xhtml,	
  "buMon"	
  -­‐>	
  SHtml.ajaxBuMon(Text("Press	
  me"),	
  
       ()=>updateText))	
  
                                                                                      26!
Comet!


Ajax!
Comet!


Comet!
Comet!

•    Lift: Long Pulling!
•    Must put comets in comet folder.!
•    Extend CometActor!
•    Use tag: <lift:comet>  !

•  Letʼs look at the code: CometExp.scala!
•  Reference:

   exploring.liftweb.net/master/index-11.html!

                                                 29!
REST API So Easy!

•  Use	
  RestHelper	
  to	
  write	
  up	
  the	
  code.	
  
•  Configure	
  it	
  on	
  Boot.scala	
  

•  Let’s	
  look	
  at	
  Rest.scala	
  
•  Here	
  you	
  go!!	
  It’s	
  that	
  easy.	
  
•  Reference:	
  simply.liEweb.net/index-­‐
   Chapter-­‐11.html	
  


                                                                30!
Conclusions!

•  LiE	
  tackles	
  Web	
  from	
  a	
  view-­‐first	
  perspec9ve.	
  
•  LiE	
  gives	
  you	
  js/ajax/comet	
  for	
  free.	
  
•  LiE	
  also	
  gives	
  you	
  rest	
  API	
  for	
  free.	
  



•  All	
  feature	
  goes	
  to	
  backend,	
  designs	
  frontend.	
  
•  No	
  more	
  plumbing	
  yourself.	
  


                                                                          31!
Why I love Lift!

•  Get	
  all	
  the	
  feature	
  done	
  at	
  backend	
  
•  The	
  Snippet	
  logic	
  makes	
  much	
  more	
  sense	
  
   than	
  MVC	
  for	
  me.	
  (although	
  I	
  love	
  django	
  too)	
  
•  API	
  so	
  easy,	
  no	
  much	
  code	
  needed	
  




                                                                               32!
Why I hate Lift!

•  It’s	
  really	
  hard	
  to	
  get	
  HTML/XML	
  out	
  of	
  snippet	
  
   code.	
  
•  Learning	
  curve	
  is	
  s9ff	
  if	
  you	
  are	
  not	
  used	
  to	
  its	
  
   logic.	
  
•  Try	
  s9ck	
  to	
  the	
  latest	
  version.	
  
•  Too	
  many	
  ways	
  to	
  write	
  it.	
  




                                                                                        33!
Free Books!

•  Exploring	
  LiE:	
  exploring.liEweb.net	
  
•  Simply	
  LiE:	
  simply.liEweb.net	
  
•  LiE	
  Cookbook:	
  cookbook.liEweb.net	
  




                                                   34!
References!

•  David	
  Pollak	
  On	
  LiE	
  Framework	
  and	
  Scala	
  
   www.infoq.com/interviews/LiE-­‐Scala-­‐David-­‐
   Pollak	
  
•  Example	
  &	
  Demo	
  Site:	
  demo.liEweb.net	
  
•  Start	
  Up	
  Project	
  with	
  Maven:	
  
   www.assembla.com/wiki/show/liEweb/
   Using_Maven	
  



                                                                   35!
Get to me!

•  Email:	
  wisnton@fliptop.com	
  
•  URLs:	
  
   –  hMp://www.repfans.com/profile/33335/Winston
      %20Chen	
  
   –  hMp://careers.stackoverflow.com/wingchen	
  




                                                    36!
The last Q&A!


    Winston!
Model!

•  Mapper	
  or	
  Record	
  

•  Take	
  a	
  look	
  at	
  here:	
  
   stackoverflow.com/ques9ons/6564332/when-­‐
   to-­‐use-­‐mapper-­‐or-­‐record-­‐in-­‐liE	
  




                                                    38!
Menu Configurations!

•  stackoverflow.com/ques9ons/2175246/
   liEweb-­‐menu-­‐customiza9on	
  




                                        39!
Thank you.!

Lift talk

  • 1.
  • 2.
    Topics! •  Coding  Monk/Winston   •  View  First  v.s.  MVC   •  Version  Assump9ons  &  Configura9ons   •  Template  –  snippet  &  value  binding   •  Javascript  from  LiE   •  Ajax  &  Coment   •  Fast  &  Easy  API   •  My  Love  &  Pain  with  LiE   2!
  • 3.
    Slide and SampleProject! •  hMp://engineering.fliptop.com/2012/08/25/   3!
  • 4.
    Coding Monk/Winston! •  Love  wine/Learning  Whiskey   •  Love  scala/java,  python,  liE,  django   •  Struts  -­‐>  Struts  2  -­‐>  Spring  -­‐>  django  -­‐>  rails  -­‐>   liE   •  Wish  List:  big  data/data  mining/machine   learning,  the  architecture  and  algorithm   •  Having  a  lot  of  fun  at  fliptop   4!
  • 5.
    The problem withMVC! •  MVC  Architecture  Graph   •  Because  complex  HTML  pages  rarely  contain  a   dominant  piece  of  logic...  a  single  controller...   but  contain  many  different  components.     •  We  end  up  pu]ng  a  lot  of  logic  into  a  single   controller  and  view.     5!
  • 6.
  • 7.
  • 8.
    Lift! •  you  define  the  collec9on  of  components  to  be   rendered  in  the  resul9ng  HTML  page  in  the   view.   •  Simple  and  Clear   8!
  • 9.
  • 10.
    Lift! 10!
  • 11.
    Assumptions! •  Use  maven  to  set  up  LiE   •  Use  XHTML  liE,  not  HTML5  liE   •  HTML5  StyleSnippet:   •  XHTML  Style  Snippet:   11!
  • 12.
    Start Up alift project! mvn  archetype:generate      -­‐DarchetypeGroupId=net.liEweb      -­‐DarchetypeAr9factId=liE-­‐archetype-­‐basic_2.8.1      -­‐DarchetypeVersion=2.3      -­‐DarchetypeRepository=hMp://scala-­‐tools.org/repo-­‐ releases      -­‐DremoteRepositories=hMp://scala-­‐tools.org/repo-­‐ releases      -­‐DgroupId=com.fliptop.liE      -­‐Dar9factId=fliptop_rocks      -­‐Dversion=1.0   12!
  • 13.
  • 14.
    Run it!! •  mvn  jeMy:run   •  hMp://localhost:8080   •  You  now  got  ProtoUser  Module  (we  won’t   cover  today)  with  AddUserMenusAEer  set  up   for  you.   (More  on  ProtoUser:     hMp://blog.thegodcode.net/post/141132296/ super-­‐quick-­‐start-­‐with-­‐liEs-­‐protouser)   14!
  • 15.
    Boot.scala! •  No  xml  configura9on!  Pure  code!!   •  LiERules   •  DB,  Proper9es  and  Run  modes   •  SiteMap:   –  Menu   –  Access  Control   15!
  • 16.
    Create a page! • Set  up  a  path  in  Boot.scala   •  Create  an  HTML  page  in  webapp  or  a  view   class  in  class  folder.   •  Fill  in  the  snippets  if  using  HTML  pages.   •  Request  Rou9ng:   –  Template  -­‐>  View   –  We  are  using  Template,  not  view   16!
  • 17.
    Snippet 101! •  snippet101.html   <liE:surround  with="default"  at="content”>      <liE:SnippetExp.snipprt101/>   </liE:surround>   •  SnippetExp.scala   class  SnippetExp  {      def  snipprt101:NodeSeq  =          <div>This  is  a  very  bad  prac9ce!!</div>   }   17!
  • 18.
    Bad Practice! •  A  lot  of  HTML  in  a  snippet  code   class  SnippetExp  {      def  thisIsBad:NodeSeq  =  {        val  goodCode  =  false        val  badCode  =  if(goodCode)  “not  at  all”        else  “bad  prac9ce,  HTML  in  snippet!!”        <div>{badCode}</div>      }   }   18!
  • 19.
    Complex Snippet: databinding! •  simple_form.html   <liE:surround  with="default"  at="content”>    <liE:SnippetExp.bindingExample   form="POST”>      <p>Do  Something  with  your  email:</p>      <p><entry:email/></p>      <p><entry:submit/></p>    </liE:SnippetExp.bindingExample>   </liE:surround>   19!
  • 20.
    A Simple FormSnippet! def  bindingExample(xhtml:NodeSeq):NodeSeq  =  {    var  email  =  ""    def  process  (){      print("The  email  is:  "  +  email)    }    bind("entry",  xhtml,      “email”  -­‐>  SHtml.text(email,  email  =  _,    "id”>"email"),        "submit"  -­‐>  SHtml.submit("search",  process))   }   20!
  • 21.
    Recursive Binding! •  Rendering  a  list  or  a  table   •  recursive_binding.html   <liE:SnippetExp.recursiveBinding>    <table>          <entry:lis9tem>            <tr>                      <td><item:name/></td><td><item:email/></td>            </tr>      </entry:lis9tem>    </table>   </liE:SnippetExp.recursiveBinding>   21!
  • 22.
    Recursive Binding! def  recursiveBinding(xhtml:NodeSeq):NodeSeq  =  {    val  theList  =  new  ListBuffer[(String,  String)]    theList  +=  new  Tuple2("robbie@fliptop.com",  "Robbie  Cheng")    theList  +=  new  Tuple2("winston@fliptop.com",  "Winston  Chen")    bind("entry",  xhtml,  "lis9tem"  -­‐>  theList.toList.flatMap(        item  =>  {          bind("item",  chooseTemplate("entry","lis9tem",  xhtml),              "email"  -­‐>  item._1,            "name"  -­‐>  item._2          )        }      )    )      }   22!
  • 23.
    Javascript Integration! •  Javascript  expressions  and  statements   •  Javascript  forms   •  Ajax   •  Comet  (Long  pulling)   23!
  • 24.
    Javascript Expressions/Statements! •  The  magic  Call  func9on   <script>   func9on  this_is_an_alert_triggered_by_liE_call(){    alert("This  is  an  alert  triggered  by  liE  call()!!")   }   </script>   <liE:JsSnippetExp.call>   <input  id="buMon"  type="buMon"  value="Click  me"  />   </liE:JsSnippetExp.call>   Snippet:   def  call  =          "#buMon  [onclick]"  #>  JE.Call ("this_is_an_alert_triggered_by_liE_call",  "").toJsCmd   24!
  • 25.
    Json Forms! •  Let’s  look  at  the  code  directly:  JsSnippetExp   25!
  • 26.
    Ajax! •  Template:   <liE:JsSnippetExp.ajaxBuMon>    <item:buMon/>   </liE:JsSnippetExp.ajaxBuMon>   <div  id="ajaxb"></div>   •  Snippet:   def  updateText  =  SetHtml("ajaxb",  Text("Fliptop  is  a  great   company!!"))   def  ajaxBuMon(xhtml:NodeSeq):NodeSeq  =  bind("item",   xhtml,  "buMon"  -­‐>  SHtml.ajaxBuMon(Text("Press  me"),   ()=>updateText))   26!
  • 27.
  • 28.
  • 29.
    Comet! •  Lift: Long Pulling! •  Must put comets in comet folder.! •  Extend CometActor! •  Use tag: <lift:comet>  ! •  Letʼs look at the code: CometExp.scala! •  Reference:
 exploring.liftweb.net/master/index-11.html! 29!
  • 30.
    REST API SoEasy! •  Use  RestHelper  to  write  up  the  code.   •  Configure  it  on  Boot.scala   •  Let’s  look  at  Rest.scala   •  Here  you  go!!  It’s  that  easy.   •  Reference:  simply.liEweb.net/index-­‐ Chapter-­‐11.html   30!
  • 31.
    Conclusions! •  LiE  tackles  Web  from  a  view-­‐first  perspec9ve.   •  LiE  gives  you  js/ajax/comet  for  free.   •  LiE  also  gives  you  rest  API  for  free.   •  All  feature  goes  to  backend,  designs  frontend.   •  No  more  plumbing  yourself.   31!
  • 32.
    Why I loveLift! •  Get  all  the  feature  done  at  backend   •  The  Snippet  logic  makes  much  more  sense   than  MVC  for  me.  (although  I  love  django  too)   •  API  so  easy,  no  much  code  needed   32!
  • 33.
    Why I hateLift! •  It’s  really  hard  to  get  HTML/XML  out  of  snippet   code.   •  Learning  curve  is  s9ff  if  you  are  not  used  to  its   logic.   •  Try  s9ck  to  the  latest  version.   •  Too  many  ways  to  write  it.   33!
  • 34.
    Free Books! •  Exploring  LiE:  exploring.liEweb.net   •  Simply  LiE:  simply.liEweb.net   •  LiE  Cookbook:  cookbook.liEweb.net   34!
  • 35.
    References! •  David  Pollak  On  LiE  Framework  and  Scala   www.infoq.com/interviews/LiE-­‐Scala-­‐David-­‐ Pollak   •  Example  &  Demo  Site:  demo.liEweb.net   •  Start  Up  Project  with  Maven:   www.assembla.com/wiki/show/liEweb/ Using_Maven   35!
  • 36.
    Get to me! • Email:  wisnton@fliptop.com   •  URLs:   –  hMp://www.repfans.com/profile/33335/Winston %20Chen   –  hMp://careers.stackoverflow.com/wingchen   36!
  • 37.
  • 38.
    Model! •  Mapper  or  Record   •  Take  a  look  at  here:   stackoverflow.com/ques9ons/6564332/when-­‐ to-­‐use-­‐mapper-­‐or-­‐record-­‐in-­‐liE   38!
  • 39.
  • 40.