The CoffeeScript Edge

                          Presented by Trevor Burnham at Philly ETE 2012




Wednesday, April 11, 12
Who Am I?




Wednesday, April 11, 12
http://pragprog.com/book/tbcoffee/coffeescript
Wednesday, April 11, 12
“This book helps
                                          readers become better
                                          JavaScripters in the
                                          process of learning
                                          CoffeeScript. What’s
                                          more, this book is a
                                          blast to read.”
                                          —Brendan Eich



                  http://pragprog.com/book/tbcoffee/coffeescript
Wednesday, April 11, 12
Preface
             The Compleat History of JavaScript



Wednesday, April 11, 12
1995 to 2003: Ancient JavaScript




Wednesday, April 11, 12
Paul Graham on JavaScript:




Wednesday, April 11, 12
Paul Graham on JavaScript:

                                       “I would not even use
                                       Javascript, if I were
                                       you... Most of the
                                       JavaScript I see on the
                                       Web isn’t necessary,
                                       and much of it breaks.”
                                       (“The Other Road Ahead,” 2001)




Wednesday, April 11, 12
2004-2008: Medieval JavaScript




Wednesday, April 11, 12
Ajax!




Wednesday, April 11, 12
Crockford!




Wednesday, April 11, 12
Solid libraries!




Wednesday, April 11, 12
Solid libraries!




                          ...And probably others!


Wednesday, April 11, 12
2009-: Modern JavaScript




Wednesday, April 11, 12
JavaScript on the Server




Wednesday, April 11, 12
JavaScript as an
                          Embedded Scripting Language




Wednesday, April 11, 12
JavaScript is Now FAST!




Wednesday, April 11, 12
The New First Language?




                            http://www.codecademy.com/

Wednesday, April 11, 12
Everyone Who Knows JavaScript
                      Feels Like Superman!




Wednesday, April 11, 12
Wednesday, April 11, 12
“A Little Language”




Wednesday, April 11, 12
Timeline




Wednesday, April 11, 12
Timeline


                          Christmas 2009: First announced on HN




Wednesday, April 11, 12
Timeline


                          Christmas 2009: First announced on HN
                          Christmas 2010: 1.0 Released




Wednesday, April 11, 12
Timeline


                          Christmas 2009: First announced on HN
                          Christmas 2010: 1.0 Released
                          April 13, 2011:   Added to Ruby on Rails




Wednesday, April 11, 12
https://github.com/rails/rails/commit/9f09aeb8273177fc2d09ebdafcc76ee8eb56fe33

Wednesday, April 11, 12
David Heinemeier Hansson




Wednesday, April 11, 12
Ward Cunningham




Wednesday, April 11, 12
Ward Cunningham

                                 “CoffeeScript and the
                                 environment will all the
                                 powerful browsers is
                                 the closest I felt to the
                                 power I had twenty
                                 years ago in Smalltalk.”
                                 —Interview with InfoQ, November 2011




Wednesday, April 11, 12
Brendan Eich (!)




Wednesday, April 11, 12
Brendan Eich (!)



                                   CoffeeScript user




Wednesday, April 11, 12
Eich + Ashkenas at JsConf 2011




Wednesday, April 11, 12
Who uses it?




           https://github.com/jashkenas/coffee-script/wiki/In-The-Wild

Wednesday, April 11, 12
Ponder This...




                          https://github.com/languages/CoffeeScript

Wednesday, April 11, 12
I
                    CoffeeScript: A Bird’s-Eye View



Wednesday, April 11, 12
Things CoffeeScript Isn’t:




Wednesday, April 11, 12
Things CoffeeScript Isn’t:

                          Ruby/Python




Wednesday, April 11, 12
Things CoffeeScript Isn’t:

                          Ruby/Python
                          jQuery




Wednesday, April 11, 12
Things CoffeeScript Isn’t:

                          Ruby/Python
                          jQuery
                          GWT




Wednesday, April 11, 12
Things CoffeeScript Isn’t:

                          Ruby/Python
                          jQuery
                          GWT
                          Dart




Wednesday, April 11, 12
Things CoffeeScript Isn’t:

                          Ruby/Python
                          jQuery
                          GWT
                          Dart

                          alert	
  'Hello	
  World!'	
  	
  #	
  1	
  line!!!


Wednesday, April 11, 12
“It’s Just JavaScript”




Wednesday, April 11, 12
“It’s Just JavaScript”
                          a	
  =	
  b	
  	
  	
  	
  	
  #	
  var	
  a	
  =	
  b;




Wednesday, April 11, 12
“It’s Just JavaScript”
                          a	
  =	
  b	
  	
  	
  	
  	
  #	
  var	
  a	
  =	
  b;
                          x	
  is	
  y	
  	
  	
  	
  #	
  x	
  ===	
  y;




Wednesday, April 11, 12
“It’s Just JavaScript”
                          a	
  =	
  b	
  	
  	
  	
  	
  #	
  var	
  a	
  =	
  b;
                          x	
  is	
  y	
  	
  	
  	
  #	
  x	
  ===	
  y;
                          f	
  arg	
  	
  	
  	
  	
  #	
  f(arg);




Wednesday, April 11, 12
“It’s Just JavaScript”
                          a	
  =	
  b	
  	
  	
  	
  	
  #	
  var	
  a	
  =	
  b;
                          x	
  is	
  y	
  	
  	
  	
  #	
  x	
  ===	
  y;
                          f	
  arg	
  	
  	
  	
  	
  #	
  f(arg);
                          f	
  =	
  -­‐>	
  x
                          #	
  var	
  f	
  =	
  function()	
  {return	
  x;};




Wednesday, April 11, 12
“It’s Just JavaScript”
                          a	
  =	
  b	
  	
  	
  	
  	
  #	
  var	
  a	
  =	
  b;
                          x	
  is	
  y	
  	
  	
  	
  #	
  x	
  ===	
  y;
                          f	
  arg	
  	
  	
  	
  	
  #	
  f(arg);
                          f	
  =	
  -­‐>	
  x
                          #	
  var	
  f	
  =	
  function()	
  {return	
  x;};
                          No standard library. No additional types.
                          Nothing but sweet, sweet syntax!


