Main menu

Stay in touch for more remote team tips

15 aug

How To Hire An AngularJS Developer

First, we’ll talk a bit about why you want to hire an AngularJS developer or AngularJS freelancer. Then, you’ll learn more about the advantages of this framework. Once you understand its benefits, we’ll talk about what questions to ask during the interview process so you can learn if your applicants are truly AngularJS experts.

 

Why Hire An AngularJS Developer?

AngularJS has become indispensable since its release because of its numerous benefits, including assisting with HTML, supporting advanced JavaScript, and making the process of designing and testing more simple overall.

If you use AngularJS to build a data-driven web application, no other frameworks or plugins are necessary. Because it’s a complete front-end development solution, outfits like Intel, Google, and other large companies utilize AngularJS for these benefits, increasing their performance, speed of creation and testing, and more.

This JavaScript framework works to simplify the process of building dynamic, single page web apps (SPAs) and make your and your developers’ lives simpler.

 

Combine Modules

With AngularJS, it’s possible to combine different modules to create applications.

This framework utilizes modules instead of main methods to instantiate and connect different aspects of the application. These modules explain declaratively how the application should be bootstrapped.

This makes the code easier to understand, gives developers a chance to reuse these modules, loads only specific modules in unit tests, helps to increase speed, and more. The modules delay execution, so they are able to be loaded in any order, including parallel.

AngularJS, then, helps take a lot of work off the developer by identifying situations on its own where particular objects should be provided, such as a Facebook login module, throughout an application.

After it identifies which are necessary, AngularJS then provides the needed modules and binds them together. Many of them are ready-made with solutions to common problems and tasks, such as certain routing modules like a ui-router, saving you time and lines of code.

 

Large, Active Community

This framework is open-source and has a very active community. This means that there are constantly new additions that make the developer’s life easier. Also, don’t overlook the fact that almost every question you could ever have has already been asked on sites like StackOverflow.

Because AngularJS is so popular, there are worldwide events like Meetups, hackathons, and other conferences regarding understanding this language where they explaining how you and your developers can use it to take your applications to the next level.

Because it is so popular and has such a large amount of online resources, finding experienced AngularJS remote freelancers for hire is usually simple because of the large pool of talent to choose from.

 

It’s Declarative

Because AngularJS is declarative, the code is more easy to read and support. This programming paradigm means that the logic is expressed in the code, but it exempts its control flow.

Essentially, instead of describing every single step needed to reach the end result, those programming in AngularJS just describe that final result. This saves time and increases simplicity, especially when you have a large team looking at code written by other members.

 

Built By Google Engineers

Because AngularJS was developed by Google engineers, Adam Abrons and Misko Hevery, the code base is solid and fully supportive. Having the backing of a large, stable company puts this framework over other otherwise good options, such as KnockoutJS.

Even more supporting of the stability of AngularJS is the fact that Google had developed a JavaScript framework in the past. AngularJS, however, was created to help standardize web application structure and improves upon their mistakes of the past.

 

Directives

While AngularJS’s pattern language is HTML, it also includes many directives. These directives allow you to “invent new HTML syntax, specific to your application.” Directives also help you create reusable components that can be utilized to hide complex DOM structure, CSS, and behavior.

For example, developers can operate HTML like XML rather than creating numerous CSS classes for each object’s intention. This means that you have many more options for different attributes without having too many classes. Angular’s HTML compiler combined with directives help you engage this behavior in your code so you can focus on how the application looks separately from what it does.

 

Simplified Testing

First of all, AngularJS requires no additional frameworks or plugins for testing; instead, it was designed from the ground up to be testable. Angular is linked with its Dependency Injection (DI) which is used for managing controllers and scopes. Each controller relies on DI to relay information, and AngularJS places example data into the controller in order to measure its behavior.

DI helps in additional ways as well. Using the injector subsystem, you can more easily focus on “creating components, resolving their dependencies, and providing them to other components as requested,” according to AngularJS’s developer guide.

Because you can easily separate modules, you are able to automatically and simply test different portions of your application. Testers will also appreciate behavior-view separation and the ability to inject and mock services within unit testing that AngularJS comes with, pre-bundled.

