SPA開発(例えばVuejsなど)ではWebAPIのレスポンスをWebpackのDevServerでモックサービスとして稼働させることで開発効率を上げることは一般的な方法だと思っていたのだが、Angularだと(In-memory Web APIが主流なのか?)付属のwebpackだけではこれが実現できなかったので、備忘録として記事にまとめることにした。
想定環境
$ ng --version
_ _ ____ _ ___
/ \ _ __ __ _ _ _| | __ _ _ __ / ___| | |_ _|
/ △ \ | '_ \ / _` | | | | |/ _` | '__| | | | | | |
/ ___ \| | | | (_| | |_| | | (_| | | | |___| |___ | |
/_/ \_\_| |_|\__, |\__,_|_|\__,_|_| \____|_____|___|
|___/
Angular CLI: 12.1.2
Node: 14.15.4
Package Manager: npm 7.20.0
OS: darwin x64
Angular:
...
Package Version
------------------------------------------------------
@angular-devkit/architect 0.1201.2 (cli-only)
@angular-devkit/core 12.1.2 (cli-only)
@angular-devkit/schematics 12.1.2 (cli-only)
@schematics/angular 12.1.2 (cli-only)
プロジェクトを作成
ng
で作成する。特に設定変更せずデフォルトのまま。
$ ng new sample
// デフォルトのままエンター連打
$ tree ./sample
./sample
├── README.md
├── angular.json
├── karma.conf.js
├── node_modules
// 省略
├── package-lock.json
├── package.json
├── src
│ ├── app
│ ├── assets
│ ├── environments
│ ├── favicon.ico
│ ├── index.html
│ ├── main.ts
│ ├── polyfills.ts
│ ├── styles.css
│ └── test.ts
├── tree.txt
├── tsconfig.app.json
├── tsconfig.json
└── tsconfig.spec.json
custom-webpack
を追加
Angularにもともと付属しているWebpackでは実現できないので、custom-webpackを追加で導入し、angular.json
を設定する。
ついでに、DevServerの設定(extra-webpack.config.ts
)もTypeScriptで記述できるように@types/webpack-dev-server
も追加する。
$ npm i -D @angular-builders/custom-webpack
$ npm i -D @types/webpack-dev-server
"prefix": "app",
"architect": {
"build": {
- "builder": "@angular-devkit/build-angular:browser",
+ "builder": "@angular-builders/custom-webpack:browser",
"options": {
+ "customWebpackConfig": {
+ "path": "./extra-webpack.config.ts"
+ },
"outputPath": "dist/angular",
"index": "src/index.html",
"main": "src/main.ts",
}
},
"serve": {
- "builder": "@angular-devkit/build-angular:dev-server",
+ "builder": "@angular-builders/custom-webpack:dev-server",
"options": {
"browserTarget": "angular:build"
},
extra-webpack.config.ts を作成
モックサービスとなるWebAPIのレスポンスをextra-webpack.config.ts
に記述する。
$ tree ./sample
./sample
├── README.md
├── angular.json
├── extra-webpack.config.ts ## ここに新規作成
├── karma.conf.js
├── node_modules
├── package-lock.json
├── package.json
├── src
│ ├── app
│ ├── assets
│ ├── environments
│ ├── favicon.ico
│ ├── index.html
│ ├── main.ts
│ ├── polyfills.ts
│ ├── styles.css
│ └── test.ts
├── tree.txt
├── tsconfig.app.json
├── tsconfig.json
└── tsconfig.spec.json
import { Configuration } from 'webpack';
import 'webpack-dev-server';
export default {
devServer: {
before: (app, server) => {
app.get("/api/sample", (req, resp) => {
// モック内容を定義
resp.json({
resultCode: 0
});
});
}
}
} as Configuration;
クライアントコード作成
WebAPU呼び出しのサンプルコードを作成する。
+import { HttpClientModule } from '@angular/common/http';
@NgModule({
imports: [
BrowserModule,
+ HttpClientModule,
],
})
export class AppModule { }
import { Component } from '@angular/core';
+import { HttpClient, HttpErrorResponse } from '@angular/common/http';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.css']
})
export class AppComponent {
title = 'sample';
+ constructor(private http: HttpClient) {
+ http.get('/api/sample').toPromise()
+ .then(resp => {
+ alert(resp);
+ })
+ .catch((err: HttpErrorResponse) => {
+ console.error(err);
+ })
+ }
}
動作確認
アプリ起動してブラウザで開発者ツールを起動し、通信内容を確認すると/api/sample
をgetしていることがわかるはず。
$ ng serve --open
// ブラウザが起動するので開発者ツールを起動してコンソールを確認
まとめ
Angularでwebpackのdevserverをカスタマイズして使う方法をまとめてみたが、今回の内容は意外とググっても情報が少なかったように思う。
Angularの場合、公式ガイドラインにあるようにIn-memory Web APIを使うことでも目的を達成することができるためだろうか。
あるいはdevserverのproxy機能を利用して、モックではなく本物のWebAPIへリバースプロキシする方法もある。プロキシする場合は@angular-builders/custom-webpack
を使う必要はなく、Angular付属のwebpackのみで対応できるのでこっちのほうが手軽かもしれ合い。