Wednesday, April 11, 12
Ruby-isms




Wednesday, April 11, 12
Ruby-isms
                          "That	
  costs	
  $#{price}"
                          #	
  "That	
  costs	
  $"	
  +	
  price




Wednesday, April 11, 12
Streamlined Literals (I)




Wednesday, April 11, 12
Streamlined Literals (I)
                          [
                          	
  	
  "Commas?"
                          	
  	
  "We"
                          	
  	
  "don't"
                          	
  	
  "need"
                          	
  	
  "no"
                          	
  	
  "stinking"
                          	
  	
  "commmas!"
                          ]


Wednesday, April 11, 12
Streamlined Literals (II)




Wednesday, April 11, 12
Streamlined Literals (II)
                          outer:
                          	
  	
  inner:
                          	
  	
  	
  	
  "You	
  got	
  YAML	
  in	
  my	
  JSON!"
                          {outer:
                          	
  	
  {inner:
                          	
  	
  	
  	
  "You	
  got	
  YAML	
  in	
  my	
  JSON!"
                          	
  	
  }
                          }


Wednesday, April 11, 12
{key: key} Shorthand and
                          Destructuring Assignment




Wednesday, April 11, 12
{key: key} Shorthand and
                             Destructuring Assignment
                          obj	
  =	
  {x}	
  	
  #	
  obj	
  =	
  {x:	
  x};




Wednesday, April 11, 12
{key: key} Shorthand and
                             Destructuring Assignment
                          obj	
  =	
  {x}	
  	
  #	
  obj	
  =	
  {x:	
  x};
                          {x}	
  =	
  obj	
  	
  #	
  x	
  =	
  obj.x;




Wednesday, April 11, 12
{key: key} Shorthand and
                             Destructuring Assignment
                          obj	
  =	
  {x}	
  	
  #	
  obj	
  =	
  {x:	
  x};
                          {x}	
  =	
  obj	
  	
  #	
  x	
  =	
  obj.x;
                          func	
  =	
  ({x})	
  -­‐>
                          func	
  =	
  function(o)	
  {
                          	
  	
  var	
  x	
  =	
  o.x;
                          }



Wednesday, April 11, 12
More Syntactic Sugar




Wednesday, April 11, 12
More Syntactic Sugar

                          f()	
  if	
  z	
  	
  #	
  if	
  (z)	
  {	
  f();	
  }




Wednesday, April 11, 12
More Syntactic Sugar

                          f()	
  if	
  z	
  	
  #	
  if	
  (z)	
  {	
  f();	
  }
                          f?()	
  	
  	
  	
  	
  	
  #	
  if	
  (...)	
  {	
  f();	
  }




Wednesday, April 11, 12
More Syntactic Sugar

                          f()	
  if	
  z	
  	
  #	
  if	
  (z)	
  {	
  f();	
  }
                          f?()	
  	
  	
  	
  	
  	
  #	
  if	
  (...)	
  {	
  f();	
  }
                          obj?	
  	
  	
  	
  	
  	
  #	
  obj	
  !=	
  null;




Wednesday, April 11, 12
More Syntactic Sugar

                          f()	
  if	
  z	
  	
  #	
  if	
  (z)	
  {	
  f();	
  }
                          f?()	
  	
  	
  	
  	
  	
  #	
  if	
  (...)	
  {	
  f();	
  }
                          obj?	
  	
  	
  	
  	
  	
  #	
  obj	
  !=	
  null;
                          x	
  ?	
  y	
  	
  	
  	
  	
  #	
  x	
  !=	
  null	
  ?	
  x	
  :	
  y;




Wednesday, April 11, 12
More Syntactic Sugar

                          f()	
  if	
  z	
  	
  #	
  if	
  (z)	
  {	
  f();	
  }
                          f?()	
  	
  	
  	
  	
  	
  #	
  if	
  (...)	
  {	
  f();	
  }
                          obj?	
  	
  	
  	
  	
  	
  #	
  obj	
  !=	
  null;
                          x	
  ?	
  y	
  	
  	
  	
  	
  #	
  x	
  !=	
  null	
  ?	
  x	
  :	
  y;
                          Plus, significant whitespace...



Wednesday, April 11, 12
The Beauty of Indentation
                            source: https://github.com/TrevorBurnham/connect-assets




Wednesday, April 11, 12
The Beauty of Indentation
                                      source: https://github.com/TrevorBurnham/connect-assets


                          for	
  ext	
  in	
  exts
                          	
  	
  sourcePath	
  =	
  stripExt(route)	
  +	
  ".#{ext}"
                          	
  	
  try
                          	
  	
  	
  	
  stats	
  =	
  fs.statSync	
  @absPath(sourcePath)
                          	
  	
  	
  	
  if	
  ext	
  is	
  'css'
                          	
  	
  	
  	
  	
  	
  {mtime}	
  =	
  stats
                          	
  	
  	
  	
  	
  	
  if	
  timeEq	
  mtime,	
  @cache.map[route]?.mtime
                          	
  	
  	
  	
  	
  	
  	
  	
  css	
  =	
  @cache.map[route].data
                          	
  	
  	
  	
  	
  	
  else
                          	
  	
  	
  	
  	
  	
  	
  	
  css	
  =	
  fs.readFileSync	
  @absPath(sourcePath)




Wednesday, April 11, 12
The Curly-Braced Equivalent