Additionally, this framework eliminates test flakiness through an end-to-end scenario runner that understands the full inner workings of it. With this testing model, your tests are executed in an environment as similar to your actual application as possible.

 

Data Binding

AngularJS features two-way data binding, which means that the changes made to application objects also affect the user interface. Essentially, it’s the “automatic synchronization of data between the model and view components.” The way the Angular handles data binding allows you to treat the model as the single-source-of-truth in the application.

This means that the model is always projected as the view and when one changes, so does the other. Developers no longer have to user wrappers, getters, setters, or class declarations because it’s handled by AngularJS. Instead, you can write code either with custom types or JavaScript primitives.

Typically, data is bound in only one direction, merging the model components and template together into a view but not automatically reflecting any future model changes in the view or vice versa. These developers, then, are forced to “write code that constantly syncs the view with the model and the model with the view.”

With AngularJS, instead, the template is first compiled on the browser and the compilation step produces a live view. So, any view changes are shown on the model, as well as the opposite option. This helps programmers work faster and with more confidence, and assists in testing because controllers can simply be tested in isolation without the view and related DOM/browser dependency.

 

Conducting An AngularJS Interview

Now that you understand the benefits of having an Angular developer, it’s time to discuss what interview questions are most important and telling of the developer’s knowledge of the framework.

 

Explain Scope In AngularJS

Scope is an object that is an execution context for expressions. Scopes refer to the application model and are arranged in a hierarchical structure that mimics the Document Object Model (DOM) structure of the application.

 

Scopes are able to both watch expressions and propagate events. Some of its important characteristics include:

  • Providing APIs ($watch) to observe model mutations

  • Nesting scopes in order to control access to certain application components and properties. These nested scopes are referred to as either “child scopes” or “isolate scopes.” As their names imply, child scopes inherit properties from their parent scopes while isolate scopes do not.

  • Evaluating expressions through the context of the scope

  • Propagating model changes from outside of the AngularJS realm through the system into the view with APIs ($apply) provided by scopes

 

Referring to scope as a data-model, it is the “glue between application controller and the view.” Directives set up $watch expressions on the scope during the template linking phase, which help directives to know about property changes. This, in turn, lets the directive send the updated value to the DOM.

The controller is isolated from both the directive and the DOM because controllers and directives do not have reference to each other, but they both have reference to the scope. This assists in making the controller's view agnostic, improving testing.

Any person who is interviewing for an AngularJS job should have extensive knowledge of scope. $scope objects are a vital concept in this framework, bridging the application controller and view.

 

An example given in the AngularJS documentation is below:

angular.module('scopeExample', [])
.controller('MyController', ['$scope', function($scope) {
 $scope.username = 'World';

 $scope.sayHello = function() {
   $scope.greeting = 'Hello ' + $scope.username + '!';
 };
}]);

As we can see in this example, World is assigned to the username property of the scope with the  MyController. Then, the scope notifies the input, and the input is pre-filled with the username. With the above example, you can understand how data is written into the scope via a controller.

 

The scope’s properties can also be automatically updated when bound to HTML input widgets. In another example given in the documentation, a behavior assigned to scope is invoked upon a user click. The example is as follows:

it('should say hello', function() {
 var scopeMock = {};
 var cntl = new MyController(scopeMock);

 // Assert that username is pre-filled
 expect(scopeMock.username).toEqual('World');

 // Assert that we read new username and greet
 scopeMock.username = 'angular';
 scopeMock.sayHello();
 expect(scopeMock.greeting).toEqual('Hello angular!');
});

To understand the logical rendering of {{greeting}}, it’s important to recognize that this includes:

  • “retrieval of the scope associated with DOM node where {{greeting}} is defined in template. In this example this is the same scope as the scope which was passed into MyController.

  • Evaluate the greeting expression against the scope retrieved above, and assign the result to the text of the enclosing DOM element.”

So, the scope can be considered the single source-of-truth for everything view related. Separating the controller and the view helps test the code without needing to focus on any rendering details.

 

To summarize, the scope is able to watch expressions and propagate events. It glues together the application controller and the view, they are arranged hierarchical, and they closely imitate the DOM structure of the application.

 

