accelint-security-best-practices について
フレームワークを問わず JavaScript と TypeScript アプリを監査・修正するセキュリティスキルです。脆弱性の発見、OWASP に基づくリスク分類、修正、検証を 4 段階で進めます。
主な機能
- 014 段階のセキュリティ監査ワークフロー
- 02OWASP カテゴリーと重大度による分類
- 03入力検証とインジェクション対策の指針
- 04カテゴリー別の修正リファレンス
- 05監査レポートのテンプレート
活用シーン
- 01アプリや API の脆弱性を確認
- 02セキュリティ上の指摘を分類して報告
- 03機能開発中にセキュリティ修正を適用
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ gohypergiant/ agent-skills --skill accelint-security-best-practicesインストール後、Claude Code で/accelint-security-best-practicesを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
AGENTS.mdREADME.mdassets/output-report-template.mdreferences/authentication.mdauthorization.mdcsrf-protection.mddependency-security.mdfile-uploads.mdinjection-prevention.mdinput-validation.mdmfa.mdquick-reference.mdrate-limiting.mdsecrets-management.mdsecurity-headers.mdsensitive-data.mdssrf-prevention.mdxss-prevention.md詳細
セキュリティのベストプラクティス
JavaScript/TypeScript アプリケーションの体系的なセキュリティ監査と脆弱性検出を行います。本番環境に対応したコードを実現するため、監査ワークフローと OWASP Top 10 のセキュリティパターンを組み合わせています。
フレームワークに依存しないガイダンス:このスキルでは、さまざまなフレームワーク(Express、Fastify、Nest.js、Next.js など)に適用できるセキュリティ原則を紹介します。コード例では一般的なパターンを使って概念を説明しています。プロジェクトで使用しているフレームワークやパッケージマネージャー(npm、yarn、pnpm、bun)に合わせて調整してください。
セキュリティの実装時に絶対にしてはいけないこと
注記: 型安全性、コード品質、ドキュメントなどの一般的なベストプラクティスには、それぞれの accelint スキルを使用してください。このセクションでは、セキュリティに特化したアンチパターンのみを扱います。
-
シークレットをハードコードしてはいけません - API キー、トークン、パスワード、認証情報をソースコードに記述すると、バージョン管理にプッシュした時点で漏えいします。プライベートリポジトリであっても、従業員の入れ替わり、サードパーティーのアクセス、Git の履歴などからシークレットが漏れる可能性があります。2024 年の侵害分析では、流出した認証情報の 47% は誤ってコミットされた後に「削除」された(ただし Git の履歴には残っていた)
.envファイルに由来していました。攻撃者は、プッシュから数分以内に公開 GitHub コミットをスキャンします。環境変数のみを使用してください。 -
ユーザー入力を信頼してはいけません - 型、形式、サイズ、内容を対象とするスキーマ(Zod、Joi)で検証してください。
-
ユーザー入力をクエリに連結してはいけません - パラメーター化クエリ、ORM、またはプリペアドステートメントのみを使用してください。SQL、NoSQL、またはシェルコマンドでの文字列連結は、インジェクション攻撃を可能にします。
-
機密データを localStorage に保存してはいけません - localStorage は、悪意のあるスクリプトにトークンを盗まれる XSS 攻撃に対して脆弱です。localStorage に保存した JWT トークン、セッション ID、認証情報はセッションをまたいで残り、あらゆる JavaScript コードからアクセスできます。認証トークンには httpOnly Cookie を使用してください。
-
認可チェックを省略してはいけません - 認証は本人確認を行い、認可は権限を確認します。攻撃者は ID を改ざんしたり、認証を回避したり、URL を推測したりします。リソースにアクセスするすべてのエンドポイントで、リクエストしたユーザーがそのリソースを所有しているか、適切なロールを持っているかを確認してください。
-
詳細なエラーをユーザーに公開してはいけません - サーバー側でログに記録し、汎用的なメッセージを返してください。スタックトレースは偵察に利用できるアーキテクチャ情報を漏らします。
-
権限チェックに Array.includes() を使用してはいけません - ロールが 100 個以上ある権限配列では、検索に O(n) の時間がかかり、型安全性の問題も生じます。O(1) で検索できる
Set.has()を使用するか、適切な型チェックを備えたロールベースアクセス制御(RBAC)を使用してください。 -
API のレート制限を省略してはいけません - API リクエストが無制限だと、ブルートフォース攻撃(毎秒 1000 回のパスワード試行)、サービス拒否(サーバーリソースの枯渇)、データスクレイピング(すべてのユーザーやリソースの列挙)が可能になります。認証や高負荷な操作にはより厳しい制限を設け、すべてのエンドポイントにレート制限を適用してください。
-
機密データをログに記録してはいけません - パスワード、トークン、クレジットカード番号、個人情報がログに含まれると、ログ集約システム、バックアップ、サードパーティーサービスに保存されます。ログにアクセスできる人は、アプリケーション自体にアクセスできる人より多いものです。ログに記録する前に、機密フィールドをマスキングしてください。
-
本番環境でデフォルト設定を使用してはいけません - デフォルトのシークレット、無効なセキュリティヘッダー、寛容な CORS 設定、本番環境での開発モードは、既知の脆弱性を生み出します。攻撃者はデフォルト設定をスキャンします。本番環境向けにすべての設定を堅牢化してください。
セキュリティを実装する前に確認すること
次の観点を適用し、包括的なセキュリティ対策が行われているか確認してください。
脅威の評価
- 攻撃対象領域はどこですか? ユーザー入力がシステムに入るすべての箇所(フォーム、API、ファイルアップロード、URL)を特定します
- 最悪のシナリオは何ですか? データ侵害、不正アクセス、サービスの中断、金銭的損失を考慮します
- 攻撃者は誰ですか? スクリプトキディは既知の脆弱性を悪用し、巧妙な攻撃者は複数の弱点を連鎖させます
コンプライアンスの検証
- 保護されたすべてのルートで認証が有効になっていますか? パブリック API は意図したものかもしれませんが、各エンドポイントのアクセス方針を確認してください。
- 操作の前に認可チェックを行っていますか? リソースの読み取り、書き込み、削除を行う前に、所有権や権限を確認してください。
- すべてのユーザー入力を検証していますか? 処理の前に、スキーマを使って型、形式、サイズ、内容を確認してください。
多層防御
- 単一障害点はありませんか? 1 つの防御を回避されてもシステム全体が侵害されないよう、防御を重ねてください。
- エラーを適切に処理していますか? 未処理のエラーは情報漏えいにつながります。適切に処理すれば、セキュリティ態勢を維持できます。
- 監査証跡に十分なログを記録していますか? インシデント対応のため、セキュリティイベント(ログイン試行、アクセス拒否、不審なパターン)を必ず記録してください。
使い方
このスキルは、コンテキストの使用量を最小限に抑えるために段階的開示を利用します。
1. ワークフローから始める(SKILL.md)
以下の 4 段階の監査ワークフローに従って、体系的にセキュリティ分析を行ってください。
2. セキュリティルールの概要を参照する(AGENTS.md)
AGENTS.md を読み込み、カテゴリ別に整理された簡潔なセキュリティルールの要約を確認してください。
3. 必要に応じて具体的なセキュリティパターンを読み込む
具体的なセキュリティ上の問題を特定したら、対応するリファレンスファイルを読み込み、詳細な❌/✅の例を確認してください。
4. レポートテンプレートを使用する
このスキルを呼び出したときは、標準化されたレポート形式を使用してください。
テンプレート: assets/output-report-template.md
セキュリティ監査ワークフロー
2 つの動作モード:
-
監査モード - スキルを直接呼び出す(
/accelint-security-best-practices <path>)か、ユーザーがセキュリティ監査を明示的に依頼した場合- テンプレートを使って構造化された監査レポートを作成します(フェーズ 1~2 のみ)。
- 実装前に、ユーザーが確認できるよう検出結果を報告します。
- 適用するセキュリティ修正はユーザーが決定します。
-
実装モード - 機能の作業中にスキルが自動的に起動する場合
- セキュリティ修正を特定し、直接適用します(全 4 フェーズ)。
- 正式なレポートは不要です。
- 脆弱性をその場で修正することに重点を置きます。
進捗を管理するには、このチェックリストをコピーしてください:
- [ ] Phase 1: Discover - Identify security vulnerabilities through systematic code analysis
- [ ] Phase 2: Categorize - Classify issues by OWASP category and severity
- [ ] Phase 3: Remediate - Apply security patterns from references/
- [ ] Phase 4: Verify - Validate fixes and confirm vulnerability closure
フェーズ 1:セキュリティ脆弱性の検出
重要:セキュリティ脆弱性がないか、コードをすべて監査してください。 露出の可能性に関する推測を理由に、コードの確認を省略しないでください。実装が単独で存在しているように見えても、内部ユーティリティ、ヘルパー、データ変換処理は、API、ファイルアップロード、ユーザーとのやり取りを通じて公開されていることがよくあります。
体系的な静的コード解析を行い、セキュリティ上のアンチパターンをすべて特定してください:
- ハードコードされたシークレット(API キー、パスワード、トークン)
- 入力検証の不足(ユーザーデータ、ファイルアップロード、API レスポンス)
- インジェクションの脆弱性(SQL、NoSQL、コマンド、XSS)
- アクセス制御の不備(認証の欠如、所有権チェックの欠如、IDOR)
- 認証の脆弱性(localStorage 内のトークン、弱いセッション管理)
- レート制限の不足(認証エンドポイント、高コストな処理)
- 機密データの漏えい(ログ、エラーメッセージ、クライアントへのレスポンス)
- セキュリティ設定の不備(デフォルト設定、セキュリティヘッダーの欠如、制限の緩い CORS)
- 脆弱な依存関係(古いパッケージ、既知の CVE)
- CSRF 対策の不足(状態を変更する操作)
- SSRF の脆弱性(検証されていない URL の取得)
出力: 特定した脆弱性をすべて、発生箇所、深刻度、OWASP カテゴリとともに一覧で示します。「発生可能性」に基づいて絞り込まず、見つかった問題をすべて報告してください。
フェーズ 2:分類とリスク評価
フェーズ 1 で特定したすべての脆弱性について、OWASP カテゴリーと重大度を分類します。
すべての脆弱性を OWASP Top 10 カテゴリーで分類してください:
| OWASP カテゴリー | よくある問題 | 重大度の範囲 |
|---|---|---|
| A01: アクセス制御の不備 | 認証の欠如、所有権の確認なし、IDOR | Critical-High |
| A02: 暗号化の不備 | ハードコードされたシークレット、脆弱なハッシュ化、安全でない保存 | Critical-Medium |
| A03: インジェクション | SQL、NoSQL、コマンド、XSS の脆弱性 | Critical-High |
| A04: 安全でない設計 | レート制限の欠如、入力検証なし | High-Medium |
| A05: セキュリティ設定の不備 | デフォルト設定、ヘッダーの欠如、本番環境での開発モード | High-Low |
| A06: 脆弱なコンポーネント | 古い依存関係、既知の CVE | Critical-Low |
| A07: 認証の不備 | 脆弱なセッション管理、MFA なし、クレデンシャルスタッフィング | Critical-High |
| A08: データの完全性の不備 | CSRF 対策の欠如、署名されていない更新 | High-Medium |
| A09: ログ記録の不備 | セキュリティログなし、不十分な監視 | Medium-Low |
| A10: SSRF | 検証されていない URL の取得、内部ネットワークへのアクセス | High-Medium |
重大度レベル:
-
Critical:データ侵害、リモートコード実行、またはシステムの完全な侵害に直接つながる
- 例:SQL インジェクション、本番環境のシークレットのハードコード、管理者用エンドポイントの認証なし
-
High:不正アクセス、データ窃取、またはサービス妨害につながる可能性が高い
- 例:認可チェックの欠如、XSS の脆弱性、安全でないセッション管理
-
Medium:特定の条件下で悪用される、または他の脆弱性と組み合わせて悪用される可能性がある
- 例:レート制限の欠如、脆弱な CORS ポリシー、不十分なログ記録
-
Low:多層防御の改善、ベストプラクティス、または特殊なケースへの対策
- 例:セキュリティヘッダーの欠如、詳細すぎるエラーメッセージ
脆弱性の分類に関するクイックリファレンス:
詳細な脆弱性とカテゴリーの対応表、およびアンチパターンの検出方法については、references/quick-reference.md を読み込んでください。
出力: すべての脆弱性を OWASP カテゴリーと重大度レベルとともに分類したリスト。フィルタリングや優先順位付けは行わず、フェーズ 1 で見つかったすべての項目を列挙してください。
フェーズ 3:セキュリティパターンを使用して修正する
手順 1: フェーズ 2 の分析結果から、脆弱性のカテゴリを特定します。
手順 2: 該当するカテゴリの必須リファレンスを読み込みます。各ファイルを、範囲制限なしで最後まで読んでください。
| カテゴリ | 必須ファイル | 任意 | 読み込まないファイル |
|---|---|---|---|
| シークレット管理 | secrets-management.md | — | その他すべて |
| 入力検証 | input-validation.md | file-uploads.md(ファイルアップロード機能の場合) | secrets、auth |
| インジェクション防止 | injection-prevention.md | — | input validation、XSS |
| 認証 | authentication.md | mfa.md(多要素認証機能の場合) | authorization、secrets |
| 認可 | authorization.md | — | authentication |
| XSS 防止 | xss-prevention.md | — | injection、CSRF |
| CSRF 対策 | csrf-protection.md | — | XSS、auth |
| レート制限 | rate-limiting.md | — | auth、injection |
| 機密データ | sensitive-data.md | — | secrets、logging |
| 依存関係のセキュリティ | dependency-security.md | — | その他すべて |
| セキュリティヘッダー | security-headers.md | — | XSS、CSRF |
| SSRF 防止 | ssrf-prevention.md | — | injection、input validation |
注記:
- 脆弱性が複数のカテゴリにまたがる場合は、関連するすべてのカテゴリのリファレンスを読み込みます
- セキュリティパターンは累積的に適用します。すべてのカテゴリに対処して、多層防御を実現してください
- 特定の機能(ファイルアップロード、MFA など)を実装する場合は、任意のファイルも読み込みます
手順 3: 修正中にすぐ参照できるよう、スキャンします
AGENTS.md を読み込み、カテゴリ別に整理されたセキュリティルールの要約を確認します。上記の詳細なリファレンスファイルのパターンを実装する際に、すぐ参照できる資料として使用してください。
パターンを体系的に適用します:
- 特定した脆弱性カテゴリのリファレンスファイルを読み込みます
- ❌/✅ の例をスキャンし、一致するパターンを探します
- 多層防御を確保しながら、セキュリティ修正を適用します
- セキュリティ上の考慮事項と、該当するパターンへの参照を説明するコメントを追加します
修正例:
// ❌ Before: SQL Injection vulnerability
const query = `SELECT * FROM users WHERE email = '${email}'`;
const user = await db.query(query);
// ✅ After: Parameterized query prevents injection
// Security: injection-prevention.md - parameterized queries
const user = await db.query(
'SELECT * FROM users WHERE email = $1',
[email]
);
フェーズ 4:セキュリティ修正を検証する
脆弱性が解消されたことを検証します:
- コードを確認し、脆弱性に完全に対処できていることを確かめます
- 修正によって新たな脆弱性が持ち込まれていないことを検証します
- 多層防御を確認します。重要なリソースは複数の層によって保護されていますか?
セキュリティテスト:
- 既存のテストスイートを実行します。すべてのテストに合格する必要があります
- 脆弱性に対するセキュリティ専用テストを追加します
- 重大な脆弱性については、ペネトレーションテストを検討します
セキュリティ修正を記録します:
// Security fix applied: 2026-02-01
// Vulnerability: SQL injection via email parameter (Critical)
// OWASP Category: A03 - Injection
// Pattern: injection-prevention.md - parameterized queries
// Verified: All tests pass, manual SQL injection attempts blocked
修正をデプロイするかどうかの判断:
- 重大な脆弱性: 必要に応じて緊急プロセスを使用し、直ちにデプロイします
- 高リスクの脆弱性: 次のリリースサイクル(数日以内、数週間以内ではなく)にデプロイします
- 中リスクの脆弱性: 次回の予定リリースにデプロイします
- 低リスクの脆弱性: 都合のよいときにデプロイするか、他のセキュリティ改善とまとめてデプロイします
テストに失敗した場合: セキュリティ実装を修正するか、別の解決策を見つけます。セキュリティ修正によって機能が損なわれてはなりません。
よくある実装上の落とし穴
セキュリティ修正が既存の機能と競合する場合があります。よくあるシナリオに対する専門家の解決策を以下に示します。
| 問題 | ❌ 誤ったアプローチ | ✅ 正しいアプローチ |
|---|---|---|
| パラメーター化クエリによって動的な列の並べ替えが機能しなくなる | try-catch を追加し、文字列連結にフォールバックする | 列名の許可リストを使う:const allowed = ['name', 'email', 'created_at']; if (!allowed.includes(column)) throw Error; その後、安全に連結する |
| レート制限によって負荷テストが機能しなくなる | テスト環境ではレート制限を無効にする | 環境の判定に基づき、テスト用に別のレート制限設定を使う |
| CSRF トークンによって API 統合テストが機能しなくなる | テストでは CSRF 検証をスキップする | CSRF ライブラリのトークン生成関数を使い、テストのセットアップ時に有効な CSRF トークンを生成する |
| 入力検証によって正当なエッジケースが拒否される | 検証ルールを緩める | そのエッジケースを調査します。正当なものならスキーマを更新し、そうでなければ拒否します。実際のユーザーが検証エラーに遭遇するべきではありません。 |
| 認可チェックによって管理者のなりすまし機能が使えなくなる | 管理者ユーザーの認証チェックをスキップする | 適切ななりすまし機能を実装します。管理者には対象ユーザーの権限を持つ一時トークンを付与し、監査用に記録します |
| HTTPOnly Cookie によってモバイルアプリの認証が機能しなくなる | モバイル向けにトークンを localStorage に保存する | 安全なトークン保存方法を使います。iOS Keychain、Android Keystore、またはプラットフォーム固有の安全なストレージ API を利用します |
セキュリティと機能が競合する場合
優先順位:
- Critical の脆弱性(SQL インジェクション、ハードコードされたシークレット、認証の欠如)については、決して妥協しないでください。代替アーキテクチャを見つけてください
- High の脆弱性では、適切に文書化し、他の制御で補完できる場合に限り、わずかなトレードオフを許容できます
- Medium/Low の脆弱性は、ビジネス上の正当な理由が強く、リスクが受容されている場合、対応を先送りできることがあります
トレードオフに関する文書化の要件:
// SECURITY TRADE-OFF DOCUMENTED: 2026-02-01
// Issue: Rate limiting breaks webhook ingestion from trusted partner
// Decision: Exempt partner IP range from rate limiting
// Compensating controls:
// - IP whitelist strictly maintained (only 2 partner IPs)
// - Separate monitoring for partner traffic
// - Manual review of partner traffic daily
// - 30-day review scheduled to implement alternative solution
// Risk accepted by: [Name], [Title]
自由度の調整
脆弱性の深刻度に応じて、ガイダンスの具体性を調整します。
| 脆弱性の深刻度 | 自由度 | ガイダンスの形式 | 例 |
|---|---|---|---|
| Critical(データ侵害、RCE) | 自由度:低 | 参照例と同じパターンを使い、逸脱しない | 「パラメーター化クエリを使う:db.query('SELECT * FROM users WHERE id = $1', [id])」 |
| High(不正アクセス) | 自由度:中 | 例を含むパターンを示し、網羅性を確認する | 「リソースへのアクセス前に RBAC または所有権チェックを実装する」 |
| Medium(多層防御) | 自由度:中 | 複数の有効な方法を示し、アーキテクチャに応じて選ぶ | 「express-rate-limit を使うか、カスタムミドルウェアを実装してレート制限を行う」 |
| Low(ベストプラクティス) | 自由度:高 | 一般的なガイダンスを示し、実装方法は問わない | 「多層防御のために、セキュリティヘッダーの追加を検討する」 |
判断基準:「深刻度と影響範囲はどの程度か?」
- 深刻度が Critical/High → ミスを防ぐため、具体的なパターンを示して自由度を低くする
- 深刻度が Medium → 検証済みの方法を示して自由度を中程度にする
- 深刻度が Low → 一般的なベストプラクティスを示して自由度を高くする
重要な注意事項
- すべてを監査する方針 - セキュリティ上の脆弱性がないか、すべてのコードを監査してください。内部ユーティリティ、ヘルパー、データ変換は、独立しているように見えても、API やユーザー操作を通じて利用できることがよくあります。セキュリティ境界について決めつけないでください。
- すべての検出事項を報告する - 体系的な静的解析を実施し、すべての脆弱性を特定して、深刻度と OWASP カテゴリを添えて報告してください。悪用される「可能性」に基づいて除外しないでください。
- 参照ファイルが優先されます - references/ のパターンは OWASP のベストプラクティスに従っています。セキュリティ要件により必要な場合を除き、厳密に従ってください。
- 多層防御 - 1 つの脆弱性でシステム全体が侵害されないよう、セキュリティ制御を重ねてください。認証 + 認可 + 入力検証 + レート制限。
- セキュリティテスト - セキュリティ修正では、悪意のある入力やエッジケースを使ったテストが必要です。デプロイ前に、攻撃シナリオのテストを追加してください。
- インシデント対応 - セキュリティのログ記録と監視により、攻撃の検知と対応が可能になります。調査に十分な詳細を含め、すべてのセキュリティイベントを記録してください。
クイック判定ツリー
この表を使って、該当するセキュリティカテゴリと適切な深刻度をすばやく特定してください。
すべてを監査:現在の露出状況にかかわらず、コード内のすべてのセキュリティ上の脆弱性を特定してください。すべての検出事項を、深刻度と OWASP カテゴリを添えて報告してください。
| 次のものを見つけた場合... | 脆弱性の種類 | OWASP カテゴリ | 一般的な深刻度 |
|---|---|---|---|
| ソースコード内の API キー、パスワード、またはトークン | ハードコードされたシークレット | A02: 暗号化の失敗 | 重大 |
| SQL/NoSQL クエリへのユーザー入力の直接埋め込み | インジェクションの脆弱性 | A03: インジェクション | 重大 |
保護されたルートに authenticate ミドルウェアがない | 認証の欠如 | A01: アクセス制御の不備 | 重大 |
| リソースへのアクセス前に所有権/権限を確認していない | 認可の欠如 | A01: アクセス制御の不備 | 高 |
localStorage.setItem() 内の JWT トークン | 安全でないトークン保存 | A07: 認証の失敗 | 高 |
| スキーマ検証を行わないユーザー入力 | 入力検証の欠如 | A04: 安全でない設計 | 高 |
/api/login または /api/register にレート制限がない | レート制限の欠如 | A04: 安全でない設計 | 高 |
サニタイズされていない dangerouslySetInnerHTML | XSS の脆弱性 | A03: インジェクション | 高 |
| CSRF トークンのない状態変更操作 | CSRF 保護の欠如 | A08: データ整合性の失敗 | 高 |
console.log() 内のパスワード、トークン、または PII | ログ内の機密データ | A09: ログ記録の失敗 | 中 |
| ユーザーに送信されるスタックトレースまたはデータベースエラー | 情報漏えい | A05: セキュリティ設定ミス | 中 |
npm audit で脆弱性が表示される | 脆弱な依存関係 | A06: 脆弱なコンポーネント | 重大〜低(状況による) |
検証されていない fetch(userProvidedUrl) | SSRF の脆弱性 | A10: SSRF | 高 |
| セキュリティヘッダー(CSP、HSTS)がない | セキュリティヘッダーの欠如 | A05: セキュリティ設定ミス | 中 |
| 所有権の確認がない連番ユーザー ID | IDOR の脆弱性 | A01: アクセス制御の不備 | 高 |
本番環境での CORS: * | 許可範囲が広すぎる CORS | A05: セキュリティ設定ミス | 中 |
process.env.NODE_ENV !== 'production' のチェックがない | 本番環境での開発モード | A05: セキュリティ設定ミス | 中〜低 |
この表の使い方:
- コードレビューでパターンを特定します
- 「次のものを見つけた場合...」列で該当する行を探します
- OWASP カテゴリと一般的な深刻度を確認します
- フェーズ 3 の該当するセキュリティカテゴリに移動します
- そのカテゴリの必須参照ファイルを読み込みます