60
JAVASCRIPT FUNDAMENTALS FOR PHP DEVELOPERS @chrisramakers November 2013 PHPBenelux Usergroup Meeting

Javascript fundamentals for php developers

Embed Size (px)

DESCRIPTION

Javascript fundamentals from a PHP developers' point of view. Compares some of the principles of javascript with their php counterpart. Introduces a way to build simple robust modules in Javascript. You can view the source of the slides (html+js) here: https://bitbucket.org/chrisramakers/talk-javascript-for-php-developers

Citation preview

Page 1: Javascript fundamentals for php developers

JAVASCRIPT FUNDAMENTALSFOR PHP DEVELOPERS

@chrisramakersNovember 2013 PHPBenelux Usergroup Meeting

Page 2: Javascript fundamentals for php developers

WHO AM I?@chrisramakersZend Certified PHP EngineerSoftware Engineer @ NucleusFront- and backend developmentBuilding RESTFUL API'sIntegrating them with AngularJS

Page 3: Javascript fundamentals for php developers

WHAT ABOUT YOU?Never used JavascriptIntermediate JavascriptJavascript expert

Page 4: Javascript fundamentals for php developers

WHAT IS THIS TALK ABOUT?I can hear you "I know Javascript! Booooring!"

I'm not a guru either but I have a lot of experience.So I'm going to share some of it with you.

HistoryJavascript BootcampWriting modulesWhat will the future bring?

Page 5: Javascript fundamentals for php developers

JAVASCRIPT HISTORY

Page 6: Javascript fundamentals for php developers

JAVASCRIPT HISTORYInterpreted scripting languageObject oriented but not Class basedMost popular language on GithubDeveloped at Netscape in 1995Around the same time as PHP (1997)First called LiveScript, then renamed JavascriptStandardised as ECMAScript (ECMA-262) in 1997Other implementations

Serverside: Netscape Enterprise Server, Node.JS,Databases: CouchDB, MongoDB, Riak, ...CoffeescriptAdobe: ExtendScript, Actionscript,

Page 7: Javascript fundamentals for php developers

IT'S EVEN A POWERPOINT REPLACEMENT!These slides are built with reveal.js

Check it out: lab.hakim.se/reveal-js

Page 8: Javascript fundamentals for php developers

WE KNEW JAVASCRIPT LIKE THIS

Note: This is a screenshot, not a real error!!! :D

Page 9: Javascript fundamentals for php developers

AND THIS

Page 10: Javascript fundamentals for php developers

SIGH

Page 11: Javascript fundamentals for php developers

BUT WE COULD DO STUFF LIKE THIS TOOfunction trollolololl() { window.open(self.location, '');}window.onload = trollolololl;

And feel like a real hacker :)note: this no longer works

Page 12: Javascript fundamentals for php developers

HOW WE KNOW JAVASCRIPTA lot has changed, there are many high quality libraries and tools available.

But we are not going to talk about that ...

Page 13: Javascript fundamentals for php developers

JAVASCRIPT BOOTCAMP!

Page 14: Javascript fundamentals for php developers

OPERATORSTHE BASIC BUNCH

Assignment operators = += -= *= ...Arithmic operators + - / *Bitwise operators >> << & ̂ | ~Comparison operators == != === !== > >= < <=Logical operators || && !

Look familiar no?

Page 15: Javascript fundamentals for php developers

OPERATORS CONTINUED ...concatoperator +

concatenates 2 strings

in -operator determines if the left operant is a property of the rightoperant

delete removes a property from an object

typeof returns the data type of an object

instanceof determines of the left operant is of the the right operantobject type

And more like new, this, ...Again most of these should look familiar.

Page 16: Javascript fundamentals for php developers

DATA TYPES PHP JavascriptPrimitives string

integerfloatboolean

StringNumberBoolean

Compound arrayobject

ArrayObject

Special resourcenull

undefinednull

Page 17: Javascript fundamentals for php developers

THE GLOBAL OBJECTSomething like $GLOBALS inphpAccessible everywherewindow-object in browsers

Page 18: Javascript fundamentals for php developers

3 GLOBAL PROPERTIESNaNInfinityundefined

Page 19: Javascript fundamentals for php developers

9 GLOBAL FUNCTIONSJavascript PHPparseInt() intval()parseFloat() floatval()isNaN() is_nan()isFinite() is_finite()encodeURIComponent() urlencode()decodeURIComponent() urldecode()encodeURI() ??decodeURI() ??eval() eval()

