ESP32 で Angular アプリケーション

ESP32 で Web サーバを立てて,Angular アプリケーションを動かす方法を紹介します.

はじめに

ESP32 に Web API を実装する場合,簡易的な Web UI もつけたくなったりしますが,まとまった資料がなかったので紹介します.

Angular 側で準備を行った後,ESP32 へ組み込んでいきます.

Angular 側の準備

Angular 側でやることは,大きく次の2つがあります.順に説明していきます.

  • ファイル名のランダム化の停止
  • ファイルの圧縮と配置パスの指定

ファイル名のランダム化の停止

ng build --prod で普通に Angular アプリをビルドすると,下記のようにファイル名がランダム化されています.ファイル名が一意に決まらないと ESP32 への組み込みに不便なので,この機能を停止させます.

angular.json の中の "outputHashing": "none","outputHashing": "none", に変更すれば OK です.

ファイルの圧縮と配置パスの指定

Angular アプリはシンプルなものでもサイズがそれなりに大きくなってしまいます.小さなアプリであればそのままでも収まるかもしれませんが,ESP32 の Flash サイズは潤沢ではないので,gzip で圧縮して配信しておくのがおすすめです.

そのため,下記のような Makefile を使って圧縮されたファイルを生成するようにします.「esp32-wifi-io」は,お使いの Angular アプリケーション名で置き換えてください.

ng build を実行する際に,アプリを配置するパスを指定しています.Angular アプリを ESP32 で配信する場合,おそらく API サーバも ESP32 で動かすことになると思います.ルートではなく /app にアプリを配置し,API のエンドポイントを /api に配置すると,配信の際の扱いがしやすくなります.

実行すると下記のようになり,676KB あったものが約 1/4 の 176KB になっていることが分かります.これなら,ROM サイズ(4MB)に対してかなり小さいので,サイズを気にせずにアプリ開発が行えます.

ESP32 への組み込み

以上で準備したファイルを ESP32 から配信できるようにします.ESP-IDF の使用を前提に,順に説明していきます.

  • ファームへのファイルの組み込み
  • サーバによるファイルの配信

ファームへのファイルの組み込み

main/component.mk に次のように記載します.これにより,生成されるファイルに Angular アプリケーションが組み込まれるようになります.

「../angular/dist/esp32-wifi-io/」は,生成した Angular アプリケーションの相対パスで置き換えてください.

サーバによるファイルの配信

まずは全体像を示します.下記のコードで Angular アプリを配信できるようになります.

APP_PATH は,Angular アプリをビルドしたときの --base-href= の指定と合わせておきます.

コードのポイントを順に説明します.

ファイルデータの取得

COMPONENT_EMBED_FILES で指定して組み込んだファイルデータの開始・終了アドレスは,次のようにして取得できます.

アドレスさえ取得できれば,あとは httpd_resp_send_chunk にて送信データとして指定してやれば配信できます.

gzip ファイルの配信

上のほうで HTML 以外は gzip で圧縮しました.そのため,次のようにして,圧縮されていることをブラウザーに通知します.

パスのワイルドカード指定

ESP32 の HTTP Server ライブラリでは,パスに対応するハンドラ関数を指定してやる必要がありますが,Angular のように複数のファイルがある場合,ファイル毎に関数を用意するのは手間です.

そこで,ワイルドカードによる指定を行えるようにするため,下記のようにします.

その上で,次のようにすると,/app 以下の全てのアクセスに対して http_handle_app が呼ばれるようになります.(下記では APP_PATH マクロを展開しています)

あとは, http_handle_app の中で,req->uri を基にどのファイルへのアクセスか判定して,適切なファイルを配信してやれば OK.

動作確認

Wifi 接続が完了したタイミングで次の関数を呼んでおけば,Angular アプリを実行できるようになっています.