Explain How $watch Works Within The $digest Cycle

This question covers a few different positions. Not only do your potential employees need to understand both $watch and $digest, they need to understand how these two concepts fit together.

Essentially, with each digest cycle, the current and previous $watch expressions are compared to each other; the $digest must be called via the $apply method if you wish to trigger it manually. It’s performed asynchronously. Because of this, the $watch is only notified during the $digest phase, not immediately.

Because of this delay, you can be certain that other $watches aren’t running at the same time as another $watch notification. Additionally, one $watch notification coalesces many different model updates, if necessary. Each change of the $watch value creates an additionally $digest cycle until all values are updates.

To simplify this process, the AngularJS documentation explains that, “At the end of $apply, AngularJS performs a $digest cycle on the root scope, which then propagates throughout all child scopes. During the $digest cycle, all $watched expressions or functions are checked for model mutation and if a mutation is detected, the $watch listener is called.”

From here, the scope is destroyed, as well as any unnecessary child scopes. Destroying these processes is particularly necessary to save memory by stopping the $digest calls into the child scope.

This digest cycle is a loop that completes what was explained in the first question: when the model is changed, the view is updated.

To summarize, first, a event is triggered, changing the activity model value. Then, AngularJS compares these values to the old values. If they are different, the digest cycle begins. This cycle checks the watchers that are assigned to each object in the scope. These watches then tell the digest cycle which model is changed, and therefore, which should be updated. Lastly, this cycle runs again (referred to as a dirty check), which ensures the model and view are in sync.

Some bonus points for the AngularJS interview can be earned if the interviewee also explains how having too many watchers make the digest cycle too slow and consumes too much memory. A general rule is that over 2000 watchers on a page is too many.

 

Explain What A Service Is And Why It’s Used

Services in AngularJS are “substitutable objects that are wired together using dependency injection (DI).” Services are global and used to organize and share code across your app.

They are only instantiated if an application component depends on it, otherwise referred to as lazily instantiated. This makes AngularJS applications less error prone and more robust.

Additionally, services are singletons, which means that “each component dependent on a service gets a reference to the single instance generated by the service factory.” Put simply, each service is responsible for only its specific task.

These services can be created using either a factory or a service method. If the person being interviewed does not explain the difference between these two types of methods, ask them to explain further. Our answer is located below.

With an AngularJS service, it’s possible to develop business logic without needing the View logic that it will work with. Some popular inbuilt services that AngularJS provides include the $http service, the $log service, and the $anchorScroll.

The $http service helps you connect to the remote HTTP servers. The $log service is a simple server that helps the developers log, safely writing any messages into the browser’s console. The $anchorScroll scrolls either to the element that is related to the declared hash or the current value of  $location.hash().

To make sure your applicant knows their way around services, ask them to name a few of the popular built-in services provided by AngularJS. Some of these, all of which begin with the $ symbol, include:

  • $window - a reference to the browser’s window object

  • $location - parses the URL in the browser address bar based on the window.location so this URL is available to your application

  • $filter - used to formatting data that is displayed to the user

  • $resource - lets you interact with Restful APIs

  • $timeout - provides a reference to the window.setTimeout function

  • $rootScope - each application has only one root scope in which every other scope is descended from. Scope was discussed in-depth above

  • $document - a jQuery or jqLite wrapper for the browser’s window.document object

  • $exceptionHandler - handles any uncaught exception in AngularJS expressions. By default, any exceptions are delegated to $log.error which logs it into the browser console.

  • $parse - simply converts AngularJS expression into a function

  • $cacheFactory - constructs cache objects and gives access to them

 

Of course, your applicant won’t have all of these memorized, but they should be able to name a few that they commonly interact with.

Your developers can evolve reusable APIs within their application through services creating reusable components. Additionally, using the AngularJS controller, it’s possible to inject one service into another.

Injecting the data that is held in one service into another via the controller is the simplest way to share data between controllers. Keep in mind, through, that it’s also possible to share data between controllers by using events, or things such as $parent or nextSibling to access the controllers directly.

However, your interviewee should know that using services and a controller in the method describe above is the most efficient and helps facilitate easier testing.

 

