Interview notes
Concepts
JavaScript
Primitives
Primitive types
represent simple values stored directly in the variable object for a given
context.
- Boolean
- Number
- String
- Null
- Undefined
Reference
These are the closest thing to classes in JavaScript, and
objects are instances of reference types.
- Array
- Date
- Error
- Function
- Object
- RegExp
Types
Scope
JavaScript use lexical-scope: the place where the variable was defined at author-time determines it's scope. In JavaScript, scopes are delimited by function blocks. ECMAScript 6 introduces the let keyword to define variables at block-scope.
var test = 'I am in the global scope';
function inner() {
isGlobal = 'Sad, but true';
var a = 1;
var test = 'I belong to the inner() function scope';
console.log(test);
}
inner(); // output: 'I belong to the inner() function scope'
console.log(test); // output: 'I am in the global scope'
console.log(isGlobal); // output: 'Sad, but true'
console.log(a); // ReferenceError: a is not defined
'use strict';
var i;
var x = 3;
var y = 2;
if (x > y) {
let z = x + y;
i = z;
}
console.log(i); // output: 5
console.log(z); // ReferenceError
Closures
Closure is when a function is able to remember and access its lexical scope even when that function is executing outside its lexical scope.
var a = 2;
function foo() {
var b = 4;
function innerFoo() {
return a + b;
}
return innerFoo;
}
var f = foo();
f(); // output: 6
Some good use cases for closures are:
- Data encapsulation
- Module pattern
- Prevent global scope pollution
This binding
Determining the this binding for an executing function requires
finding the direct call-site of that function. Once examined, four rules
can be applied to the call-site, in this order of precedence
-
Used new operator? Uses the newly constructed object.
- Called with call, apply or bind? Uses the specified object.
- Called with a context object owning the call? Uses that context object.
- Default: undefined in strict mode, otherwise, uses the global object.
var obj = {
x: 81,
getX: function() { return this.x; }
};
// output: 81
console.log(obj.getX.bind(obj)());
console.log(obj.getX.call(obj));
console.log(obj.getX.apply(obj));
var name = 'Richard';
function sayHi() {
return 'Hi ' + this.name;
}
// output: Hi Richard
sayHi();
// output: Hi Peter
sayHi.call({ name: 'Peter' });
// output: Hi John
sayHi.apply({ name: 'John' });
// output: Hi Mike
sayHi.bind({ name: 'Mike' })();
Inheritance
JavaScript implements inheritance through prototype chaining. A prototype chain is created between object when the [[Prototype]] property of one of them is set equal to another. Generic objects inherit from the Object prototype.
function Person(name) {
this.name = name;
}
Person.prototype.sayName = function() {
return this.name;
}
function Hero(name) {
// constructor stealing
Person.call(this, name);
}
// Setting the prototype to a new instance of Person
Hero.prototype = new Person;
/*
var hero = new Hero('Superman');
console.log(hero.__proto__) // => Object
console.log(hero.constructor) // => Person
*/
// Setting the prototype to Person.prototype
Hero.prototype = Person.prototype;
/*
var hero = new Hero('Superman');
console.log(hero.__proto__) // => Person
console.log(hero.constructor) // => Person
*/
// Using Object.create method
Hero.prototype = Object.create(Person.prototype, {
constructor: {
value: Hero,
writable: true,
configurable: true,
enumerable: true
}
});
/*
var hero = new Hero('Superman');
console.log(hero.__proto__) // => Hero
console.log(hero.constructor) // => Hero
*/
Concepts
AngularJS
2-way
We have a two way data binding when a the data can be modified both by the view and the model itself, generating a live view. The view is a projection of the model at all times. When the model changes, the view reflects the change, and vice versa.
1-time
The main purpose of one-time binding is to provide a way to create a binding that gets unregistered and frees up resources once the binding is complete. If the expression will not change once set, it is a candidate for one-time binding.
Data binding
Services
Angular services are substitutable objects that are wired together using dependency injection (DI). You can use services to organize and share code across your app.
Angular services are:
- Lazily instantiated – Angular only instantiates a service when an application component depends on it.
- Singletons – Each component dependent on a service gets a reference to the single instance generated by the service factory.
Dependency Injection
Dependency Injection (DI) is a software design pattern that deals with how components get hold of their dependencies.
To manage the responsibility of dependency creation, each Angular application has an injector. The injector is a service locator that is responsible for construction and lookup of dependencies.
The application code simply declares the dependencies it needs on the constructor, without having to deal with the injector.
Directives
A directive is just a function which executes when the compiler encounters it in the DOM.
At a high level, directives are markers on a DOM element (such as an attribute, element name, comment or CSS class) that tell AngularJS's to attach a specified behavior to that DOM element or even transform the DOM element and its children.
Testing
JavaScript is a dynamically typed language which comes with great power of expression, but it also comes with almost no help from the compiler.
Angular makes testing your applications easy. So there is no excuse for not testing.
Unit testing
Unit testing, as the name implies, is about testing individual units of code. It help us to answer questions like "Did I think about the logic correctly?" or "Does the sort function order the list in the right order?"
Angular provides several tools for writing our unit tests, among these we can find: Karma, Jasmin and angular-mocks
Karma
Karma is a Node.js command line tool that can be used to spawn a web server which loads your application's source code and executes your tests. You can configure Karma to run against a number of browsers, which is useful for being confident that your application works on all browsers you need to support. Karma is executed on the command line and will display the results of your tests on the command line once they have run in the browser.
Unit testing
Jasmine
Jasmine is a behavior driven development framework for JavaScript that has become the most popular choice for testing Angular applications. It provides functions to help with structuring your tests and also making assertions. As your tests grow, keeping them well structured and documented is vital, and Jasmine helps achieve this.
Unit testing
Angular mocks
Angular provides the ngMock module, which provides mocking for your tests. This is used to inject and mock Angular services within unit tests. In addition, it is able to extend other modules so they are synchronous. Having tests synchronous keeps them much cleaner and easier to work with. One of the most useful parts of ngMock is $httpBackend, which lets us mock XHR requests in tests, and return sample data instead.
Unit testing
PhantomJS
PhantomJS is a headless webkit browser, scriptable with a
JavaScript API. It has native support for various web standards such as:
- DOM, Canvas & SVG
- CSS Selectors
- JSON
Unit testing
Performance issues
- Watching functions: Never bind anything (ng-show, ng-repeat, etc.) directly to a function. Never watch a function result directly. This function will run on every digest cycle, possibly slowing your application to a crawl.
- Watching objects: Never use the third parameter (true) in the scope.$watch. Use $watchCollection, instead.
- Long Lists: Avoid long lists. ng-repeat does some pretty heavy DOM manipulation. When possible use virtual rendering approach.
- Bindings: Try to and minimize your bindings by using a one-time binding notation where possible. One-time bindings do not add watchers to the expressions.
- Isolate scope or transclusion: These creates a new scope of properties to watch, so be careful deciding whether you need transclusion or isolated scopes.
Things I had to deal with
Build scripts
Grunt & Gulp
Grunt
- Uses intermediate files on disk
- Focuses on configuration
- Initially built around a set of built-in, and commonly used tasks.
Gulp
- Uses node.js vinyl streams to create in-memory files.
- Focuses on code
- Built on community-developed micro-tasks that should connect to each other.
Common build tasks
- Asset compilation such as Jade templates, CoffeeScript, SCSS, etc...
- CSS automatic vendor prefixing, linting & concatenation.
- JavaScript static code analysis & linting.
- JavaScript minification & concatenation.
About me
Self-presentation
Soft skills
-
Teaching, mentoring, and knowledge sharing: I'm able to transmit knowledge, I have a background on IT education at Cisco Certified Network Associate course.
- Curiosity: The need to find and resolve new challenges, interconnect things, look at the output reiterate.
- Flexibility: Web technologies are in constant evolution, new languages, new frameworks. I spend a couple minutes a week to be on the track of this.
- Communication skills: I have very good writing and verbal communication skills
Interview notes
By Ricardo Casares
Interview notes
- 638