コンテンツにスキップ

通知文面テンプレートの書き方

通知文面(タイトル・本文)を作成する方向けの手引き。

  • 対象読者notification_template に登録する文面を書く方
  • 前提:通知基盤(Worker)は、この文面に値を差し込んで SSE・メール・受信箱へ配信する
  • 関連【通知基盤】機能設計

文面は notification_template テーブルの 2 つの列に入る。

内容
notification_title_template通知タイトル。受信箱の一覧・メールの件名になる
notification_content_template通知本文。受信箱の詳細・メール本文になる

どの文面が使われるかは、次の4 つの組み合わせで決まる。

キー意味
notification_caseFLIGHT_PLAN_CONFLICT_CAUSED通知ケース(何が起きたか)
notification_dest_typeSELF宛先種別(誰に送るか)
notification_methodEMAIL通知手段(SSE / OS / EMAIL / UI)
適用期間available_date_fromavailable_date_toいつからいつまで使う文面か

同じキーで期間が重なる文面は登録できない(DB の除外制約で弾かれる)。文面を差し替えるときは、 古い行の available_date_to を新しい行の available_date_from に合わせる。 期間を先に登録しておけば予約もできる(例:明日 9 時から新文面)。

通知手段ごとに別レコードになる。同じ通知でも、メールは丁寧に長く、SSE は短く、といった書き分けができる。 10 月デモでは OS 通知(OS)は対象外なので用意不要。


2. 記法(Thymeleaf テキストテンプレート)

Section titled “2. 記法(Thymeleaf テキストテンプレート)”

HTML ではなくプレーンテキストとして扱う。タグは書かない。

[(${userName})] さん
飛行計画が重複しています。機体ID: [(${aircraft_id})]
  • [(${...})] … 値をそのまま出す。通常はこちらを使う
  • [[${...}]] … エスケープして出す。テキスト文面では通常使わない
