Angular support for TypeScript

Web Services

Angular web services are supported for both the older Http and new HttpClient (Angular ≥4.3) libraries. The method calls get, post, put, delete, jsonp, and request are recognized.

example web services

import { HttpClient } from '@angular/common/http';

// web-service_GET.ts
 
export class ExampleService {

  constructor(private http: HttpClient) { }
  getData() {
    const url = "http://httpbin.org/get";
    return this.http.get(url);
  }
}

The results of this code snippet are shown below.:

Finally the use of the rxjs/ajax API as web service call is also supported. The different types of web services (GET, POST, PUT, DELETE) are represented with the same Angular objects we have used above, despite they are not restricted to the Angular framework.

Angular components and HTML fragments

In addition to the basic TypeScript objects the analyzer will generate specific objects and links for the Angular framework. In the following example, the analyzer creates a TypeScript Module object associated with the file and a TypeScript Class object associated with the decorated class MyComponent. Angular components objects are created when finding special class decorators with the name Component. The view of Angular components is described in HTML language and the associated code can be either found in an external .html file or embedded in the decorator metadata. 

Link to html fragments

// example.ts
 
@Component({
  selector: 'click-me',
  template: `
    <button (click)="onClickMe()">Click me!</button>
    {{clickMessage}}`
})
export class MyComponent {
}

For embedded data, the analyzer creates an HTML5 HTML Fragment belonging to the component, and will automatically generate a use (U) link between the Component and the HTML fragment:

The generation of these links is necessary to describe the higher level call flow abstracted in the Angular framework and thus to retrieve transactions.

Event Emitter

An EventEmiiter emitts custom events and registers handlers for those events. An event can be emitted using the emit method of an EventEmitter instance as follows:

counter.component.ts

import { Component, Input, Output, EventEmitter } from '@angular/core';

@Component({
  selector: 'counter',
  template: `./counter.component.html`,
})
export class CounterComponent  {
  @Input() name: string;
  @Input() val: number;
  @Output() changed = new EventEmitter<number>()

  inc() {
    this.changed.emit(this.val + 1)
  }
}

In the previous example, the inc method emits an event to the changed EventEmitter. This event can be called in the template of an angular component:

app-component.html

<counter (changed)="my_callee($event)"></counter>

In that example, when a changed event is received, the my_callee method of the corresponding angular component is called:

app-component.ts

@Component({
//...
})
export class AppComponent  {

  my_callee(count: number){
//...
  }
}

When analyzing the previous source code, the com.castsoftware.typescript extension creates a callLink between the inc method and the *my_callee *method:

A subscription can also be added to an EventEmitter using the subscribe method of an EventEmitter:

app-component.ts

import { CounterComponent } from './counter.component';

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
})
export class AppComponent  {

  constructor(private counterComponent: CounterComponent) {
  }

  my_subscribe(){
     this.counterComponent.changed.subscribe((count: number) => {
       //...
     })
  }
}

When analyzing the previous source codes, a *callLink *is created between the inc method and the anonymous function given as argument of the subscribe call:

Environment variables

In our analysis, we consider a production deployment scenario. Thus we mimic the behavior of Angular when overloading behind-the-scenes the variables declared inside the exported environment dictionary defined in environment.ts  by those defined in environment.prod.ts. Global variables might be used to connect different technology layers (via URLs for example), thus retrieving them correctly can be critical for full transactions. The latest versions of Angular allow using many different production files. We only support a single production environment file, the standard environment.prod.ts. When using a no-production environment file a warning message will be logged.

// environment.ts
export const environment = { 
  production: false,
  urls = { .... }   // urls used for development
};
// environment.prod.ts
export const environment = { 
  production: true,
  urls = { .... }   // production urls
};

Injection with useValue

Dependencies are services or objects that a class needs to perform its function. Dependency injection, or DI, is a design pattern in which a class requests dependencies from external sources rather than creating them. The useValue key allows associating a fixed value with a Dependency Injection (DI) token. This is often used to provide runtime configuration constants such as website base addresses.

For instance, in the following, the Angular module provides an “environment” value.

import {Environment} from 'path/to/environmentinterface';
import { NgModule } from '@angular/core';

const environment: Environment = {
  my_url: "foo/path"
}

@NgModule({
  providers: [
    { provide: Environment, useValue: environment}
  ]
})
export class AppModule { 
}

This value can be accessed by other components through the constructor (note that the Type given to the “env” variable is the same as the one given in the provided key (see previous source code):

import { HttpClient } from '@angular/common/http';
import { Environment } from 'path/to/environmentinterface';
import { Component } from '@angular/core';


@Component()
export class FooClass{
  constructor (private http: HttpClient, private env : Environment){}

  getData() {
    const url = env.my_url;
    return this.http.get(url);
  }
}

Analyzing the previous modules will create a web service with the URL given through injection:  

Known limitations

  • Connectivity between components through Angular routing is not supported.
  • The support of TypeScript Map is limited. See the section Support of TypeScript Map to see which cases are supported.
  • Use of HttpRequest in Angular is not supported.