Wednesday, April 11, 12
The Curly-Braced Equivalent
                          var	
  css,	
  ext,	
  mtime,	
  sourcePath,	
  stats,	
  _i,	
  _len,	
  _ref;
                          for	
  (_i	
  =	
  0,	
  _len	
  =	
  exts.length;	
  _i	
  <	
  _len;	
  _i++)	
  {
                          	
  	
  ext	
  =	
  exts[_i];
                          	
  	
  sourcePath	
  =	
  stripExt(route)	
  +	
  ("."	
  +	
  ext);
                          	
  	
  try	
  {
                          	
  	
  	
  	
  stats	
  =	
  fs.statSync(this.absPath(sourcePath));
                          	
  	
  	
  	
  if	
  (ext	
  ===	
  'css')	
  {
                          	
  	
  	
  	
  	
  	
  mtime	
  =	
  stats.mtime;
                          	
  	
  	
  	
  	
  	
  if	
  (timeEq(mtime,	
  (_ref	
  =	
  this.cache.map[route])	
  !=	
  
                          null	
  ?	
  _ref.mtime	
  :	
  void	
  0))	
  {
                          	
  	
  	
  	
  	
  	
  	
  	
  css	
  =	
  this.cache.map[route].data;
                          	
  	
  	
  	
  	
  	
  }	
  else	
  {
                          	
  	
  	
  	
  	
  	
  	
  	
  css	
  =	
  fs.readFileSync(this.absPath(sourcePath));
                          	
  	
  	
  	
  	
  	
  }
                          	
  	
  	
  	
  }
                          	
  	
  }	
  catch	
  (_e)	
  {}
                          }




Wednesday, April 11, 12
Wednesday, April 11, 12
II
                          Language Features



Wednesday, April 11, 12
The Wrapper




Wednesday, April 11, 12
The Wrapper
                          CoffeeScript in:
                          console.log	
  i	
  for	
  i	
  in	
  arr
                          JavaScript out:
                          (function()	
  {
                          	
  	
  var	
  i,	
  _i,	
  _len;
                          	
  	
  for	
  (_i	
  =	
  0,	
  _len	
  =	
  arr.length;	
  _i	
  <	
  _len;	
  _i++)	
  {
                          	
  	
  	
  	
  i	
  =	
  arr[_i];
                          	
  	
  	
  	
  console.log(i);
                          	
  	
  }
                          }).call(this);




Wednesday, April 11, 12
Why Use The Wrapper?
                            source: http://stackoverflow.com/questions/5211638/




Wednesday, April 11, 12
Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript




Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript
                          Conditionals




Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript
                          Conditionals
                          Parentheses




Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript
                          Conditionals
                          Parentheses
                          Objects




Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript
                          Conditionals
                          Parentheses
                          Objects
                          Loops




Wednesday, April 11, 12
Things That Don’t Create Scope
                              in JavaScript
                          Conditionals
                          Parentheses
                          Objects
                          Loops
                          Files (!)


Wednesday, April 11, 12
Wednesday, April 11, 12
Don’t Let This Happen to You!




                          http://blog.meloncard.com/post/12175941935
Wednesday, April 11, 12
CoffeeScripters Need No var!




Wednesday, April 11, 12
CoffeeScripters Need No var!

                          console.log	
  i	
  for	
  i	
  in	
  arr
                          (function()	
  {
                          	
  	
  var	
  i,	
  _i,	
  _len;
                          	
  	
  for	
  (_i	
  =	
  0,	
  _len	
  =	
  arr.length;	
  _i	
  <	
  _len;	
  _i++)	
  {
                          	
  	
  	
  	
  i	
  =	
  arr[_i];
                          	
  	
  	
  	
  console.log(i);
                          	
  	
  }
                          }).call(this);




Wednesday, April 11, 12
JS Best Practices,
                          CoffeeScript Defaults!




Wednesday, April 11, 12
JS Best Practices,
                               CoffeeScript Defaults!

                          Parappa the Wrapper




Wednesday, April 11, 12
JS Best Practices,
                               CoffeeScript Defaults!

                          Parappa the Wrapper
                          Proper Indentation




Wednesday, April 11, 12
JS Best Practices,
                               CoffeeScript Defaults!

                          Parappa the Wrapper
                          Proper Indentation
                          Avoiding ==




Wednesday, April 11, 12
JS Best Practices,
                               CoffeeScript Defaults!

                          Parappa the Wrapper
                          Proper Indentation
                          Avoiding ==
                          Packaging extensible objects as “classes”




Wednesday, April 11, 12
Plain, Ordinary JavaScript Objects




Wednesday, April 11, 12
Plain, Ordinary JavaScript Objects

                          lifeEtAl =
                            answer: 42
                            showAnswer: ->
                              console.log @answer #	
  @	
  ==	
  this




Wednesday, April 11, 12
Plain, Ordinary JavaScript Objects

                          lifeEtAl =
                            answer: 42
                            showAnswer: ->
                              console.log @answer #	
  @	
  ==	
  this

                          lifeEtAl.showAnswer()




Wednesday, April 11, 12
Plain, Ordinary JavaScript Objects

                          lifeEtAl =
                            answer: 42
                            showAnswer: ->
                              console.log @answer #	
  @	
  ==	
  this

                          lifeEtAl.showAnswer()

                          setTimeout	
  lifeEtAl.showAnswer,	
  10



Wednesday, April 11, 12
Wednesday, April 11, 12
Classes to the Rescue!




Wednesday, April 11, 12
Classes to the Rescue!

                          class LifeEtAl
                            answer: 42
                            showAnswer: => # fat ->
                              console.log @answer




Wednesday, April 11, 12
Classes to the Rescue!

                          class LifeEtAl
                            answer: 42
                            showAnswer: => # fat ->
                              console.log @answer

                          myLife = new LifeEtAl




Wednesday, April 11, 12
Classes to the Rescue!

                          class LifeEtAl
                            answer: 42
                            showAnswer: => # fat ->
                              console.log @answer

                          myLife = new LifeEtAl

                          setTimeout myLife.showAnswer, 10



Wednesday, April 11, 12
How About a Little Privacy?




Wednesday, April 11, 12
How About a Little Privacy?

                          class LifeEtAl
                            answer = 42
                            showAnswer: ->
                              console.log answer




Wednesday, April 11, 12
How About a Little Privacy?

                          class LifeEtAl
                            answer = 42
                            showAnswer: ->
                              console.log answer

                          myLife = new LifeEtAl