Explain The Difference Between A Factory Method And A Service Method

Now, we’ll discuss a bit about what was mentioned earlier: factories and services. The reason these two different options are provided is so developers can store business logic and persistent data separately from controllers and scopes inside of an application.

In an example below, we’ll explain the difference between a service function and a factory function. As you’ll see, both log “hello,” but the main difference to understand is located right before you print these words. With a factory, it’s a function that has to be called, whereas a service is a constructor function.

A simple way to see this is that, in the service example, you can use the keyword “this,” whereas the factory you cannot. Instead, you have to explicitly return the object you created with the factory.

// The code below is a service.
app.service('MyService', function () {
 this.sayHello = function () {
   console.log('hello');
 };
});


// The code below is a factory.
app.factory('MyService', function () {
 return {
   sayHello: function () {
     console.log('hello');
   };
 }
});

 

If your applicant really wants to impress you, they can explain how “a service calls a predefined factory, which ends up as $get()$get() method on the corresponding provider.” Put more simply, “$injector.instantiate()) is the method that ultimately calls Object.create() with the constructor function. That’s why we use this in services.”

function service(name, constructor) {
 return factory(name, ['$injector', function($injector) {
   return $injector.instantiate(constructor);
 }]);
}

 

How Many Different Ways Are There To Create Services In Angularjs? Can You Elaborate On Them?

There are five different ways, referred to by AngularJS as recipies: Factory, Service, Provider, Value, and Constant.

 

  1. Factory

Of course, we just discussed Factory a bit. With a Factory, other services are able to be injected into it after it is created. Factory has more abilities than some of the other options, like the Value recipe, such as the capability to have dependencies, or use other services, service initialization, and more.

The Factory recipe takes a string (the name of the service) and a function (the implementation) as an argument. The string is used to inject the service into a controller as a dependency. Angular executes the function once when the service is registered.

Then, the return value is cached and able to be shared with other parts of your application that inject the service.

A main difference between Factory and Service is that, with the Factory method, the callback function is executed, whereas with the Service, the function is simply instantiated. Let’s take a look at an example of how to create a Factory recipe.

 

// Create a factory service

app.factory(“username”, function() {

var name=”John”;

return {

name:name

}

});

Here we can see that function() is taken as an argument. In this, it’s possible to inject multiple dependencies or methods, depending on your particular service. An object must be returned; here the name is returned.

 

Then, let’s see how this Factory service can be used in the controller. Here’s you’ll see that the username from the Factory that was created is assigned to the scope username.

app.controller(“MainController”, function($scope, username) {

$scope.username=username.name;

});

 

Let’s look at one more example that is a common approach to creating a Factory recipe.

var app = angular.module(‘myApp’, []);

 

myApp.factory(‘myService’, function() {

    return {

        sayHello: function() {

            Return “Hello”

}

};

});

With this example, any component that lists the service, myService, as a dependency will receive the object that, in this example, simply has one method, sayHello.

 

  1. Value

This is a very simple service type that developers are able to create and use. Alluding to its name, it’s only able to store one single value. This recipe is typically used to make a global and injectable Angular service. This value can then be easily shared across the application, becoming testable.

Let’s look at a couple examples to better understand this option.

 

var app = angular.module(‘app’, []);

app.value(“employee”, 50);

Here, we have the primitive value of 50, but it’s also possible to use objects here.

var app = angular.module(‘app’, []);

app.value(“jobTitle”, {title: CEO’});

 

From here, either of the above examples can be used throughout the app via dependency injection. In this following example, you can see that a value service “employee” was created and then used in the MainController.

 

app.controller(“MainController”, function($scope, employee){

$scope.employee=employee;

});

 

  1. Constant

Once again alluding to its name, this recipe is used to declare constants. After they are declared, they are then able to be added as a dependency and used where they are needed. It can also be used during the configuration phase of the application.

This service is typically used with values such as the application name or base URLs. As your developers should know, these constant values cannot be changed. So, they are defined once, then reused throughout the app as needed.

 

Here are a couple different examples. This one sets an unchangeable username:

app.constant(‘username’, ‘Admin’);

 