[# th:if="${orgName}"]所属組織: [(${orgName})]
[/]
以下の飛行計画が対象です。
[# th:each="plan : ${plans}"]- [(${plan.flight_no})]([(${plan.start_time})])
[/]

[# で始めて [/] で閉じる。閉じ忘れると文面が壊れるので注意。


3-1. 予約語(通知基盤が必ず用意する 5 つ)

Section titled “3-1. 予約語(通知基盤が必ず用意する 5 つ)”

どの通知ケースでも使える。業務側が Outbox に入れる必要はない。

変数内容
userId宛先ユーザのID3f0c1e42-9c53-...
userName宛先ユーザの名前山田 太郎
toAddress宛先メールアドレスtaro@example.com
orgId宛先ユーザが所属する組織のID8a12b7d9-4e60-...
orgName宛先ユーザが所属する組織の名前〇〇ドローン株式会社

toAddress全通知手段で共通の予約語。メール設定を持たないユーザ宛の SSE 通知などでは 空文字になる。文面に載せるときは 3-3 の「値が無いとき」を確認すること。

3-2. 業務が渡すパラメータ(param

Section titled “3-2. 業務が渡すパラメータ(param)”

通知を依頼する側(業務サービス)が Outbox の param に入れた JSON のキーが、そのまま変数名になる。

// Outbox の param に入っている JSON
{
"aircraft_id": "DRN-2026-X1",
"latitude": 35.65858,
"longitude": 139.74543
}
機体 [(${aircraft_id})] が飛行禁止エリアに侵入しました(緯度 [(${latitude})] / 経度 [(${longitude})])。

どのケースでどのキーが来るかは、通知を依頼する業務側と合わせること。

  • 変数が存在しない、または値が null の場合は空文字として描画される(エラーにはならない)
  • 「値が無ければ行ごと消したい」場合は [# th:if=...] で囲む

#ルール理由
1param のキー名は英数字とアンダースコアのみaircraft_id は可、aircraft-id は不可)[(${aircraft-id})] は「aircraft 引く id」という引き算と解釈され、値が出ない。ドット・スペース・先頭数字も同様
2値の見せ方(桁数・単位・書式)は、渡す側で確定させる通知基盤は値を加工しない。受け取った文字列をそのまま差し込む。35.6585835.66 と出したいなら、渡す時点でそう入れる
3HTML タグを書かないテキストとして扱うため、タグはそのまま文字として出る
4外部の画像・リンク先を埋め込まないメールの到達性に影響するほか、文面は暗号化対象の情報を含みうる
5個人情報を文面に直接書かない宛先ごとの値は予約語(userName 等)で差し込む。テンプレート自体は宛先に依存しない形にする
6文面が見つからない場合、その通知手段はスキップされる(通知全体は止まらない)10 月デモの割り切り。登録漏れは静かに欠落するため、必要な case × dest_type × method の組み合わせを揃えること

4-2. メール通知(EMAIL)で追加でお願いしたいこと

Section titled “4-2. メール通知(EMAIL)で追加でお願いしたいこと”

10 月デモのメール通知は Amazon SES で送り、宛先には Microsoft Teams のチャネルも含まれます。 実際に送って確認した結果として、次の 4 点をお願いします。

#ルール理由
1タイトルだけで内容が分かるように書くタイトルが Teams チャネルの投稿タイトルになります。 一覧では本文が見えないため、「通知があります」のような文面だと何の通知か分からなくなります
2タイトルに改行を入れない件名は 1 行です。改行が入っていた場合、通知基盤側で半角スペースへ置き換えます
3段落は空行(改行 2 つ)で区切る空行での段落分けは Teams でもメールクライアントでも意図どおりに表示されることを確認しています。単一改行 1 つだけの挙動は未検証なので、段落の区切りには空行を使ってください
4装飾(太字・色・表)は使えない本文はプレーンテキストで送ります(HTML メールにはしません)。強調したいときは 【】 や記号で表現してください

改行コード(\n / \r\n)はどちらで登録していただいても構いません。送信時に通知基盤が \r\n(メールの規格)へ揃えます。


5. 記入例(デモシナリオ 2 本)

Section titled “5. 記入例(デモシナリオ 2 本)”

5-1. 飛行禁止エリアへの侵入(INTRUSION_NOFLY_AREA

Section titled “5-1. 飛行禁止エリアへの侵入(INTRUSION_NOFLY_AREA)”

タイトル

[(${aircraft_id})] が飛行禁止エリアに侵入しました

本文(メール)

[(${userName})] さん
[(${orgName})] が運航する機体 [(${aircraft_id})] が、飛行禁止エリアに侵入しました。
発生位置: 緯度 [(${latitude})] / 経度 [(${longitude})]
速やかに違反状態を回避してください。

5-2. 飛行計画同士の競合(起因側)(FLIGHT_PLAN_CONFLICT_CAUSED

Section titled “5-2. 飛行計画同士の競合(起因側)(FLIGHT_PLAN_CONFLICT_CAUSED)”

タイトル

飛行計画の重複が検出されました

本文(SSE。画面に短く出す想定)

[(${userName})] さんの飛行計画が他の計画と重複しています。運航調整を開始してください。

notification.notification_template への INSERT で登録する。

INSERT INTO notification.notification_template (notification_case,
notification_dest_type,
notification_method,
notification_title_template,
notification_content_template,
available_date_from,
available_date_to)
VALUES ('INTRUSION_NOFLY_AREA',
'SELF',
'EMAIL',
'[(${aircraft_id})] が飛行禁止エリアに侵入しました',
'[(${userName})] さん' || chr(10) || '...',
'2026-10-01 00:00:00+09',
'2099-12-31 23:59:59+09');
  • available_date_to終わりを決めていなければ十分先の日時を入れる(NULL 不可)
  • 同じキーで期間が重なる行があると、除外制約でエラーになる

  • どのキーが param に来るかが分からない → 通知を依頼する業務側へ確認
  • 文面が正しく差し込まれるか試したい → エアロダインへご連絡ください。ローカル環境で描画結果を確認できます

本書の記法は Thymeleaf のテキストテンプレートモードに基づく。**描画エンジンの実装は Step3 で行い、 そこで実際の描画結果を確認する。**差異が見つかった場合は本書を更新する。


@author Yuki Sudoh (Aerodyne Japan)