Angular 4 教學 - Multiple Modules

-- Pageviews

Angular 4 教學 - Multiple Modules 範例執行結果

本篇將介紹 Angular 4 的 Routing 在多個 Modules 的情況下,實現 Single Page Application(SPA)。

程式碼延續前兩篇的範例:
ASP.NET Core + Angular 4 教學 - 從無到有
ASP.NET Core + Angular 4 教學 - Webpack打包

ASP.NET Core Routing 不熟悉的話,請先參考:
ASP.NET Core + Angular 4 教學 - Routing

1. Single Module

1.2 File Structure

首先我建立兩個資料夾分別為 firstsecond,各三個 Component 為 one.componenttwo.componentthree.component
檔案結構如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
index.html
app/
main.ts
app.component.ts
app.component.html
app.routes.ts
components/
first/
one.component.ts
two.component.ts
three.component.ts
second/
one.component.ts
two.component.ts
three.component.ts

1.2 Routing

在 main.ts 中,會有 Angular 進入點的 Module,如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
//...

@NgModule({
imports: [
BrowserModule,
RouterModule.forRoot(AppRoutes.getRoutes())
],
declarations: [
AppComponent,
AppRoutes.getComponents()
],
bootstrap: [
AppComponent
]
})
export class AppModule { }

platformBrowserDynamic().bootstrapModule(AppModule);

如過不想拆分模組,可以把 Routing 全部註冊在 app.routes.ts,例如:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
// ...

const routes: RouteItem[] = [
{
path: "",
redirectTo: "first",
pathMatch: "full",
},
{
path: "first",
children: [
{
path: "",
redirectTo: "one",
pathMatch: "full"
},
{
path: "one",
component: First.OneComponent
},
{
path: "two",
component: First.TwoComponent
},
{
path: "three",
component: First.ThreeComponent
}
]
},
{
path: "second",
children: [
{
path: "",
redirectTo: "one",
pathMatch: "full"
},
{
path: "one",
component: Second.OneComponent
},
{
path: "two",
component: Second.TwoComponent
},
{
path: "three",
component: Second.ThreeComponent
}
]
},
];

export class AppRoutes {
public static getRoutes(): RouteItem[] {
return routes;
}

public static getComponents(): any[] {
return RouteUtil.getComponents(routes);
}
}

但隨著系統越做越大,這樣的架構並不是這麼好管理,而且效能也會比較差,所以就會建議拆分多個模組。

2. Multiple Modules

2.1 File Structure

firstsecond 這兩個資料夾,變成兩個模組,分別加入一個 *.routes.ts。 同時改變上述的檔案結構,如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
index.html
app/
main.ts
app.component.ts
app.component.html
app.routes.ts
first/
first.routes.ts
components/
one.component.ts
two.component.ts
three.component.ts
second/
second.routes.ts
components/
one.component.ts
two.component.ts
three.component.ts

有關檔案結構可參考:Angular 4 File Structure

2.2 Routing

first.routes.ts

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
// ...

const routes: Route[] = [
{
path: "",
redirectTo: "one",
pathMatch: "full",
}, {
path: "one",
component: OneComponent
}, {
path: "two",
component: TwoComponent
}, {
path: "three",
component: ThreeComponent
}
];

@NgModule({
imports: [
RouterModule.forChild(routes)
],
declarations: [
RouteUtil.getComponents(routes)
],
exports: [
RouterModule
]
})
export class FirstModule { }

會發現 first.routes.ts 很像是 main.ts 及 app.routes.ts 的綜合體,基本上也可以把 first.routes.ts 拆成兩個 ts,分別為:

  • first.ts 負責宣告 NgModule,如同 main.ts。
  • first.routes.ts 負責管理 routes,如同 app.routes.ts。

因為 second.routes.ts 幾乎一樣,所以省略說明。

透過 loadChildren 把 FirstModule 及 SecondModule 加到 app.routes.ts 的路由中:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
// ...

const routes: Route[] = [
{
path: "",
redirectTo: "first",
pathMatch: "full",
},
{
path: "first",
loadChildren: () => FirstModule
},
{
path: "second",
loadChildren: () => SecondModule
}
];

export class AppRoutes {
public static getRoutes(): Route[] {
return routes;
}

public static getComponents(): any[] {
return RouteUtil.getComponents(routes);
}
}

路由只要指到 /first,就會去找 FirstModule 裡面的 RouterModule.forChild(routes),接力完成路由。
用 loadChildren 就可以輕鬆完成多模組的路由了。

2.3 執行結果

Angular 4 教學 - Multiple Modules 範例執行結果

程式碼下載

asp-net-core-angular-routing

範例程式是用 ASP.NET Core + Angular 4,Angular 4 要改成 lite-server 執行的話,可以參考 Angular 4 教學 - 從頭開始