This example sets a constant of max iterations:

var app = angular.module(‘myApp’, []);

app.constant(MAX_ITERATIONS”, 5);

 

  1. Service

This one is similar to the factory recipe except it receives a JavaScript class or a constructor function that is instantiated as an argument rather than a function. The function is instantiated only once and “every component that injects your service as a dependency share the same exact cached object that this instantiation returns.”

 

Here are some examples that you can see of this one.

function Example(number) {

this.var=”value”; }

After you’ve established a function, you can convert it into a Service with the Factory recipe.

app.factory(“service”,[“num”, function(num) {

return new Example(num);

}]);

As you see, a new instance is created and returned and num is injected as a dependency in the Factory.

 

Here’s one more example:

var app = angular.module(‘app’, []);

app.service(‘service’, function() {

    this.helloWorld = function() {

        return “Hello World”

    };

});

If you compare this to the Factory recipe, you can see that they are very similar. In the Service recipe, though, you can use the this keyword to define properties and methods of the object that the Service returns. This is because it’s instantiated, rather than being executed.

 

  1. Provider

The fifth option is the Provider recipe, and it is rather complex when compared to the other options. It is actually the parent of all the service types that you can use within AngularJS (apart from a Constant).

It is the core of the service types, so the others work on top of it. It also provides many features that the others don’t, although it is more verbose. The service registered with this is able to be accessed by the application during its configuration phase, which is quite useful if the service will be shared across different applications and needs to be properly configured.

This configurable service must implement the $get method in order to retrieve the object to inject. This service can also be used to show the API responsible for configuration across the application.

Another important thing that your applicants should know about using this recipe is that the callback function is instantiated with each application that it is registered with, and all components that inject that service share its return value. Essentially, the Provider recipe treats the callback function that is passed as a constructor.

Here are some examples to help with this more difficult recipe.

The first example initializes a provider named authentication and implements the $get function that returned the method getUserName which, aptly named, returns the private variable username.

 

app.provider('authentication', function() {

  var username = "John";

  return {

      set: function(newUserName) {

          username = newUserName;

      },

      $get: function() {

          function getUserName() {

              return username;

          }

          return {

              getUserName: getUserName

          };

      }

  };

});

 

There is additionally a setter that is utilized on application startup to set the username.

 

app.config([“authenticationProvider”, function(authenticationProvider) {

    authenticationProvider.set(“Provider”);

}]);

 

Let’s take a look at one more example where we create a Service named helloWorld that is available during the configuration phase of the application. As you’ll see, once the service is registered, the app.config method is called and the helloWorld service is passed as an argument to the anonymous callback function.

 

var app = angular.module(‘myApp’, []);

 

app.provider(‘helloWorld’, function() {

 this.name = ‘Default’;

 

   this.$get = function() {

    var name = this.name;

    return {

     sayHello: function() {

       return “Hello, “ + name

    }

   }

  };

  this.setName = function(name) {

    this.name = name;

  };

});

 

app.config(function(helloWorldProvider) {

 helloWorldProvider.setName(‘World’);

});

 

Within this callback, the service’s setName method sets the name value. The helloWorld service is able to be used with a different “name” value in another application if you need to.

 

Explain Unit Testing And End-to-end Testing

Unit testing

First, let’s talk about unit testing. Because JavaScript is dynamically typed, there’s great power of expression but the compiler does not assist the developer much. Because of this, strong, frequent tests are a non-negotiable for any application written in JavaScript.

While testing can be difficult to perform, AngularJS provides its users with multiple different features that help make testing easier.

Unit testing is, as you might imagine, testing specific units of code. Some of the questions these tests work to answer are ones such as “Did I think about the logic correctly?” or “Does the sort function order the list in the right order?”

As most developers know, these questions can’t be answered well if related pieces such as the DOM elements or XHR calls are made to fetch the data to sort are created. The reason the specific piece of code needs to be isolated is in order to test only the sort function and nothing else.

Even if you understand why each element should be separated, it can be very difficult to test specific functions or methods and stop the code from doing things such as making that XHR request, sorting the response data, and manipulating the DOM.

