Not
Åtkomst till den här sidan kräver auktorisering. Du kan prova att logga in eller ändra kataloger.
Åtkomst till den här sidan kräver auktorisering. Du kan prova att ändra kataloger.
Viktigt!
Från och med den 1 maj 2025 är Azure AD B2C inte längre tillgängligt att köpa för nya kunder. Läs mer i våra vanliga frågor och svar.
Den här artikeln visar hur du lägger till Azure Active Directory B2C-autentisering (Azure AD B2C) i ditt eget Angular-ensidesprogram (SPA). Lär dig hur du integrerar ett Angular-program med MSAL för Angular-autentiseringsbiblioteket .
Använd den här artikeln med den relaterade artikeln Konfigurera autentisering i ett angular-exempelprogram med en sida. Ersätt Angular-exempelappen med din egen Angular-app. När du har slutfört stegen i den här artikeln godkänner programmet inloggningar via Azure AD B2C.
Förutsättningar
Slutför stegen i artikeln Konfigurera autentisering i ett angular-exempelprogram med en sida .
Skapa ett Angular-appprojekt
Du kan använda ett befintligt Angular-appprojekt eller skapa ett nytt. Kör följande kommandon för att skapa ett nytt projekt.
Kommandona:
- Installera Angular CLI med hjälp av npm-pakethanteraren.
-
Skapa en Angular-arbetsyta med en routningsmodul. Appnamnet är
msal-angular-tutorial. Du kan ändra det till valfritt giltigt Angular-appnamn, till exempelcontoso-car-service. - Ändra till mappen appkatalog.
npm install -g @angular/cli
ng new msal-angular-tutorial --routing=true --style=css --strict=false
cd msal-angular-tutorial
Installera beroendena
Om du vill installera MSAL Browser - och MSAL Angular-biblioteken i ditt program kör du följande kommando i kommandogränssnittet:
npm install @azure/msal-browser @azure/msal-angular
Installera komponentbiblioteket för Angular Material (valfritt för användargränssnittet):
npm install @angular/material @angular/cdk
Lägg till autentiseringskomponenterna
Exempelkoden består av följande komponenter:
| Komponent | Typ | Beskrivning |
|---|---|---|
| auth-config.ts | Konstanter | Den här konfigurationsfilen innehåller information om din Azure AD B2C-identitetsprovider och webb-API-tjänsten. Angular-appen använder den här informationen för att upprätta en förtroenderelation med Azure AD B2C, logga in och logga ut användaren, hämta token och verifiera token. |
| app.module.ts | Angular-modul | Den här komponenten beskriver hur programdelarna passar ihop. Det här är rotmodulen som används för att starta och öppna programmet. I den här genomgången lägger du till några komponenter i modulen app.module.ts och startar MSAL-biblioteket med MSAL-konfigurationsobjektet. |
| app-routing.module.ts | Angular-routningsmodul | Den här komponenten aktiverar navigering genom att tolka en webbläsar-URL och läsa in motsvarande komponent. I den här genomgången lägger du till några komponenter i routningsmodulen och skyddar komponenter med MSAL Guard. Endast behöriga användare kan komma åt de skyddade komponenterna. |
| app.component.* | Angular-komponent | Kommandot ng new skapade ett Angular-projekt med en rotkomponent. I den här genomgången ändrar du appkomponenten så att den är värd för det övre navigeringsfältet. Navigeringsfältet innehåller olika knappar, inklusive inloggnings- och utloggningsknappar. Klassen app.component.ts hanterar inloggnings- och utloggningshändelserna. |
| hem.component.* | Angular-komponent | I den här genomgången lägger du till hemkomponenten för att återge startsidan för anonym åtkomst. Den här komponenten visar hur du kontrollerar om en användare har loggat in. |
| profil.komponent.* | Angular-komponent | I den här genomgången lägger du till profilkomponenten för att lära dig hur du läser ID-tokenanspråken. |
| webapi.* | Angular-komponent | I den här genomgången lägger du till webapi-komponenten för att lära dig hur du anropar ett webb-API. |
Om du vill lägga till följande komponenter i din app kör du följande Angular CLI-kommandon. Kommandona generate component :
- Skapa en mapp för varje komponent. Mappen innehåller TypeScript-, HTML-, CSS- och testfilerna.
- Uppdatera
app.module.ts-filerna ochapp-routing.module.ts-filerna med referenser till de nya komponenterna.
ng generate component home
ng generate component profile
ng generate component webapi
Lägg till appinställningarna
Inställningar för Azure AD B2C-identitetsprovidern och webb-API:et lagras i filen auth-config.ts . I mappen src/app skapar du en fil med namnet auth-config.ts som innehåller följande kod. Ändra sedan inställningarna enligt beskrivningen i 3.1 Konfigurera Angular-exemplet.
import { LogLevel, Configuration, BrowserCacheLocation } from '@azure/msal-browser';
const isIE = window.navigator.userAgent.indexOf("MSIE ") > -1 || window.navigator.userAgent.indexOf("Trident/") > -1;
export const b2cPolicies = {
names: {
signUpSignIn: "b2c_1_susi_reset_v2",
editProfile: "b2c_1_edit_profile_v2"
},
authorities: {
signUpSignIn: {
authority: "https://your-tenant-name.b2clogin.com/your-tenant-name.onmicrosoft.com/b2c_1_susi_reset_v2",
},
editProfile: {
authority: "https://your-tenant-name.b2clogin.com/your-tenant-name.onmicrosoft.com/b2c_1_edit_profile_v2"
}
},
authorityDomain: "your-tenant-name.b2clogin.com"
};
export const msalConfig: Configuration = {
auth: {
clientId: '<your-MyApp-application-ID>',
authority: b2cPolicies.authorities.signUpSignIn.authority,
knownAuthorities: [b2cPolicies.authorityDomain],
redirectUri: '/',
},
cache: {
cacheLocation: BrowserCacheLocation.LocalStorage,
storeAuthStateInCookie: isIE,
},
system: {
loggerOptions: {
loggerCallback: (logLevel, message, containsPii) => {
console.log(message);
},
logLevel: LogLevel.Verbose,
piiLoggingEnabled: false
}
}
}
export const protectedResources = {
todoListApi: {
endpoint: "http://localhost:5000/api/todolist",
scopes: ["https://your-tenant-name.onmicrosoft.com/api/tasks.read"],
},
}
export const loginRequest = {
scopes: []
};
Initiera autentiseringsbiblioteken
Offentliga klientprogram är inte betrodda för att bevara programhemligheter på ett säkert sätt, så de har inga klienthemligheter. I mappen src/app öppnar du app.module.ts och gör följande ändringar:
- Importera MSAL Angular- och MSAL Browser-biblioteken.
- Importera Azure AD B2C-konfigurationsmodulen.
- Importera
HttpClientModule. HTTP-klienten används för att anropa webb-API:er. - Importera Angular HTTP-avlyssningstjänsten. MSAL använder interceptorn för att infoga bärartoken i HTTP-auktoriseringsheadern.
- Lägg till de viktigaste Angular-materialen.
- Instansiera MSAL med hjälp av det offentliga klientprogramobjektet för flera konton. MSAL-initieringen omfattar att skicka:
- Konfigurationsobjektet för auth-config.ts.
- Konfigurationsobjektet för routskyddet.
- Konfigurationsobjektet för MSAL-avlyssnaren. Interceptorklassen hämtar automatiskt token för utgående begäranden som använder klassen Angular HttpClient för kända skyddade resurser.
- Konfigurera
HTTP_INTERCEPTORSochMsalGuardangularprovidrar. - Lägg till
MsalRedirectComponenti Angular bootstrap.
I mappen src/app redigerar du app.module.ts och gör ändringarna som visas i följande kodfragment. Ändringarna flaggas med "Ändringarna börjar här" och "Ändringarna slutar här".
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
/* Changes start here. */
// Import MSAL and MSAL browser libraries.
import { MsalGuard, MsalInterceptor, MsalModule, MsalRedirectComponent } from '@azure/msal-angular';
import { InteractionType, PublicClientApplication } from '@azure/msal-browser';
// Import the Azure AD B2C configuration
import { msalConfig, protectedResources } from './auth-config';
// Import the Angular HTTP interceptor.
import { HttpClientModule, HTTP_INTERCEPTORS } from '@angular/common/http';
import { ProfileComponent } from './profile/profile.component';
import { HomeComponent } from './home/home.component';
import { WebapiComponent } from './webapi/webapi.component';
// Add the essential Angular materials.
import { MatButtonModule } from '@angular/material/button';
import { MatToolbarModule } from '@angular/material/toolbar';
import { MatListModule } from '@angular/material/list';
import { MatTableModule } from '@angular/material/table';
/* Changes end here. */
@NgModule({
declarations: [
AppComponent,
ProfileComponent,
HomeComponent,
WebapiComponent
],
imports: [
BrowserModule,
AppRoutingModule,
/* Changes start here. */
// Import the following Angular materials.
MatButtonModule,
MatToolbarModule,
MatListModule,
MatTableModule,
// Import the HTTP client.
HttpClientModule,
// Initiate the MSAL library with the MSAL configuration object
MsalModule.forRoot(new PublicClientApplication(msalConfig),
{
// The routing guard configuration.
interactionType: InteractionType.Redirect,
authRequest: {
scopes: protectedResources.todoListApi.scopes
}
},
{
// MSAL interceptor configuration.
// The protected resource mapping maps your web API with the corresponding app scopes. If your code needs to call another web API, add the URI mapping here.
interactionType: InteractionType.Redirect,
protectedResourceMap: new Map([
[protectedResources.todoListApi.endpoint, protectedResources.todoListApi.scopes]
])
})
/* Changes end here. */
],
providers: [
/* Changes start here. */
{
provide: HTTP_INTERCEPTORS,
useClass: MsalInterceptor,
multi: true
},
MsalGuard
/* Changes end here. */
],
bootstrap: [
AppComponent,
/* Changes start here. */
MsalRedirectComponent
/* Changes end here. */
]
})
export class AppModule { }
Konfigurera vägar
I det här avsnittet konfigurerar du vägarna för ditt Angular-program. När en användare väljer en länk på sidan för att flytta i ditt ensidesprogram eller anger en URL i adressfältet mappar vägarna URL:en till en Angular-komponent. Angular-routnings canActivate-gränssnittet använder MSAL Guard för att kontrollera om användaren är inloggad. Om användaren inte är inloggad tar MSAL användaren till Azure AD B2C för att autentisera.
I mappen src/app, gör ändringarna som visas i följande kodfragment genom att redigera app-routing.module.ts. Ändringarna flaggas med "Ändringarna börjar här" och "Ändringarna slutar här".
import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { MsalGuard } from '@azure/msal-angular';
import { HomeComponent } from './home/home.component';
import { ProfileComponent } from './profile/profile.component';
import { WebapiComponent } from './webapi/webapi.component';
const routes: Routes = [
/* Changes start here. */
{
path: 'profile',
component: ProfileComponent,
// The profile component is protected with MSAL Guard.
canActivate: [MsalGuard]
},
{
path: 'webapi',
component: WebapiComponent,
// The profile component is protected with MSAL Guard.
canActivate: [MsalGuard]
},
{
// The home component allows anonymous access
path: '',
component: HomeComponent
}
/* Changes end here. */
];
@NgModule({
/* Changes start here. */
// Replace the following line with the next one
//imports: [RouterModule.forRoot(routes)],
imports: [RouterModule.forRoot(routes, {
initialNavigation:'enabled'
})],
/* Changes end here. */
exports: [RouterModule]
})
export class AppRoutingModule { }
Lägg till inloggnings- och utloggningsknapparna
I det här avsnittet lägger du till knapparna för inloggning och utloggning i appkomponenten . I mappen src/app öppnar du filen app.component.ts och gör följande ändringar:
Importera nödvändiga komponenter.
Ändra klassen för att implementera metoden OnInit. Metoden
OnInitprenumererar på den observerbara händelsen MSAL MsalBroadcastServiceinProgress$. Använd den här händelsen för att känna till statusen för användarinteraktioner, särskilt för att kontrollera att interaktioner har slutförts.Innan du interagerar med MSAL-kontoobjektet kontrollerar du att egenskapen
InteractionStatusreturnerarInteractionStatus.None. HändelsensubscribeanroparsetLoginDisplaymetoden för att kontrollera om användaren är autentiserad.Lägg till klassvariabler.
Lägg till metoden
loginsom startar auktoriseringsflödet.Lägg till metoden
logoutsom loggar ut användaren.Lägg till den
setLoginDisplaymetod som kontrollerar om användaren är autentiserad.Lägg till metoden ngOnDestroy för att rensa prenumerationshändelsen
inProgress$.
Efter ändringarna bör koden se ut som följande kodfragment:
import { Component, OnInit, Inject } from '@angular/core';
import { MsalService, MsalBroadcastService, MSAL_GUARD_CONFIG, MsalGuardConfiguration } from '@azure/msal-angular';
import { InteractionStatus, RedirectRequest } from '@azure/msal-browser';
import { Subject } from 'rxjs';
import { filter, takeUntil } from 'rxjs/operators';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
/* Changes start here. */
export class AppComponent implements OnInit{
title = 'msal-angular-tutorial';
loginDisplay = false;
private readonly _destroying$ = new Subject<void>();
constructor(@Inject(MSAL_GUARD_CONFIG) private msalGuardConfig: MsalGuardConfiguration, private broadcastService: MsalBroadcastService, private authService: MsalService) { }
ngOnInit() {
this.broadcastService.inProgress$
.pipe(
filter((status: InteractionStatus) => status === InteractionStatus.None),
takeUntil(this._destroying$)
)
.subscribe(() => {
this.setLoginDisplay();
})
}
login() {
if (this.msalGuardConfig.authRequest){
this.authService.loginRedirect({...this.msalGuardConfig.authRequest} as RedirectRequest);
} else {
this.authService.loginRedirect();
}
}
logout() {
this.authService.logoutRedirect({
postLogoutRedirectUri: 'http://localhost:4200'
});
}
setLoginDisplay() {
this.loginDisplay = this.authService.instance.getAllAccounts().length > 0;
}
ngOnDestroy(): void {
this._destroying$.next(undefined);
this._destroying$.complete();
}
/* Changes end here. */
}
I mappen src/app redigerar du app.component.html och gör följande ändringar:
- Lägg till en länk till profil- och webb-API-komponenterna.
- Lägg till inloggningsknappen med klickhändelseattributet inställt på
login()metoden. Den här knappen visas bara omloginDisplayklassvariabeln ärfalse. - Lägg till utloggningsknappen med klickhändelseattributet inställt på
logout()metoden. Den här knappen visas bara omloginDisplayklassvariabeln ärtrue. - Lägg till ett router-outlet-element .
Efter ändringarna bör koden se ut som följande kodfragment:
<mat-toolbar color="primary">
<a class="title" href="/">{{ title }}</a>
<div class="toolbar-spacer"></div>
<a mat-button [routerLink]="['profile']">Profile</a>
<a mat-button [routerLink]="['webapi']">Web API</a>
<button mat-raised-button *ngIf="!loginDisplay" (click)="login()">Login</button>
<button mat-raised-button *ngIf="loginDisplay" (click)="logout()">Logout</button>
</mat-toolbar>
<div class="container">
<router-outlet></router-outlet>
</div>
Du kan också uppdatera app.component.css-filen med följande CSS-kodfragment:
.toolbar-spacer {
flex: 1 1 auto;
}
a.title {
color: white;
}
Hantera appomdirigeringar
När du använder omdirigeringar med MSAL måste du lägga till direktivet app-redirect i index.html. I mappen src redigerar du index.html enligt följande kodfragment:
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>MsalAngularTutorial</title>
<base href="/">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="icon" type="image/x-icon" href="favicon.ico">
</head>
<body>
<app-root></app-root>
<!-- Changes start here -->
<app-redirect></app-redirect>
<!-- Changes end here -->
</body>
</html>
Ange app-CSS (valfritt)
I mappen /src uppdaterar du styles.css-filen med följande CSS-kodfragment:
@import '~@angular/material/prebuilt-themes/deeppurple-amber.css';
html, body { height: 100%; }
body { margin: 0; font-family: Roboto, "Helvetica Neue", sans-serif; }
.container { margin: 1%; }
Tips/Råd
Nu kan du köra din app och testa inloggningsupplevelsen. Information om hur du kör din app finns i avsnittet Kör Angular-programmet .
Kontrollera om en användare är autentiserad
Filen home.component visar hur du kontrollerar om användaren är autentiserad. I mappen src/app/home uppdaterar du home.component.ts med följande kodfragment.
Koden:
- Prenumererar på MSAL MsalBroadcastService
msalSubject$ochinProgress$observerbara händelser. - Ser till att händelsen
msalSubject$skriver autentiseringsresultatet till webbläsarkonsolen. - Ser till att
inProgress$-händelsen kontrollerar om en användare är autentiserad. MetodengetAllAccounts()returnerar ett eller flera objekt.
import { Component, OnInit } from '@angular/core';
import { MsalBroadcastService, MsalService } from '@azure/msal-angular';
import { EventMessage, EventType, InteractionStatus } from '@azure/msal-browser';
import { filter } from 'rxjs/operators';
@Component({
selector: 'app-home',
templateUrl: './home.component.html',
styleUrls: ['./home.component.css']
})
export class HomeComponent implements OnInit {
loginDisplay = false;
constructor(private authService: MsalService, private msalBroadcastService: MsalBroadcastService) { }
ngOnInit(): void {
this.msalBroadcastService.msalSubject$
.pipe(
filter((msg: EventMessage) => msg.eventType === EventType.LOGIN_SUCCESS),
)
.subscribe((result: EventMessage) => {
console.log(result);
});
this.msalBroadcastService.inProgress$
.pipe(
filter((status: InteractionStatus) => status === InteractionStatus.None)
)
.subscribe(() => {
this.setLoginDisplay();
})
}
setLoginDisplay() {
this.loginDisplay = this.authService.instance.getAllAccounts().length > 0;
}
}
I mappen src/app/home uppdaterar du home.component.html med följande HTML-kodavsnitt.
*ngIf-direktivet kontrollerar loginDisplay klassvariabeln för att visa eller dölja välkomstmeddelandena.
<div *ngIf="!loginDisplay">
<p>Please sign-in to see your profile information.</p>
</div>
<div *ngIf="loginDisplay">
<p>Login successful!</p>
<p>Request your profile information by clicking Profile above.</p>
</div>
Läs ID-tokenanspråken
Filen profile.component visar hur du kommer åt användarens ID-tokenanspråk. I mappen src/app/profile uppdaterar du profile.component.ts med följande kodfragment.
Koden:
- Importerar nödvändiga komponenter.
- Prenumererar på den observerbara händelsen MSAL MsalBroadcastService
inProgress$. Händelsen laddar kontot och läser ID-tokenanspråken. - Säkerställer att
checkAndSetActiveAccountmetoden kontrollerar och anger det aktiva kontot. Den här åtgärden är vanlig när appen interagerar med flera Azure AD B2C-användarflöden eller anpassade principer. - Säkerställer att
getClaimsmetoden hämtar ID-tokenanspråken från det aktiva MSAL-kontoobjektet. Metoden lägger sedan till anspråken i matrisendataSource. Matrisen återges till användaren med komponentens mallbindning.
import { Component, OnInit } from '@angular/core';
import { MsalBroadcastService, MsalService } from '@azure/msal-angular';
import { EventMessage, EventType, InteractionStatus } from '@azure/msal-browser';
import { Subject } from 'rxjs';
import { filter, takeUntil } from 'rxjs/operators';
@Component({
selector: 'app-profile',
templateUrl: './profile.component.html',
styleUrls: ['./profile.component.css']
})
export class ProfileComponent implements OnInit {
displayedColumns: string[] = ['claim', 'value'];
dataSource: Claim[] = [];
private readonly _destroying$ = new Subject<void>();
constructor(private authService: MsalService, private msalBroadcastService: MsalBroadcastService) { }
ngOnInit(): void {
this.msalBroadcastService.inProgress$
.pipe(
filter((status: InteractionStatus) => status === InteractionStatus.None || status === InteractionStatus.HandleRedirect),
takeUntil(this._destroying$)
)
.subscribe(() => {
this.checkAndSetActiveAccount();
this.getClaims(this.authService.instance.getActiveAccount()?.idTokenClaims)
})
}
checkAndSetActiveAccount() {
let activeAccount = this.authService.instance.getActiveAccount();
if (!activeAccount && this.authService.instance.getAllAccounts().length > 0) {
let accounts = this.authService.instance.getAllAccounts();
this.authService.instance.setActiveAccount(accounts[0]);
}
}
getClaims(claims: any) {
let list: Claim[] = new Array<Claim>();
Object.keys(claims).forEach(function(k, v){
let c = new Claim()
c.id = v;
c.claim = k;
c.value = claims ? claims[k]: null;
list.push(c);
});
this.dataSource = list;
}
ngOnDestroy(): void {
this._destroying$.next(undefined);
this._destroying$.complete();
}
}
export class Claim {
id: number;
claim: string;
value: string;
}
I mappen src/app/profile uppdaterar du profile.component.html med följande HTML-kodavsnitt:
<h1>ID token claims:</h1>
<table mat-table [dataSource]="dataSource" class="mat-elevation-z8">
<!-- Claim Column -->
<ng-container matColumnDef="claim">
<th mat-header-cell *matHeaderCellDef> Claim </th>
<td mat-cell *matCellDef="let element"> {{element.claim}} </td>
</ng-container>
<!-- Value Column -->
<ng-container matColumnDef="value">
<th mat-header-cell *matHeaderCellDef> Value </th>
<td mat-cell *matCellDef="let element"> {{element.value}} </td>
</ng-container>
<tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
<tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>
Anropa ett webb-API
Om du vill anropa ett webb-API för tokenbaserad auktorisering måste appen ha en giltig åtkomsttoken. MsalInterceptor-providern hämtar automatiskt token för utgående begäranden som använder klassen Angular HttpClient till kända skyddade resurser.
Viktigt!
MSAL-initieringsmetoden (i app.module.ts klassen) mappar skyddade resurser, till exempel webb-API:er, med nödvändiga appomfattningar med hjälp protectedResourceMap av objektet. Om koden behöver anropa ett annat webb-API lägger du till webb-API-URI:n och HTTP-metoden för webb-API:et, med motsvarande omfång, i protectedResourceMap objektet. Mer information finns i Skyddad resurskarta.
När HttpClient-objektet anropar ett webb-API utför MsalInterceptor-providern följande steg:
Hämtar en åtkomsttoken med nödvändiga behörigheter (omfång) för webb-API-slutpunkten.
Skickar åtkomsttoken som en bearertoken i auktoriseringshuvudet för HTTP-begäran med det här formatet:
Authorization: Bearer <access-token>
Filen webapi.component visar hur du anropar ett webb-API. I mappen src/app/webapi uppdaterar du webapi.component.ts med följande kodfragment.
Koden:
- Använder klassen Angular HttpClient för att anropa webb-API:et.
- Läser
auth-configklassensprotectedResources.todoListApi.endpointelement. Det här elementet anger webb-API-URI:n. Baserat på webb-API-URI:n hämtar MSAL-interceptorn en åtkomsttoken med motsvarande omfång. - Hämtar profilen från webb-API:et och anger
profileklassvariabeln.
import { Component, OnInit } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { protectedResources } from '../auth-config';
type ProfileType = {
name?: string
};
@Component({
selector: 'app-webapi',
templateUrl: './webapi.component.html',
styleUrls: ['./webapi.component.css']
})
export class WebapiComponent implements OnInit {
todoListEndpoint: string = protectedResources.todoListApi.endpoint;
profile!: ProfileType;
constructor(
private http: HttpClient
) { }
ngOnInit() {
this.getProfile();
}
getProfile() {
this.http.get(this.todoListEndpoint)
.subscribe(profile => {
this.profile = profile;
});
}
}
I mappen src/app/webapi uppdaterar du webapi.component.html med följande HTML-kodfragment. Komponentens mall återger det namn som webb-API:et returnerar. Längst ned på sidan renderar mallen webbadressen till webb-API:et.
<h1>The web API returns:</h1>
<div>
<p><strong>Name: </strong> {{profile?.name}}</p>
</div>
<div class="footer-text">
Web API: {{todoListEndpoint}}
</div>
Du kan också uppdatera webapi.component.css-filen med följande CSS-kodfragment:
.footer-text {
position: absolute;
bottom: 50px;
color: gray;
}
Kör Angular-programmet
Kör följande kommando:
npm start
Konsolfönstret visar antalet portar där programmet finns.
Listening on port 4200...
Tips/Råd
Du kan också köra npm start kommandot genom att använda Felsökningsprogrammet för Visual Studio Code. Felsökningsprogrammet hjälper dig att påskynda din redigerings-, kompilerings- och felsökningsloop.
Gå till http://localhost:4200 i webbläsaren för att visa programmet.