Welcome!

Java IoT Authors: Yeshim Deniz, Pat Romanski, Liz McMillan, Zakia Bouachraoui, Carmen Gonzalez

Related Topics: @CloudExpo, Java IoT, Machine Learning

@CloudExpo: Blog Feed Post

Angular 2: Guarding Routes | @CloudExpo #API #Cloud #Angular2

Here are some scenarios that require a certain validation to be performed

In this blog I’ll show you how to guard routes in Angular 2 Router (currently at 3.0.0-beta.2).

Let’s consider some scenarios that require a certain validation to be performed to decide if the user (or a program) is allowed to navigate to or leave the route:

  • Allowed to open the route only if the user is authenticated and authorized to do so.
  • Implement a multi-part form that consists of several components, and the user is allowed to navigate to the next form section only if the data entered in the current one is valid.
  • Allow to navigate to a route only after a certain data structures have been populated.
  • Remind the user about the unsaved changes if he or she tries to navigate from the route.

The router has the hooks that give you more control over the navigation to/from a route, and you can use these hooks to implement the any of above scenarios to guard the routes.

Angular includes a number of component lifecycle hooks that allow you to handle important events in the life of a component. First, it worth noting that the route configuration is done outside of the components. You configure routes in an object of type RouterConfig, then give it to the provideRouter() function, which in turn is given to the function bootstrap() that loads your app.

The type RouterConfig that implements the Route interface shown below:

export interface Route {
path?: string;
terminal?: boolean;
component?: Type | string;
outlet?: string;
canActivate?: any[];
canDeactivate?: any[];
redirectTo?: string;
children?: Route[];
}

While configuring routes you’ll typically use two properties from this interface: path and component. For example, an app that has two links Home and Product Details can specify and bootstrap the routes as follows:

bootstrap(RootComponent, [
provideRouter([
{path: '', component: HomeComponent},
{path: 'product', component: ProductDetailComponent}]),
{provide: LocationStrategy, useClass: HashLocationStrategy}
]);

But in this blog I’d like to you to get familiar with the properties canActivate and canDeactivate that allow you to hook up the routes with the guards. Basically you need to write a function(s) implementing the validating logic that will return either true or false and assign it to one of these properties. If canActivate is equal to true, the user can navigate to the route. If canDeactivate is true, the user can navigate from the route. Since each of these properties accept an array as a value, you can assign multiple functions (the guards) if you need to check more than one condition to allow or forbid the navigation.

Let’s create a simple app with Home and Product Details links to illustrate how you can protect the product route from the users who are not logged in. To keep the example simple, we won’t use an actual login service, but will generate the login status randomly.

We’ll create a guard class that implements the interface CanActivate, which declares only one function to implement: canActivate(). This function should contain the application logic that returns true or false. If the function returns false (the user is not logged in) the application will not navigate to the route and will print the error message on the console.

import {CanActivate} from "@angular/router";
import {Injectable} from "@angular/core";

@Injectable()
export class LoginGuard implements CanActivate{

canActivate() {
return this.checkIfLoggedIn();
}

private checkIfLoggedIn(): boolean{

// A call to the actual login service would go here
// For now we'll just randomly return true or false

let loggedIn:boolean = Math.random() < 0.5;

if(!loggedIn){
console.log("LoginGuard: The user is not logged in and can't navigate product details");
}

return loggedIn;
}
}

As you see from the code, our implementation of the function canActivate() will randomly return true or false emulating the user’s logged in status.

The next step is to update the router configuration so it uses our guard. The code snippet below shows how the function provideRouter() can look like for the app that has Home and Product Detail routes and the latter is protected by our LoginGuard:

provideRouter([
{path: '', component: HomeComponent},
{path: 'product', component: ProductDetailComponent,
canActivate:[LoginGuard]}
])

Adding one or more guards to the array given to the canActivate property will automatically invoke all guards one after the other. If any of the guards returns false, the navigation to the route will be prohibited.

But who will instantiate the class LoginGuard? Angular will do it for use using its dependency injection mechanism, but you have to mention this class in the list of providers which are needed for injection to work. We’ll just add the name LoginGuard to the list of providers in the bootstrap() function of our app:

bootstrap(RootComponent, [
provideRouter([
{path: '', component: HomeComponent},
{path: 'product', component: ProductDetailComponent,

canActivate:[LoginGuard]}]),
LoginGuard,
{provide: LocationStrategy, useClass: HashLocationStrategy}
]);

The complete code of the main app script is shown next:

import {bootstrap} from '@angular/platform-browser-dynamic';
import {Component} from '@angular/core';
import {LocationStrategy, HashLocationStrategy} from '@angular/common';
import {provideRouter, ROUTER_DIRECTIVES} from '@angular/router';

import {HomeComponent} from './components/home';
import {ProductDetailComponent} from './components/product';

import {LoginGuard} from './guards/login.guard';

@Component({
selector: 'basic-routing',
directives: [ROUTER_DIRECTIVES],
template: `
<a>Home</a>
<a>Product Details</a>


` })
class RootComponent {}

bootstrap(RootComponent, [
provideRouter([
{path: '', component: HomeComponent},
{path: 'product', component: ProductDetailComponent,
canActivate:[LoginGuard]}]),
LoginGuard,
{provide: LocationStrategy, useClass: HashLocationStrategy}
]);

If you run this app and will try to lick on the Product Details link, it’ll either navigate to this route or print the error message on the browser console depending on the randomly generated value in the LoginGuard. The snapshot below was taken after the user tried to click on the Product Details link, but the LoginGuard “decided” that the user is not logged in.

ch3_loginguard

