Top Banner
Using Play Framework 2 in production VSUG meetup 20.6.2013 Christian Papauschek [email protected]
21

Using Play Framework 2 in production

Dec 07, 2014

Download

Technology

Talk at the Vienna Scala User Group on 2013-06-20
Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.
Transcript
Page 1: Using Play Framework 2 in production

Using Play Framework 2 in production

VSUG meetup 20.6.2013

Christian Papauschek [email protected]

Page 2: Using Play Framework 2 in production
Page 3: Using Play Framework 2 in production

Technology choice

• PHP, Java, C#, …

• Easy to find developers

• Big communities, lots of existing libraries

• Scala

• Hard to find developers

• More expressive, probably more productive

• A lot more fun

Page 4: Using Play Framework 2 in production

First steps with Play 2 on Startup Live (January 2013)

• IDE: IntelliJ IDEA

• Git Repo hosted on Dropbox (yeah, I know…)

• Quickstart with Play 2 console

• Hotreload for development

• Packaged app and put it on EC2

Page 5: Using Play Framework 2 in production

What did we learn?

• Play is forgiving

• Learn it while being productive

• Adapt it to fit your needs

Page 6: Using Play Framework 2 in production

First production code

// Controller for landing pages

object Landing extends Controller {

// show main landing page

def showMain = Action {

implicit request =>

Ok(views.html.landing.main)

}

}

(conf/routes)

GET / controllers.Landing.showMain

(Landing.scala)

(main.scala.html)

[…]

Page 7: Using Play Framework 2 in production

Does it stay that simple?

Page 8: Using Play Framework 2 in production

Does it stay that simple?

Are you kidding me?

Page 9: Using Play Framework 2 in production

Serious production code (if you spot a bug, let us know :D )

SEO Authentication Caching DB Access I18n

object Landing extends Controller {

// show main landing page

def landing(language: String) = RichAction {

implicit request => Translate(language, otherLang => routes.Landing.landing(otherLang)) {

implicit lang => {

// fetch featured authors and guides

val (guides, authors) = Cache.getOrElse("landing.guides")(

DB.default withSession {

implicit session: Session => {

(GuideItems.getFiltered(GuideFilter()), RichUsers.getAuthorSample)

}

})

Ok(views.html.landing.landing(

Random.shuffle(guides),

Random.shuffle(authors)))

}

}

}

}

Page 10: Using Play Framework 2 in production
Page 11: Using Play Framework 2 in production

Play fundamentals

// Controller for landing pages

object Landing extends Controller {

// show main landing page

def showMain = Action {

implicit request =>

Ok(views.html.landing.main)

}

}

(Landing.scala)

Request: contains requested URL, parameters, Cookies, etc. Response: HTTP Response containing Status Code, HTML/JSON/etc. Action: something that takes a request, and returns a response

Page 12: Using Play Framework 2 in production

Action Composition (how we extend the Play framework for DRYness)

// represents an abstract request that may or may not be authenticated

abstract class RichRequest[A](private val request: Request[A])

extends WrappedRequest(request) {

def maybeUserSession: Option[UserSession]

}

// non-authenticated request

case class DefaultRequest[A](maybeUserSession: Option[UserSession],

private val request: Request[A])

extends RichRequest[A](request)

// represents an authenticated request

case class AuthRequest[A](userSession: UserSession,

private val request: Request[A])

extends RichRequest[A](request)

// run action with authenticated user data, or default request data

object RichAction {

def apply[A](f: RichRequest[A] => Result) =

Action { request =>

Auth.check(request) match {

case Some(authRequest) => f(authRequest)

case _ => f(DefaultRequest(None, None, request))

}

}

}

Page 13: Using Play Framework 2 in production

Birds-eye view Lots of libraries to integrate

Page 14: Using Play Framework 2 in production

Play Framework 2

Pitfalls

Page 15: Using Play Framework 2 in production

Mistake #1: CSS/less compilation

• Play uses Rhino, a library that runs JS in Java, to compile less (it‘s very slow!)

• Switched to lessc compiler for production

• Switched to less.js during development

Page 16: Using Play Framework 2 in production

Mistake #2: HTTPS using Play 2

• Don‘t use Play/netty to handle SSL

• Now using nginx as reverse proxy

Page 17: Using Play Framework 2 in production

Mistake #3: Not managing Javascript

• First we hardcoded javascript routes

Eg. In Javascript: „$http.post(´/edit/guide/save`, ...)“

• Now:

• Javascript Routes

• Javascript Translations

• Javascript minification / compilation

Page 18: Using Play Framework 2 in production

Mistake #4: Configuring play for synchronous code (Slick)

• Need to configure Play to have more threads

• Reuse of data access code

• Refactoring (where did I use this? Rename it!)

Page 19: Using Play Framework 2 in production

// filters guides which are visible on marketplace

def displayedGuides =

(for { g <- Guides if g.visible === 1 } yield g)

// return used category ids

def usedCategories(implicit session: Session) = (for {

g <- displayedGuides

cat <- GuideCategories if cat.guideId === g.id

} yield cat.categoryId).groupBy(id => id).map(g => g._1).list

• write Scala that’s compiled to SQL • keeps your database queries DRY

Page 20: Using Play Framework 2 in production

Why Play 2? Retrospective

• Readable codebase: Learn idiomatic Scala while being productive!

• Has everything you need built in, but allows you to throw everything out piece by piece as you have more advanced requirements (less compilation, templates, etc.)

• DRY

• Play is (relatively) fast. How fast? Google „TechEmpower Performance benchmarks“

Page 21: Using Play Framework 2 in production

Summary: Why Play 2?

• We know that code-bases eventually grow big. Scala helps.

• Took the good stuff from other successful frameworks such as Ruby on Rails.

„Embraces HTTP“

Adopted by Typesafe as de-facto standard web framework for Scala

• As a startup: attract people who want to learn and find better ways to develop in the web.

• Scala as a new and powerful, but stable language

• Play 2 as a bleeding edge, but amazingly stable framework

• For other languages/frameworks you might find more developers, but Scala acts as a good filter to find the good ones.