That’s why AngularJS created tools to try and help you organize your code into units to better test it. As they explain, “For your XHR requests, we provide dependency injection, so your requests can be simulated. For the DOM, we abstract it, so you can test your model without having to manipulate the DOM directly.”

This way, the tests don’t need to create or look at the state of the DOM or get data returned from the XHR requests. Instead, they can simply see if the data has been properly sorted in isolation.

Dependency injection is a particularly useful built-in feature that your applicants should be able to explain to you in detail. As testing is so important for any application, it’s important that they know how AngularJS makes it more simple.

With dependency injection, developers are able to pass in a component's dependencies and stub or mock them as desired. If a component has its dependencies injected, it is easily mocked for each test you run without the need for changing global variables that could potentially alter a different test.

The AngularJS injector subsystem “is in charge of creating components, resolving their dependencies, and providing them to other components as requested.” It is possible to run throughout AngularJS when defining components or providing run and config blocks for a module.

Components, including directives, filters, services, and animations, are defined by an injectable factory method or constructor function. “Service” and “value” components can then be injected into these components as dependencies.

“Service” and “value” components as dependencies can also inject controllers (defined by a constructor function). If needed, they can be provided with special dependencies. The run method accepts a function. This method can also be injected with “service” and “value,” as well as “constant” components, as dependencies. However, you cannot inject “providers” into run blocks.

Lastly, the config method accepts a function. This one can be injected with “provider” and “constant” components as dependencies, but you can’t inject “service” or “value” components into configuration.

If you want to unit test an AngularJS filter, it’s very simple. You simply have to inject the module with the filter, provide any mocks the filter needs, get an instance of the filter using $filter(‘filerName’), then assert your expectations.

While dependency injection helps make testing much more simple and useful in AngularJS, it can sometimes be difficult to know where to configure and mock the necessary dependencies when you are creating an isolated unit test. Ask your interviewee about this to truly understand their knowledge of the subject.

e2e testing

Next, let’s look into e2e, or end-to-end testing in AngularJS. One thing that is important to note is that, previously, end-to-end testing could be completed using AngularJS Scenario Runner, a deprecated tool. However, this tool is currently in maintenance mode.

Manual testing isn’t always possible. This is particularly true if your company is working with a very large and/or complex application. As the application grows, unfortunately, so do the bugs. While e2e testing can be handled manually if that’s what you prefer, it can also be delegated to continuous integration services. These can be both custom built or provided by a third party.

While unit tests should certainly help catch problems, there are issues that can’t be easily found using only unit tests. So, AngularJS has end-to-end tests to help in these situations. An end to end test runner called Protractor simulates user interaction so you can be sure to catch the bugs that your unit tests missed.

Because of its importance, an AngularJS expert should know how to use Protractor well. This is a Node.js program that runs end-to-end tests that are written in JavaScript and run with node. WebDriver is used with Protractor to control browsers and simulate actions from the user, while Jasmine is used for its test syntax.

Essentially, the e2e tests are executed against a fully initialized system of a running app. Typically, they spawn a browser instance. They also often involve commands being inputted through the user interface.

Then, as mentioned above, the code is evaluated by WebDriver or another automation program, which sends commands to a browser instance. Then, the visible results are evaluated and reported back. From here, Jasmine or a different library handle the assertions.

e2e testing works similarly to unit testing in that a test file consists of at least one it block. This block is made of commands and expectations and describes what your application requires.

Protractor, then, knows to do something with the application, like click a button or navigate to a page, from commands. It is told to assert something about the state, instead, with expectations. This includes things like a current URL or a particular value.

Test files can be told to run before or after an it block by using beforeEach and afterEach blocks. Although typically the runner marks an it block as “failed” if any expectation within it fails and then continues onto the next block, these would run whether the block passes or fails.

So, to summarize, e2e testing comes after unit tests and functions as a safety net, testing the application from the beginning to the end to try and make sure that there are no bugs. After both of these tests and subsequent repairs, everything within the application should be functioning properly, particularly regarding integration and flow issues.

Make sure that your applicant understands both e2e testing and the most popular tool to help with this type of testing, Protractor, which is built by AngularJS. It’s important to keep in mind, though, that there are other ways to run e2e tests, so the person you’re interviewing doesn’t necessarily need to run them on Protractor.

 