But if our unpredictable LoginGuard “decided” that the user is logged in, the screen will look as follows after clicking on the Product Details link:

nonguarded

In the above example we implemented the method canActivate() without providing any arguments to it. But this method can be used with the following signature:

canActivate(destination: ActivatedRouteSnapshot,
state: RouterStateSnapshot)

The values of the ActivatedRouteSnapshot and RouterStateSnapshot will be injected by Angular automatically, and may be quite handy if you want to analyze the current state of the router. For example, if you’d like to know the name of the route the user tried to navigate to, this is how to do it:

canActivate(destination: ActivatedRouteSnapshot,
state: RouterStateSnapshot) {

console.log(destination.component.name);
...
}

Implementing the CanDeactivate interface that would control the process of navigating from a route works similarly. Just create a guard class that implements the method canDeactivate(), for example:

class UnsavedChangesGuard implements CanDeactivate{

canDeactivate(){

alert("You have unsaved changes");
}
}

For a fancier way of displaying alerts use the MdDialog component from the Material Design 2 library (see https://github.com/angular/material2). This component will be released in the upcoming Alpha 7.

In this blog I didn’t show you the code of HomeComponent and ProductDetail component, but you can find them in the Github repo with the code samples from Chapter 3 in our book Angular 2 Development with TypeScript.

If you’re interested in learning Angular 2 in depth, enroll into one of our workshops. The next one we’ll run online starting from September 11, 2016.

Read the original blog entry...

More Stories By Yakov Fain

Yakov Fain is a Java Champion and a co-founder of the IT consultancy Farata Systems and the product company SuranceBay. He wrote a thousand blogs (http://yakovfain.com) and several books about software development. Yakov authored and co-authored such books as "Angular 2 Development with TypeScript", "Java 24-Hour Trainer", and "Enterprise Web Development". His Twitter tag is @yfain

IoT & Smart Cities Stories
Dion Hinchcliffe is an internationally recognized digital expert, bestselling book author, frequent keynote speaker, analyst, futurist, and transformation expert based in Washington, DC. He is currently Chief Strategy Officer at the industry-leading digital strategy and online community solutions firm, 7Summits.
Digital Transformation is much more than a buzzword. The radical shift to digital mechanisms for almost every process is evident across all industries and verticals. This is often especially true in financial services, where the legacy environment is many times unable to keep up with the rapidly shifting demands of the consumer. The constant pressure to provide complete, omnichannel delivery of customer-facing solutions to meet both regulatory and customer demands is putting enormous pressure on...
IoT is rapidly becoming mainstream as more and more investments are made into the platforms and technology. As this movement continues to expand and gain momentum it creates a massive wall of noise that can be difficult to sift through. Unfortunately, this inevitably makes IoT less approachable for people to get started with and can hamper efforts to integrate this key technology into your own portfolio. There are so many connected products already in place today with many hundreds more on the h...
The standardization of container runtimes and images has sparked the creation of an almost overwhelming number of new open source projects that build on and otherwise work with these specifications. Of course, there's Kubernetes, which orchestrates and manages collections of containers. It was one of the first and best-known examples of projects that make containers truly useful for production use. However, more recently, the container ecosystem has truly exploded. A service mesh like Istio addr...
Digital Transformation: Preparing Cloud & IoT Security for the Age of Artificial Intelligence. As automation and artificial intelligence (AI) power solution development and delivery, many businesses need to build backend cloud capabilities. Well-poised organizations, marketing smart devices with AI and BlockChain capabilities prepare to refine compliance and regulatory capabilities in 2018. Volumes of health, financial, technical and privacy data, along with tightening compliance requirements by...
Charles Araujo is an industry analyst, internationally recognized authority on the Digital Enterprise and author of The Quantum Age of IT: Why Everything You Know About IT is About to Change. As Principal Analyst with Intellyx, he writes, speaks and advises organizations on how to navigate through this time of disruption. He is also the founder of The Institute for Digital Transformation and a sought after keynote speaker. He has been a regular contributor to both InformationWeek and CIO Insight...
Andrew Keys is Co-Founder of ConsenSys Enterprise. He comes to ConsenSys Enterprise with capital markets, technology and entrepreneurial experience. Previously, he worked for UBS investment bank in equities analysis. Later, he was responsible for the creation and distribution of life settlement products to hedge funds and investment banks. After, he co-founded a revenue cycle management company where he learned about Bitcoin and eventually Ethereal. Andrew's role at ConsenSys Enterprise is a mul...
To Really Work for Enterprises, MultiCloud Adoption Requires Far Better and Inclusive Cloud Monitoring and Cost Management … But How? Overwhelmingly, even as enterprises have adopted cloud computing and are expanding to multi-cloud computing, IT leaders remain concerned about how to monitor, manage and control costs across hybrid and multi-cloud deployments. It’s clear that traditional IT monitoring and management approaches, designed after all for on-premises data centers, are falling short in ...
In his general session at 19th Cloud Expo, Manish Dixit, VP of Product and Engineering at Dice, discussed how Dice leverages data insights and tools to help both tech professionals and recruiters better understand how skills relate to each other and which skills are in high demand using interactive visualizations and salary indicator tools to maximize earning potential. Manish Dixit is VP of Product and Engineering at Dice. As the leader of the Product, Engineering and Data Sciences team at D...
Dynatrace is an application performance management software company with products for the information technology departments and digital business owners of medium and large businesses. Building the Future of Monitoring with Artificial Intelligence. Today we can collect lots and lots of performance data. We build beautiful dashboards and even have fancy query languages to access and transform the data. Still performance data is a secret language only a couple of people understand. The more busine...