Wednesday, April 11, 12
How About a Little Privacy?

                          class LifeEtAl
                            answer = 42
                            showAnswer: ->
                              console.log answer

                          myLife = new LifeEtAl

                          setTimeout myLife.showAnswer, 10



Wednesday, April 11, 12
Using a Constructor




Wednesday, April 11, 12
Using a Constructor
                          class Circle
                            twoPi = Math.PI * 2
                            constructor: (@radius) ->
                              @radiusSqr = Math.pow @radius, 2
                            diameter: => twoPi * @radius
                            area: => Math.PI * @radiusSqr




Wednesday, April 11, 12
Using a Constructor
                          class Circle
                            twoPi = Math.PI * 2
                            constructor: (@radius) ->
                              @radiusSqr = Math.pow @radius, 2
                            diameter: => twoPi * @radius
                            area: => Math.PI * @radiusSqr

                          c = new Circle(5)
                          console.log c.diameter() # 31.4159
                          console.log c.area()     # 78.5398


Wednesday, April 11, 12
Let’s Try a Little Inheritance




Wednesday, April 11, 12
Let’s Try a Little Inheritance


                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'




Wednesday, April 11, 12
Doing Inheritance via a
                            JavaScript Library




Wednesday, April 11, 12
Doing Inheritance via a
                                 JavaScript Library

                          var	
  Document	
  =	
  Backbone.Model.extend({
                          	
  	
  defaults:	
  {
                          	
  	
  	
  	
  title:	
  'Untitled'
                          	
  	
  }
                          });




Wednesday, April 11, 12
Wednesday, April 11, 12
I. The Prototype Chain




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'

                          doc	
  =	
  new	
  Document




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'

                          doc	
  =	
  new	
  Document

                          Document::	
  is	
  Document.prototype




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'

                          doc	
  =	
  new	
  Document

                          Document::	
  is	
  Document.prototype

                          doc.defaults	
  is	
  Document::defaults




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'

                          doc	
  =	
  new	
  Document

                          Document::	
  is	
  Document.prototype

                          doc.defaults	
  is	
  Document::defaults

                          doc.validate	
  is	
  Backbone.Model::validate




Wednesday, April 11, 12
I. The Prototype Chain
                          class	
  Document	
  extends	
  Backbone.Model
                          	
  	
  defaults:
                          	
  	
  	
  	
  title:	
  'Untitled'

                          doc	
  =	
  new	
  Document

                          Document::	
  is	
  Document.prototype

                          doc.defaults	
  is	
  Document::defaults

                          doc.validate	
  is	
  Backbone.Model::validate

                          doc.hasOwnProperty	
  is	
  Object::hasOwnProperty



Wednesday, April 11, 12
II. Superclass Methods Can Be
                                Invoked With super




Wednesday, April 11, 12
II. Superclass Methods Can Be
                                Invoked With super
                          class	
  AppleDevice
                          	
  	
  constructor:	
  (cost)	
  -­‐>
                          	
  	
  	
  	
  bankAccount.deduct	
  cost
                          	
  	
  	
  	
  bankAccount.deduct	
  cost	
  /	
  4	
  #	
  AppleCare




Wednesday, April 11, 12
II. Superclass Methods Can Be
                                Invoked With super
                          class	
  AppleDevice
                          	
  	
  constructor:	
  (cost)	
  -­‐>
                          	
  	
  	
  	
  bankAccount.deduct	
  cost
                          	
  	
  	
  	
  bankAccount.deduct	
  cost	
  /	
  4	
  #	
  AppleCare

                          class	
  iPhone	
  extends	
  AppleDevice
                          	
  	
  constructor:	
  (cost)	
  -­‐>
                          	
  	
  	
  	
  super	
  	
  #	
  equivalent	
  to	
  super(cost)
                          	
  	
  	
  	
  setInterval	
  (-­‐>
                          	
  	
  	
  	
  	
  	
  bankAccount.deduct	
  cost	
  /	
  4
                          	
  	
  	
  	
  ),	
  ONE_MONTH




Wednesday, April 11, 12
III. Superclass Properties are Copied




Wednesday, April 11, 12
III. Superclass Properties are Copied


                          class	
  Primate
                          	
  	
  @thumbs	
  =	
  'opposable'




Wednesday, April 11, 12
III. Superclass Properties are Copied


                          class	
  Primate
                          	
  	
  @thumbs	
  =	
  'opposable'

                          class	
  Human	
  extends	
  Primate




Wednesday, April 11, 12
III. Superclass Properties are Copied


                          class	
  Primate
                          	
  	
  @thumbs	
  =	
  'opposable'

                          class	
  Human	
  extends	
  Primate

                          Human.thumbs	
  is	
  Primate.thumbs	
  is	
  'opposable'




Wednesday, April 11, 12
Wednesday, April 11, 12
III
                          Working with CoffeeScript



Wednesday, April 11, 12
Installing coffee




Wednesday, April 11, 12
Installing coffee

                          Step 1: Install Node




Wednesday, April 11, 12
Installing coffee

                          Step 1: Install Node
                          Step 2: npm	
  install	
  -­‐g	
  coffee-­‐script




Wednesday, April 11, 12
Installing coffee

                          Step 1: Install Node
                          Step 2: npm	
  install	
  -­‐g	
  coffee-­‐script
                          Want a different version?
                          npm	
  install	
  -­‐g	
  coffee-­‐script@1.2.0




Wednesday, April 11, 12
Installing coffee

                          Step 1: Install Node
                          Step 2: npm	
  install	
  -­‐g	
  coffee-­‐script
                          Want a different version?
                          npm	
  install	
  -­‐g	
  coffee-­‐script@1.2.0




Wednesday, April 11, 12
Compiling




Wednesday, April 11, 12
Compiling

                          coffee	
  -­‐w




Wednesday, April 11, 12
Compiling

                          coffee	
  -­‐w

                          Rails / other web frameworks




Wednesday, April 11, 12
Compiling

                          coffee	
  -­‐w

                          Rails / other web frameworks
                          Middleman / other static web frameworks




