セキュリティログプラグイン (Security Log Plugin)¶
概要¶
顧客のログイン試行を詳細に記録し、不正アクセスの検知やカスタマーサポートの迅速化を実現するプラグイン。AES-256-GCM による認証付き暗号化、IPベースの位置情報特定、およびログイン失敗時の管理者即時通知機能を提供します。
パッケージ情報¶
- パッケージ名:
@ritsubi/plugins-security-log - パス:
/packages/plugins/security-log - エントリーポイント:
src/index.ts
実装機能¶
1. ログイン試行の自動記録¶
Shop API の login ミューテーションを LoginLogInterceptor
が自動的にキャプチャし、以下の情報を LoginLog
エンティティとしてデータベースに保存します。
| 項目 | 説明 | 備考 |
|---|---|---|
identifier |
試行されたメールアドレス | |
encryptedPassword |
入力されたパスワード | AES-256-GCMで暗号化 |
ipAddress |
クライアントのIPアドレス | |
location |
概算の位置情報 | geoip-lite による解析結果(JSON) |
success |
ログイン成否 | |
failureReason |
失敗理由 | エラーコード(例: INVALID_CREDENTIALS_ERROR) |
createdAt |
試行時刻 | 日本標準時 (JST) で表示可能 |
2. パスワードの安全な保存と復号¶
顧客が「パスワードが合っているはずなのにログインできない」と問い合わせた際、管理者が実際に入力された内容を確認できるように、可逆暗号化を採用しています。
- 暗号化方式: AES-256-GCM (Authenticated Encryption)
- 鍵管理: 環境変数
SECURITY_LOG_ENCRYPTION_KEYを使用。 - 改ざん検知: GCMモードにより、保存データの改ざんを検知可能。
- 復号表示: 特定の権限を持つ管理者のみ、管理画面 API を通じて平文パスワード(
decryptedPassword)を確認できます。
3. 管理者向けメール通知¶
ログイン失敗が発生した際、管理者に即座にアラートメールを送信します。
- トリガー: ログイン失敗(成功時は送信されません)
- 通知内容: 試行メールアドレス、IPアドレス、推定位置、失敗理由、発生時刻。
- テンプレート: MJML形式による日本語メールテンプレート (
login-failure)。
4. 閲覧制限と権限管理¶
セキュリティログは機密性が高いため、アクセス権限を厳格に管理しています。
- 専用権限:
ReadSecurityLog - 閲覧可能者:
SuperAdminまたは上記権限を明示的に付与された「ロール」を持つ管理者のみ。 - スタッフへの制限: 通常のCSスタッフ用ロールにはこの権限を付与しないことで、ログの露出を防げます。
技術仕様¶
プラグイン初期化¶
import { SecurityLogPlugin, loginFailureHandler } from '@ritsubi/plugins';
// vendure-config.ts
export const config: VendureConfig = {
plugins: [
SecurityLogPlugin.init({}),
EmailPlugin.init({
handlers: [
// ログイン失敗通知ハンドラーの登録
loginFailureHandler.setRecipient(
() =>
process.env.LOGIN_FAILURE_NOTIFY_EMAIL ||
'alerts@ritsubi.mail-box.ne.jp',
),
],
// ...
}),
],
};
データベースモデル (LoginLog)¶
- テーブル名:
login_log - カラム:
identifier,encryptedPassword,ipAddress,location,success,failureReason
設定・運用¶
環境変数¶
| 変数名 | 説明 | 推奨値 |
|---|---|---|
SECURITY_LOG_ENCRYPTION_KEY |
パスワード暗号化用の秘密鍵 | 32文字以上のランダム文字列 |
LOGIN_FAILURE_NOTIFY_EMAIL |
失敗通知の宛先 | alerts@ritsubi.mail-box.ne.jp |
※ SECURITY_LOG_ENCRYPTION_KEY
を変更すると、それ以前に保存された過去のログ(パスワード)は復号できなくなります(Decryption
failed と表示されます)。
管理画面での確認¶
- [設定] > [グローバル設定] > [セキュリティ] タブにて通知先メールアドレスを確認できます。
- 特定のスタッフに閲覧を許可する場合、[設定] > [ロール] から
ReadSecurityLog権限をチェックしてください。
セキュリティ考慮事項¶
- 生パスワードの非保持: データベース上には暗号文のみが存在します。
- ブルートフォース対策: このログを活用して、短期間に同一IPから多数の失敗がある場合の監視が可能です。
- GDPR/プライバシー: IPアドレスと位置情報を保持するため、プライバシーポリシーへの記載を検討してください。
開発ガイド¶
テストの実行¶
cd packages/plugins/security-log
pnpm test
すべてのロジック(暗号化・復号・インターセプター・イベント発行)はユニットテストで検証済みです。