Explain Directives In Angularjs.

Directives, at a high level, are markers on a DOM element. This could be an attribute, element name, comment, or CSS class. These tell AngularJS’s HTML compiler to perform actions, such as to transform the DOM element and its children or, more commonly, attach a specified behavior to that DOM element through event listeners.

These are a very important concepts to understand in AngularJS, so your applicant should know exactly what directives are and how to use them.

Many are built into AngularJS, such as ngBind, ngModel, and ngClass, although you can also build your own directives for AngularJS to use, just like you can build your own controllers and services. According to their Developer Guide, “when AngularJS bootstraps your application, the HTML compiler traverses the DOM matching directives against the DOM elements.”

Directives can be used in many different ways and you need to make sure that your applicant knows these numerous options. They are particularly important because they define the UI within a SPA and can be used in creating custom widgets. Essentially, they add new attributes with the ng-prefix, extending the functionality of HTML.

While it is useful for your applicant to know in-depth about how to create custom widgets, they should also know about some of the popular built-in directives. For example, ngBind “tells AngularJS to replace the text content of the specified HTML element with the value of a given expression, and to update the text content when the value of that expression changes.”

On the other hand, ngModel directive “binds an input, select, textarea (or custom form control) to a property on the scope using NgModelController, which is created and exposed by this directive.”

The last main directive is ngClass. This allows users to “dynamically set CSS classes on an HTML element by databinding an expression that represents all classes to be added.” These directives are likely memorized by the interviewee through regular use.

Before writing a directive, it’s important to understand how AngularJS determines when to use said directive via its HTML compiler. The terminology used is that “an element matches a directive when the directive is part of its declaration.”

 

For example, AngularJS shows that with this code: ng-model="foo">, it is proper to say that the input element matches the ngModel directive.

This input element also matches the ngModel: data-ng-model="foo">. Additionally, the following element matches the person directive: {{name}}.

 

To understand which elements match which directives, AngularJS normalizes an element’s tag and attribute name. Directives are referred to in the DOM by lower-case forms because HTML is case-insensitive. As you’ve seen, the dash-delimited attributes, such as ng-model, are typically used.

The way that these are normalized is by stripping the x- and data- from the from of the element or attributes and then converting the :, -, or _-delimited name to camelCase. The Developer Guide gives the follow forms as examples of equivalent forms that match the ngBind directive:

ng-controller="Controller">
 Hello ng-model='name'>

  ng-bind="name">

  ng:bind="name">

  ng_bind="name">

  data-ng-bind="name">

  x-ng-bind="name">

 

 

While this example shows many different options, it is considered best practice to use the dash-delimited format. The others are accepted for legacy reasons but the applicants should be aware that they should be avoided.

While your applicant likely uses the provided directives regularly, it is still important for them to understand how to create them on their own.

Similar to controllers, directives are registered on modules via the module.directive API. This API simply takes the normalized directive name (described above) followed by a factory function. Then, different options to tell compile how the directive should behave when matched should be returned by the factory function as an object.

 

You can perform your initialization work when the factory function is invoked for the only time when the compiler matches the directive for the first time. $injector.invoke invokes this function, making it injectable like a controller.

 

The best practice involving this is to prefix your own directive names so you don’t collide with a future standard. The example given by the Developer guide is that “if you created a directive, it would be problematic if HTML7 introduced the same element. A two or three letter prefix (e.g. btfCarousel) works well.”

 

Additionally, they advise not to prefix the directives that you create with ng so there isn’t any fear of them conflicting with the directives provided by AngularJS

 

Summary

AngularJS is a very large and powerful framework that requires an expert to give you the best possible code that is free from bugs, maintainable, and robust. This open-source, front-end JavaScript framework will help you take your applications to the next level of design while saving your developers time and making their lives easier (thus, saving you money as well).

With these questions, you’ll cover the most important concepts to make sure that you have an AngularJS developer who can provide you with the code and applications that you need. Contact Distant Job so you can relax while we find the most qualified candidate who can ace all of these questions and contribute to your team as an AngularJS developer.