Page 20: Javascript fundamentals for php developers

9 GLOBAL CONSTRUCTORSNot the same as constructors in PHP

String()Number()Boolean()Array()Object()Error()RegExp()Date()Function()

Page 21: Javascript fundamentals for php developers

IMMUTABLEAll constructors are immutable Objects

String.prototype.append = function(val){ this = this + val;}

var a = 'Foo';var b = a.append('Bar');

ReferenceError: Invalid left-hand side in assignment

Page 22: Javascript fundamentals for php developers

LITERALS AND CONSTRUCTORSWe don't need constructors ... we got literals!

Literal Constructor

String "Nucleus" new String("Nucleus");

Boolean true new Boolean(true);

Array ['a', 'a']; new Array('a', 'b');

Objects { a : 'b' } new Object();

Number 1.23; new Number(1.23);

RegExp /[A-Z]/i; new RegExp('[A-Z]', 'i');

Function function(x){ return x+1; }; new Function('x', 'return x+1;');

Date There is no Date literal new Date(2013, 11, 23);

Page 23: Javascript fundamentals for php developers

RELATION BETWEEN LITERALS AND CONSTRUCTORSvar a = "foobar";var b = a.toUpperCase();alert(b); // Alerts "FOOBAR"

Constructors wrap literals internallyJavascript internally converts primitives to their object counterpartCauses some really funky behaviour!WTFPM++

Page 24: Javascript fundamentals for php developers

AND NOW THE "FUN" BEGINS ...TYPEOF

typeof 'foo'; // "string"

typeof String; // "function"

typeof String(); // "string"

var s = new String('foo');typeof s // "object"

Page 25: Javascript fundamentals for php developers

INSTANCEOFvar foo = new String('foo');var bar = 'bar';

foo instanceof String; // truebar instanceof String; // false

Wait ... it gets better :)

var boys = new Array('Joe', 'Bob');var girls = ['Jane', 'Alice'];

boys instanceof Array; // truegirls instanceof Array; // true

instanceof on navite data types is not reliable!use jQuery.type(), angular.isString(), ...

Page 26: Javascript fundamentals for php developers

ERRORS AND ERROR HANDLINGPHP Javascript

try { ... } catch(e) { ... } try { ... } catch(e) { ... }

throw new Exception(msg, code); throw 'Something went wrong!';

throw 500;

throw 'up';

throw {message: 'foo', code: 500};

throw new Error('up');

Page 27: Javascript fundamentals for php developers

SCOPEScope refers to where a variable or functions are accessible

and in what context they are being manipulated.

There 2 types of scope

GlobalLocal

Page 28: Javascript fundamentals for php developers

Basically it means it's attached to the window object which is the topmostobject.

GLOBAL SCOPEWhen something is in the global scope

it means that it is accessible from anywhere in your code.

var foo = "Nucleus";function bar(){ alert(foo);}

bar(); // alerts 'Nucleus'alert(foo) // also alerts 'Nucleus'alert(window.foo) // again alerts 'Nucleus'

Page 29: Javascript fundamentals for php developers

LOCAL SCOPEWhen something is in the local scope it means it's only available in the

containing function and all functions defined at the same level or deeper.

function bar(){ var foo = "Nucleus"; alert(foo);}

bar(); // alerts 'Nucleus'alert(foo) // error: foo is not definedalert(window.foo) // error: foo is not defined

Page 30: Javascript fundamentals for php developers

CLOSURESA closure is an expression (typically a function) that can have

variables together with an environment that binds those variables(that "closes" the expression).

Page 31: Javascript fundamentals for php developers

PHP CLOSURESIn PHP closures are most commonly called 'anonymous functions' and are

implemented using the Closure class.

// PHP Closure$foo = function() { return 'Nucleus';};echo $foo(); // outputs 'Nucleus'echo get_class($foo); // outputs 'Closure'

Page 32: Javascript fundamentals for php developers

PHP CLOSURES AND SCOPE$foo = 'Nucleus';$bar = function() { return $foo;};echo $bar(); // PHP Notice: Undefined variable $foo

We need the 'use' construct.