Wednesday, April 11, 12
Compiling

                          coffee	
  -­‐w

                          Rails / other web frameworks
                          Middleman / other static web frameworks
                          LiveReload (Mac)




Wednesday, April 11, 12
Compiling

                          coffee	
  -­‐w

                          Rails / other web frameworks
                          Middleman / other static web frameworks
                          LiveReload (Mac)
                          Write a Cakefile



Wednesday, April 11, 12
A Piece of Cake
                          source: https://github.com/sstephenson/node-coffee-project/




Wednesday, April 11, 12
A Piece of Cake
                                    source: https://github.com/sstephenson/node-coffee-project/

                          build = (watch, callback) ->
                             if typeof watch is 'function'
                               callback = watch
                               watch = false
                             options = ['-c', '-o', 'lib', 'src']
                             options.unshift '-w' if watch
                             coffee = spawn 'coffee', options
                             coffee.stdout.on 'data', (data) -> print data.toString()
                             coffee.stderr.on 'data', (data) -> print data.toString()
                             coffee.on 'exit', (status) -> callback?() if status is 0

                          task 'build', 'Compile CoffeeScript source files', ->
                            build()

                          task 'test', 'Run the test suite', ->
                            build ->
                              require.paths.unshift __dirname + "/lib"
                              {reporters} = require 'nodeunit'
                              process.chdir __dirname
                              reporters.default.run ['test']



Wednesday, April 11, 12
Wednesday, April 11, 12
Editing




              https://github.com/jashkenas/coffee-script/wiki/Text-editor-plugins
Wednesday, April 11, 12
Documenting
                          source: http://coffeescript.org/documentation/docs/grammar.html




Wednesday, April 11, 12
Testing




Wednesday, April 11, 12
Testing

                          Mocha




Wednesday, April 11, 12
Testing

                          Mocha
                          Mocha




Wednesday, April 11, 12
Testing

                          Mocha
                          Mocha
                          Mocha




Wednesday, April 11, 12
Testing

                          Mocha
                          Mocha
                          Mocha
                          http://visionmedia.github.com/mocha/




Wednesday, April 11, 12
IV
                          The Future of Web Apps...?



Wednesday, April 11, 12
A New Area of Confusion...




                             http://stackoverflow.com/questions/7996883/

Wednesday, April 11, 12
Where is Your Code?




                          http://stackoverflow.com/questions/7996883/

Wednesday, April 11, 12
Where is Your Code?




                          http://stackoverflow.com/questions/7996883/

Wednesday, April 11, 12
Breaking the Client-Server
                                 Boundaries




Wednesday, April 11, 12
Breaking the Client-Server
                                   Boundaries

                          Stitch (37signals)




Wednesday, April 11, 12
Breaking the Client-Server
                                   Boundaries

                          Stitch (37signals)
                          browserify




Wednesday, April 11, 12
Breaking the Client-Server
                                   Boundaries

                          Stitch (37signals)
                          browserify
                          jsdom




Wednesday, April 11, 12
Wednesday, April 11, 12
Wednesday, April 11, 12
Thanks! Questions?
                          Follow me @trevorburnham and @coffeescript




                             Check out my new book, Async JavaScript
                                      http://leanpub.com/asyncjs




Wednesday, April 11, 12

