Switching to JS

Who?

  • Horia Radu

  • Full Stack Dev @ [e-spres-oh]

  • Writing code in JS, RoR

  • Passionate about: FP, JS, React, Ruby, Scala

Background

  • backend DEV

  • ~3 years of Java

  • ~1.5 years of Ruby/RoR

  • JS XP: jQuery event handlers :P

Currently

  • node (strongloop)
  • angular
  • still afraid of advanced CSS :P

How to learn a new programming language?

1# have an open mind

  • the programming language is just a tool to express yourself

2# online resources

  • code school - first contact

  • pluralsight for angular (mainly best practices, patterns, etc.)

  • stackoverflow - when needed

3# write code

  • work - code review!

  • hackerrank

  • side project

4# community

patient friends who can guide, help and explain

A trip down memory lane

one language to rule them all

  • looks like backend code

Organization

ecosystem

  • Angular
  • React
  • Strongloop
  • Express
  • Ramda
  • immutableJS
  • grunt
  • mocha
  • chai
  • so many more...

this (that, self, etc.)

function doLater(cb) {
    cb();
}

function Foo() {
    this.name = 'John';
    
    this.doSomething = function() {
        return doLater(function () {
            return this.name;
        })
    };
}

var x = new Foo();
console.log(x.doSomething());

iterator

let arr = [ 3, 5, 7 ];

for (let i in arr) {
   console.log(i); // expecting 3, 5, 7
}

?

iterator

let arr = [ 3, 5, 7 ];

for (let i in arr) {
   console.log(i);
}

arr.forEach(function (item) {
   console.log(item);
});

angular.forEach(arr, function (item) {
   console.log(item);
}

?

reuse - where's my 'import'

  • requireJS

  • commonJS

  • browserify

  • webpack

  • angular injection

?

callback hell

getSomething(..., function() {
    ...

    getSomethingElse(..., function() {
        ...

        oneMoreThing(...., function() {
            ....
        });
    });
});

error handling...

reactive programming

return Promise.all([
    getSomething()
        .then(getSomethingElse),
    getThisToo()
  ])
  .then(aggregate)
  .catch(handleError);

?

overloading

var create = function (data, options, cb) {
  if (options === undefined && cb === undefined) {
    if (typeof data === 'function') {
      // create(cb)
      cb = data;
      data = {};
    }
  } else if (cb === undefined) {
    if (typeof options === 'function') {
      // create(data, cb);
      cb = options;
      options = {};
    }
  }

  data = data || {};
  options = options || {};
  cb = cb || utils.createPromiseCallback();

  ...
}

overloading

create(cb)
create(data, cb)
create(data, options, cb)

overloading

var create = function (
    data: {}, 
    options: {}, 
    cb: utils.createPromiseCallback()) {
 
  ....
}

!?!

unit testing

expect(foo).to.have.all.keys('bar', 'baz');
it('computes the data', function () {
  return expect(Foo.computeSomething()).to.become(expected);
});
fooService
  .expects('findBy')
  .withArgs({name: 'John', lastName: 'Doe'})
  .once()
  .returnsPromise()
  .resolves([]);

running unit tests

  • run a single test file
  • run a single 'it'
mocha_istanbul: {
  coverage: {
    src: [grunt.option('test') ? 
        'server/test/**/' + grunt.option('test') : 
        'server/test/**/*.spec.js'],
    options: {
      coverageFolder: 'coverage/server',
      reportFormats : ['text', 'html']
    }
  }
}

vs

$> rspec /spec/controllers/groups_controller_spec.rb:42

npm

  "dependencies": {
    "loopback-boot": "^2.14.0",
    "loopback-component-explorer": "^2.1.1",
    "loopback-component-passport": "^1.6.0",
    "loopback-connector-mysql": "^2.2.0",
    "loopback-connector-rest": "^1.10.1",
    "loopback-datasource-juggler": "^2.41.1",
    "loopback-ds-timestamp-mixin": "^3.2.2",
    ...
  },
  "devDependencies": {
    "chai": "^3.4.1",
    "chai-as-promised": "^5.2.0",
    "sinon-chai": "^2.8.0",
    "sinon-stub-promise": "^1.0.1",
    "supertest": "^1.1.0",
    ...
  },
$> npm install --save foo

2nd level dependency bump

source 'https://rubygems.org'

ruby '2.2.3'

gem 'rails', '4.2.5'
gem 'mysql2', '0.3.18'
gem 'sass-rails', '~> 5.0'
gem 'uglifier', '>= 1.3.0'

group :development, :test do
  gem 'byebug'
  gem 'quiet_assets'
end
GEM
  remote: https://rubygems.org/
  specs:
    actionmailer (4.2.5)
      actionpack (= 4.2.5)
      rails-dom-testing (~> 1.0, >= 1.0.5)
    actionpack (4.2.5)
      rack-test (~> 0.6.2)
      rails-dom-testing (~> 1.0, >= 1.0.5)
      rails-html-sanitizer (~> 1.0, >= 1.0.2)

PLATFORMS
  ruby

DEPENDENCIES
  annotate (>= 2.5.0)
  better_errors
  bullet
  web-console (~> 2.0)
  whenever

BUNDLED WITH
   1.11.2
$> bundle install
$> bundle update
$> bundle update [gem]

ES 6 to the rescue

  • arrow functions
  • template strings
  • parameter deconstruction
  • block scope (let, const)
  • import
  • tail recursion

Q & A

Thanks!

switching-to-js

By Horia Radu

switching-to-js

  • 368