$foo = 'Nucleus';$bar = function() use ($foo) { // added 'use' construct return $foo;};echo $foo(); // Outputs 'Nucleus'

Page 33: Javascript fundamentals for php developers

JAVASCRIPT CLOSURESWhenever you see a function, wrapped within another function, a closure is

created and the inner function has access to all variables defined in the outerfunction.

Page 34: Javascript fundamentals for php developers

JAVASCRIPT CLOSURES

Outside the greet() function, there is no way to access the prefixvariable.

Only functions defined within the greet() function have access to thisvariable, same goes for the who argument which is also contained within the

closure.

// outer functionfunction greet(who) { var prefix = 'Welcome at '; // Inner function function output(suffix) { alert(prefix + who + suffix); }; output('!');}greet('Nucleus'); // Alerts 'Welcome at Nucleus!'

Page 35: Javascript fundamentals for php developers

CLOSURES IN JAVASCRIPTNow we can modify the code to return the inner function.

function greet(who) { var prefix = 'Hello '; var f = function(suffix) { alert(prefix + who + suffix); }; return f;}var joeGreeter = greet('joe');joeGreeter('?'); // Alerts 'Hello joe?'joeGreeter.prefix; // undefined

This way we receive an executable function from the greet() call, but we still have no way to modify the value of prefix.

Looks a lot like private variables in PHP

Page 36: Javascript fundamentals for php developers

CLOSURES IN JAVASCRIPTLets add an accessor and mutator (getter and setter).

function greet(who) { var prefix = 'Hello '; var f = function(suffix) { alert(prefix + who + suffix); }; f.setPrefix = function(p){ prefix = p; } f.getPrefix = function(){ return prefix; } return f;}var joeGreeter = greet('joe');joeGreeter('?'); // Alerts 'Hello joe?'

joeGreeter.setPrefix('Hey '); // joe is deaf ...joeGreeter('!!!'); // Alerts 'Hey joe!!!'

Page 37: Javascript fundamentals for php developers

SELF EXECUTING FUNCTION PATTERN(function() { // ...}());

Also called IIFE or Immediately Invoked Function ExpressionCreates it's own isolated scope without polluting the global scope.Allows us to 'import' variables into the closure without addressing themglobally

(function($, Y) { // ...}(jQuery, YAHOO));

Page 38: Javascript fundamentals for php developers

WRITING JAVASCRIPT MODULESLets do something usefull with it now ...

Javascript doesn't know the concept classes (yet)Nor does it have private/public access to propertiesHow do we build a robust module in javascript then?

Page 39: Javascript fundamentals for php developers

HELLO DESIGN PATTERNS!Self Executing Function patternModule pattern

LETS BUILD A SIMPLE MODULE

Page 40: Javascript fundamentals for php developers

var COUNTER = (function(){ }());

We start with a self-executingfunction to create an isolate scope.

console.log(COUNTER); // undefined

Page 41: Javascript fundamentals for php developers

var COUNTER = (function(){ var _counter = 0; var public = {}; return public;}());

BUILDING A MODULENow we have to actually return

something from our self-executingfunction so COUNTER is not

undefined

console.log(COUNTER); // Object {}

Page 42: Javascript fundamentals for php developers

var COUNTER = (function(){ var _counter = 0; var public = { increment : function(){ _counter++; }, getValue : function(){ return _counter; } }; return public;}());

BUILDING A MODULEIf we now add some functions topublic, we create a closure inside

the self-executing function.

console.log(COUNTER.geValue()); // 0 COUNTER.increment();console.log(COUNTER.geValue()); // 1console.log(COUNTER._counter); // undefined

Page 43: Javascript fundamentals for php developers

var COUNTER = (function(){ var _counter = 0; var format = function(value){ return 'Counter is ' + value; } var public = { increment : function(){ _counter++; }, getValue : function(){ return format(_counter); } }; return public;}());

BUILDING A MODULENow lets add a "private" method to

format the output a little

COUNTER.increment();COUNTER.increment();

console.log(COUNTER.geValue()); // Counter is 2

Page 44: Javascript fundamentals for php developers

var COUNTER = (function(){ var _counter = 0; var _format = 'Counter is '; var format = function(value){ return _format + value; } var public = { increment : function(){ _counter++; }, getValue : function(){ return format(_counter); }, setFormat: function(str){ _format = str; } }; return public;}());

BUILDING A MODULEBut we also want to change the

output format of the module. Lets adda "private" property and a "setter".

COUNTER.increment();COUNTER.increment();

console.log(COUNTER.geValue()); // Counter is 2

COUNTER.setFormat('Value = ');console.log(COUNTER.geValue()); // Value = 2

COUNTER._format = "Foobar"console.log(COUNTER.geValue()); // Value = 2

Page 45: Javascript fundamentals for php developers

var COUNTER = (function(){ var _container, _counter = 0, _format = 'Counter is '; var format = function(value){ return _format + value; } var public = { // snip... }; var init = function(container){ _container = container; _container.innerHTML = 'Counter ready!'; return public; } return init;}());

BUILDING A MODULENow we want to configure the

module from the outside. The easiestway to that is to add an init

function.

DEMO TIME ...

Page 46: Javascript fundamentals for php developers

<div id="container"></div><button id="trigger">Add 1</button>

var c = document.getElementById('container') t = document.getElementById('trigger');

var myCounter = COUNTER(c);t.onclick = function(){ myCounter.increment();};

Counter ready!Add 1

Try it yourself at http://ncl.uz/counterdemo

Page 47: Javascript fundamentals for php developers

A LITTLE EXTRA ...What if we need to build a really large module?Spread over several files?

MODULE AUGMENTATION

Page 48: Javascript fundamentals for php developers

// module.jsvar COUNTER = (function(){ var _counter = 0; var _format = 'Counter : '; var format = function(value){ return _format + value; } var public = { increment : function(){ _counter++; }, getValue : function(){ return format(_counter); }, setFormat: function(str){ _format = str; } }; return public;}());

AUGMENTING A MODULEWe want to add a new public methodshout to the already existing

COUNTER

// module.shout.jsvar COUNTER = (function(public){ public.shout = function(){ var output = public.getValue(); return output.toUpperCase(); }; return public;}(COUNTER));

Can only access/override the publicAPI

Page 49: Javascript fundamentals for php developers

THE BAD PARTS ...Only one instanceNo inheritance systemAugmentation only has access to the public API

Page 50: Javascript fundamentals for php developers

THE FUTUREUMD (UNIVERSAL MODULE DEFINITION)

Defines a way to structure modules so they work both in the browser and on the server

github.com/umdjs/umd

AMD (ASYNCHRONOUS MODULE DEFINITION)

Defines a way to load modules in any arbitrary ordergithub.com/amdjs/amdjs-api

Page 51: Javascript fundamentals for php developers

TAKING A LOOK AT ECMASCRIPT 6WHAT CAN WE EXPECT FROM ES6?

Current status: kangax.github.io/es5-compat-table/es6

Page 52: Javascript fundamentals for php developers

DEFAULT PARAMETERSES5

function increment(x, y) { y = y || 1; return x += y; }

ES6function increment(x, y = 1) { return x += y; }

Page 53: Javascript fundamentals for php developers

LEXICAL SCOPE WITH LETES5

function doSomething() { var x = 5; if (someCondition) { var x = 10; doSomethingElse(x); } console.log(x); // 10 !!}

ES6function doSomething() { let x = 5; if (someCondition) { let x = 10; doSomethingElse(x); } console.log(x); // 5 !!}

Page 54: Javascript fundamentals for php developers

CONSTANTSES5

// Nope ... no constants for you

ES6const limit = 100;limit = 200; // SyntaxError

Page 55: Javascript fundamentals for php developers

CALLBACK ARROW NOTATIONES5

[1,2,3].map(function (x) { return x * x;});

ES6[1,2,3].map(x => x * x);

Page 56: Javascript fundamentals for php developers

CLASS DEFINITIONSES5

function Vehicle(color) { this.color = color; this.speed = 0;} Vehicle.prototype.drive = function() { this.speed = 40;}

ES6class Vehicle { constructor(color) { this.color = color; this.speed = 0; } drive() { this.speed = 40; }}

Page 57: Javascript fundamentals for php developers

CLASS INHERITANCEES5

function Car(brand, color) { Vehicle.call(this, color); this.brand = brand; this.wheels = 4;} Car.prototype = Object.create(Vehicle.prototype);Car.prototype.constructor = Car;

ES6class Car extends Vehicle { constructor(brand, color) { super(color); this.brand = brand; this.wheels = 4; }}

Page 58: Javascript fundamentals for php developers

WRAPPING UP ...You can build pretty robust modules in JavascriptBut they are still not comparable to PHP ClassesWe haven't touched inheritance, interfaces, abstract classes, etc ...These are all possible with Javascript... but that's for another time

Page 59: Javascript fundamentals for php developers

QUESTIONS?

Page 60: Javascript fundamentals for php developers

[email protected]@chrisramakersAny feedback is appreciated!joind.in/10254Come talk to me!