The CoffeeScript Edge

  • 1.
    The CoffeeScript Edge Presented by Trevor Burnham at Philly ETE 2012 Wednesday, April 11, 12
  • 2.
  • 3.
  • 4.
    “This book helps readers become better JavaScripters in the process of learning CoffeeScript. What’s more, this book is a blast to read.” —Brendan Eich http://pragprog.com/book/tbcoffee/coffeescript Wednesday, April 11, 12
  • 5.
    Preface The Compleat History of JavaScript Wednesday, April 11, 12
  • 6.
    1995 to 2003:Ancient JavaScript Wednesday, April 11, 12
  • 7.
    Paul Graham onJavaScript: Wednesday, April 11, 12
  • 8.
    Paul Graham onJavaScript: “I would not even use Javascript, if I were you... Most of the JavaScript I see on the Web isn’t necessary, and much of it breaks.” (“The Other Road Ahead,” 2001) Wednesday, April 11, 12
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
    Solid libraries! ...And probably others! Wednesday, April 11, 12
  • 14.
  • 15.
    JavaScript on theServer Wednesday, April 11, 12
  • 16.
    JavaScript as an Embedded Scripting Language Wednesday, April 11, 12
  • 17.
    JavaScript is NowFAST! Wednesday, April 11, 12
  • 18.
    The New FirstLanguage? http://www.codecademy.com/ Wednesday, April 11, 12
  • 19.
    Everyone Who KnowsJavaScript Feels Like Superman! Wednesday, April 11, 12
  • 20.
  • 21.
  • 22.
  • 23.
    Timeline Christmas 2009: First announced on HN Wednesday, April 11, 12
  • 24.
    Timeline Christmas 2009: First announced on HN Christmas 2010: 1.0 Released Wednesday, April 11, 12
  • 25.
    Timeline Christmas 2009: First announced on HN Christmas 2010: 1.0 Released April 13, 2011: Added to Ruby on Rails Wednesday, April 11, 12
  • 26.
  • 27.
  • 28.
  • 29.
    Ward Cunningham “CoffeeScript and the environment will all the powerful browsers is the closest I felt to the power I had twenty years ago in Smalltalk.” —Interview with InfoQ, November 2011 Wednesday, April 11, 12
  • 30.
  • 31.
    Brendan Eich (!) CoffeeScript user Wednesday, April 11, 12
  • 32.
    Eich + Ashkenasat JsConf 2011 Wednesday, April 11, 12
  • 33.
    Who uses it? https://github.com/jashkenas/coffee-script/wiki/In-The-Wild Wednesday, April 11, 12
  • 34.
    Ponder This... https://github.com/languages/CoffeeScript Wednesday, April 11, 12
  • 35.
    I CoffeeScript: A Bird’s-Eye View Wednesday, April 11, 12
  • 36.
  • 37.
    Things CoffeeScript Isn’t: Ruby/Python Wednesday, April 11, 12
  • 38.
    Things CoffeeScript Isn’t: Ruby/Python jQuery Wednesday, April 11, 12
  • 39.
    Things CoffeeScript Isn’t: Ruby/Python jQuery GWT Wednesday, April 11, 12
  • 40.
    Things CoffeeScript Isn’t: Ruby/Python jQuery GWT Dart Wednesday, April 11, 12
  • 41.
    Things CoffeeScript Isn’t: Ruby/Python jQuery GWT Dart alert  'Hello  World!'    #  1  line!!! Wednesday, April 11, 12
  • 42.
  • 43.
    “It’s Just JavaScript” a  =  b          #  var  a  =  b; Wednesday, April 11, 12
  • 44.
    “It’s Just JavaScript” a  =  b          #  var  a  =  b; x  is  y        #  x  ===  y; Wednesday, April 11, 12
  • 45.
    “It’s Just JavaScript” a  =  b          #  var  a  =  b; x  is  y        #  x  ===  y; f  arg          #  f(arg); Wednesday, April 11, 12
  • 46.
    “It’s Just JavaScript” a  =  b          #  var  a  =  b; x  is  y        #  x  ===  y; f  arg          #  f(arg); f  =  -­‐>  x #  var  f  =  function()  {return  x;}; Wednesday, April 11, 12
  • 47.
    “It’s Just JavaScript” a  =  b          #  var  a  =  b; x  is  y        #  x  ===  y; f  arg          #  f(arg); f  =  -­‐>  x #  var  f  =  function()  {return  x;}; No standard library. No additional types. Nothing but sweet, sweet syntax! Wednesday, April 11, 12
  • 48.
  • 49.
    Ruby-isms "That  costs  $#{price}" #  "That  costs  $"  +  price Wednesday, April 11, 12
  • 50.
  • 51.
    Streamlined Literals (I) [    "Commas?"    "We"    "don't"    "need"    "no"    "stinking"    "commmas!" ] Wednesday, April 11, 12
  • 52.
  • 53.
    Streamlined Literals (II) outer:    inner:        "You  got  YAML  in  my  JSON!" {outer:    {inner:        "You  got  YAML  in  my  JSON!"    } } Wednesday, April 11, 12
  • 54.
    {key: key} Shorthandand Destructuring Assignment Wednesday, April 11, 12
  • 55.
    {key: key} Shorthandand Destructuring Assignment obj  =  {x}    #  obj  =  {x:  x}; Wednesday, April 11, 12
  • 56.
    {key: key} Shorthandand Destructuring Assignment obj  =  {x}    #  obj  =  {x:  x}; {x}  =  obj    #  x  =  obj.x; Wednesday, April 11, 12
  • 57.
    {key: key} Shorthandand Destructuring Assignment obj  =  {x}    #  obj  =  {x:  x}; {x}  =  obj    #  x  =  obj.x; func  =  ({x})  -­‐> func  =  function(o)  {    var  x  =  o.x; } Wednesday, April 11, 12
  • 58.
  • 59.
    More Syntactic Sugar f()  if  z    #  if  (z)  {  f();  } Wednesday, April 11, 12
  • 60.
    More Syntactic Sugar f()  if  z    #  if  (z)  {  f();  } f?()            #  if  (...)  {  f();  } Wednesday, April 11, 12
  • 61.
    More Syntactic Sugar f()  if  z    #  if  (z)  {  f();  } f?()            #  if  (...)  {  f();  } obj?            #  obj  !=  null; Wednesday, April 11, 12
  • 62.
    More Syntactic Sugar f()  if  z    #  if  (z)  {  f();  } f?()            #  if  (...)  {  f();  } obj?            #  obj  !=  null; x  ?  y          #  x  !=  null  ?  x  :  y; Wednesday, April 11, 12
  • 63.
    More Syntactic Sugar f()  if  z    #  if  (z)  {  f();  } f?()            #  if  (...)  {  f();  } obj?            #  obj  !=  null; x  ?  y          #  x  !=  null  ?  x  :  y; Plus, significant whitespace... Wednesday, April 11, 12
  • 64.
    The Beauty ofIndentation source: https://github.com/TrevorBurnham/connect-assets Wednesday, April 11, 12
  • 65.
    The Beauty ofIndentation source: https://github.com/TrevorBurnham/connect-assets for  ext  in  exts    sourcePath  =  stripExt(route)  +  ".#{ext}"    try        stats  =  fs.statSync  @absPath(sourcePath)        if  ext  is  'css'            {mtime}  =  stats            if  timeEq  mtime,  @cache.map[route]?.mtime                css  =  @cache.map[route].data            else                css  =  fs.readFileSync  @absPath(sourcePath) Wednesday, April 11, 12
  • 66.
  • 67.
    The Curly-Braced Equivalent var  css,  ext,  mtime,  sourcePath,  stats,  _i,  _len,  _ref; for  (_i  =  0,  _len  =  exts.length;  _i  <  _len;  _i++)  {    ext  =  exts[_i];    sourcePath  =  stripExt(route)  +  ("."  +  ext);    try  {        stats  =  fs.statSync(this.absPath(sourcePath));        if  (ext  ===  'css')  {            mtime  =  stats.mtime;            if  (timeEq(mtime,  (_ref  =  this.cache.map[route])  !=   null  ?  _ref.mtime  :  void  0))  {                css  =  this.cache.map[route].data;            }  else  {                css  =  fs.readFileSync(this.absPath(sourcePath));            }        }    }  catch  (_e)  {} } Wednesday, April 11, 12
  • 68.
  • 69.
    II Language Features Wednesday, April 11, 12
  • 70.
  • 71.
    The Wrapper CoffeeScript in: console.log  i  for  i  in  arr JavaScript out: (function()  {    var  i,  _i,  _len;    for  (_i  =  0,  _len  =  arr.length;  _i  <  _len;  _i++)  {        i  =  arr[_i];        console.log(i);    } }).call(this); Wednesday, April 11, 12
  • 72.
    Why Use TheWrapper? source: http://stackoverflow.com/questions/5211638/ Wednesday, April 11, 12
  • 73.
  • 74.
    Things That Don’tCreate Scope in JavaScript Wednesday, April 11, 12
  • 75.
    Things That Don’tCreate Scope in JavaScript Conditionals Wednesday, April 11, 12
  • 76.
    Things That Don’tCreate Scope in JavaScript Conditionals Parentheses Wednesday, April 11, 12
  • 77.
    Things That Don’tCreate Scope in JavaScript Conditionals Parentheses Objects Wednesday, April 11, 12
  • 78.
    Things That Don’tCreate Scope in JavaScript Conditionals Parentheses Objects Loops Wednesday, April 11, 12
  • 79.
    Things That Don’tCreate Scope in JavaScript Conditionals Parentheses Objects Loops Files (!) Wednesday, April 11, 12
  • 80.
  • 81.
    Don’t Let ThisHappen to You! http://blog.meloncard.com/post/12175941935 Wednesday, April 11, 12
  • 82.
    CoffeeScripters Need Novar! Wednesday, April 11, 12
  • 83.
    CoffeeScripters Need Novar! console.log  i  for  i  in  arr (function()  {    var  i,  _i,  _len;    for  (_i  =  0,  _len  =  arr.length;  _i  <  _len;  _i++)  {        i  =  arr[_i];        console.log(i);    } }).call(this); Wednesday, April 11, 12
  • 84.
    JS Best Practices, CoffeeScript Defaults! Wednesday, April 11, 12
  • 85.
    JS Best Practices, CoffeeScript Defaults! Parappa the Wrapper Wednesday, April 11, 12
  • 86.
    JS Best Practices, CoffeeScript Defaults! Parappa the Wrapper Proper Indentation Wednesday, April 11, 12
  • 87.
    JS Best Practices, CoffeeScript Defaults! Parappa the Wrapper Proper Indentation Avoiding == Wednesday, April 11, 12
  • 88.
    JS Best Practices, CoffeeScript Defaults! Parappa the Wrapper Proper Indentation Avoiding == Packaging extensible objects as “classes” Wednesday, April 11, 12
  • 89.
    Plain, Ordinary JavaScriptObjects Wednesday, April 11, 12
  • 90.
    Plain, Ordinary JavaScriptObjects lifeEtAl = answer: 42 showAnswer: -> console.log @answer #  @  ==  this Wednesday, April 11, 12
  • 91.
    Plain, Ordinary JavaScriptObjects lifeEtAl = answer: 42 showAnswer: -> console.log @answer #  @  ==  this lifeEtAl.showAnswer() Wednesday, April 11, 12
  • 92.
    Plain, Ordinary JavaScriptObjects lifeEtAl = answer: 42 showAnswer: -> console.log @answer #  @  ==  this lifeEtAl.showAnswer() setTimeout  lifeEtAl.showAnswer,  10 Wednesday, April 11, 12
  • 93.
  • 94.
    Classes to theRescue! Wednesday, April 11, 12
  • 95.
    Classes to theRescue! class LifeEtAl answer: 42 showAnswer: => # fat -> console.log @answer Wednesday, April 11, 12
  • 96.
    Classes to theRescue! class LifeEtAl answer: 42 showAnswer: => # fat -> console.log @answer myLife = new LifeEtAl Wednesday, April 11, 12
  • 97.
    Classes to theRescue! class LifeEtAl answer: 42 showAnswer: => # fat -> console.log @answer myLife = new LifeEtAl setTimeout myLife.showAnswer, 10 Wednesday, April 11, 12
  • 98.
    How About aLittle Privacy? Wednesday, April 11, 12
  • 99.
    How About aLittle Privacy? class LifeEtAl answer = 42 showAnswer: -> console.log answer Wednesday, April 11, 12
  • 100.
    How About aLittle Privacy? class LifeEtAl answer = 42 showAnswer: -> console.log answer myLife = new LifeEtAl Wednesday, April 11, 12
  • 101.
    How About aLittle Privacy? class LifeEtAl answer = 42 showAnswer: -> console.log answer myLife = new LifeEtAl setTimeout myLife.showAnswer, 10 Wednesday, April 11, 12
  • 102.
  • 103.
    Using a Constructor class Circle twoPi = Math.PI * 2 constructor: (@radius) -> @radiusSqr = Math.pow @radius, 2 diameter: => twoPi * @radius area: => Math.PI * @radiusSqr Wednesday, April 11, 12
  • 104.
    Using a Constructor class Circle twoPi = Math.PI * 2 constructor: (@radius) -> @radiusSqr = Math.pow @radius, 2 diameter: => twoPi * @radius area: => Math.PI * @radiusSqr c = new Circle(5) console.log c.diameter() # 31.4159 console.log c.area() # 78.5398 Wednesday, April 11, 12
  • 105.
    Let’s Try aLittle Inheritance Wednesday, April 11, 12
  • 106.
    Let’s Try aLittle Inheritance class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' Wednesday, April 11, 12
  • 107.
    Doing Inheritance viaa JavaScript Library Wednesday, April 11, 12
  • 108.
    Doing Inheritance viaa JavaScript Library var  Document  =  Backbone.Model.extend({    defaults:  {        title:  'Untitled'    } }); Wednesday, April 11, 12
  • 109.
  • 110.
    I. The PrototypeChain Wednesday, April 11, 12
  • 111.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' Wednesday, April 11, 12
  • 112.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' doc  =  new  Document Wednesday, April 11, 12
  • 113.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' doc  =  new  Document Document::  is  Document.prototype Wednesday, April 11, 12
  • 114.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' doc  =  new  Document Document::  is  Document.prototype doc.defaults  is  Document::defaults Wednesday, April 11, 12
  • 115.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' doc  =  new  Document Document::  is  Document.prototype doc.defaults  is  Document::defaults doc.validate  is  Backbone.Model::validate Wednesday, April 11, 12
  • 116.
    I. The PrototypeChain class  Document  extends  Backbone.Model    defaults:        title:  'Untitled' doc  =  new  Document Document::  is  Document.prototype doc.defaults  is  Document::defaults doc.validate  is  Backbone.Model::validate doc.hasOwnProperty  is  Object::hasOwnProperty Wednesday, April 11, 12
  • 117.
    II. Superclass MethodsCan Be Invoked With super Wednesday, April 11, 12
  • 118.
    II. Superclass MethodsCan Be Invoked With super class  AppleDevice    constructor:  (cost)  -­‐>        bankAccount.deduct  cost        bankAccount.deduct  cost  /  4  #  AppleCare Wednesday, April 11, 12
  • 119.
    II. Superclass MethodsCan Be Invoked With super class  AppleDevice    constructor:  (cost)  -­‐>        bankAccount.deduct  cost        bankAccount.deduct  cost  /  4  #  AppleCare class  iPhone  extends  AppleDevice    constructor:  (cost)  -­‐>        super    #  equivalent  to  super(cost)        setInterval  (-­‐>            bankAccount.deduct  cost  /  4        ),  ONE_MONTH Wednesday, April 11, 12
  • 120.
    III. Superclass Propertiesare Copied Wednesday, April 11, 12
  • 121.
    III. Superclass Propertiesare Copied class  Primate    @thumbs  =  'opposable' Wednesday, April 11, 12
  • 122.
    III. Superclass Propertiesare Copied class  Primate    @thumbs  =  'opposable' class  Human  extends  Primate Wednesday, April 11, 12
  • 123.
    III. Superclass Propertiesare Copied class  Primate    @thumbs  =  'opposable' class  Human  extends  Primate Human.thumbs  is  Primate.thumbs  is  'opposable' Wednesday, April 11, 12
  • 124.
  • 125.
    III Working with CoffeeScript Wednesday, April 11, 12
  • 126.
  • 127.
    Installing coffee Step 1: Install Node Wednesday, April 11, 12
  • 128.
    Installing coffee Step 1: Install Node Step 2: npm  install  -­‐g  coffee-­‐script Wednesday, April 11, 12
  • 129.
    Installing coffee Step 1: Install Node Step 2: npm  install  -­‐g  coffee-­‐script Want a different version? npm  install  -­‐g  coffee-­‐script@1.2.0 Wednesday, April 11, 12
  • 130.
    Installing coffee Step 1: Install Node Step 2: npm  install  -­‐g  coffee-­‐script Want a different version? npm  install  -­‐g  coffee-­‐script@1.2.0 Wednesday, April 11, 12
  • 131.
  • 132.
    Compiling coffee  -­‐w Wednesday, April 11, 12
  • 133.
    Compiling coffee  -­‐w Rails / other web frameworks Wednesday, April 11, 12
  • 134.
    Compiling coffee  -­‐w Rails / other web frameworks Middleman / other static web frameworks Wednesday, April 11, 12
  • 135.
    Compiling coffee  -­‐w Rails / other web frameworks Middleman / other static web frameworks LiveReload (Mac) Wednesday, April 11, 12
  • 136.
    Compiling coffee  -­‐w Rails / other web frameworks Middleman / other static web frameworks LiveReload (Mac) Write a Cakefile Wednesday, April 11, 12
  • 137.
    A Piece ofCake source: https://github.com/sstephenson/node-coffee-project/ Wednesday, April 11, 12
  • 138.
    A Piece ofCake source: https://github.com/sstephenson/node-coffee-project/ build = (watch, callback) ->   if typeof watch is 'function'     callback = watch     watch = false   options = ['-c', '-o', 'lib', 'src']   options.unshift '-w' if watch   coffee = spawn 'coffee', options   coffee.stdout.on 'data', (data) -> print data.toString()   coffee.stderr.on 'data', (data) -> print data.toString()   coffee.on 'exit', (status) -> callback?() if status is 0 task 'build', 'Compile CoffeeScript source files', ->   build() task 'test', 'Run the test suite', ->   build ->     require.paths.unshift __dirname + "/lib"     {reporters} = require 'nodeunit'     process.chdir __dirname     reporters.default.run ['test'] Wednesday, April 11, 12
  • 139.
  • 140.
    Editing https://github.com/jashkenas/coffee-script/wiki/Text-editor-plugins Wednesday, April 11, 12
  • 141.
    Documenting source: http://coffeescript.org/documentation/docs/grammar.html Wednesday, April 11, 12
  • 142.
  • 143.
    Testing Mocha Wednesday, April 11, 12
  • 144.
    Testing Mocha Mocha Wednesday, April 11, 12
  • 145.
    Testing Mocha Mocha Mocha Wednesday, April 11, 12
  • 146.
    Testing Mocha Mocha Mocha http://visionmedia.github.com/mocha/ Wednesday, April 11, 12
  • 147.
    IV The Future of Web Apps...? Wednesday, April 11, 12
  • 148.
    A New Areaof Confusion... http://stackoverflow.com/questions/7996883/ Wednesday, April 11, 12
  • 149.
    Where is YourCode? http://stackoverflow.com/questions/7996883/ Wednesday, April 11, 12
  • 150.
    Where is YourCode? http://stackoverflow.com/questions/7996883/ Wednesday, April 11, 12
  • 151.
    Breaking the Client-Server Boundaries Wednesday, April 11, 12
  • 152.
    Breaking the Client-Server Boundaries Stitch (37signals) Wednesday, April 11, 12
  • 153.
    Breaking the Client-Server Boundaries Stitch (37signals) browserify Wednesday, April 11, 12
  • 154.
    Breaking the Client-Server Boundaries Stitch (37signals) browserify jsdom Wednesday, April 11, 12
  • 155.
  • 156.
  • 157.
    Thanks! Questions? Follow me @trevorburnham and @coffeescript Check out my new book, Async JavaScript http://leanpub.com/asyncjs Wednesday, April 11, 12