# セキュリティ設計書

## 概要

本ドキュメントは、serve-d（D言語LSPサーバー）のセキュリティ設計を記載するものである。serve-dはエディタ（VS Code等）とstdin/stdout経由でJSON-RPCプロトコルにより通信するデスクトップツールであり、Webアプリケーションとは異なるセキュリティモデルを持つ。ネットワークに直接公開されず、信頼されたLSPクライアント（エディタ）からのリクエストのみを処理する設計となっている。

## 認証設計

### 認証方式

serve-dはstdin/stdoutパイプ経由でLSPクライアントと通信するため、ネットワーク上の認証メカニズムは実装していない。以下の特性により認証が不要な設計となっている。

- **通信方式**: stdin/stdoutパイプ（プロセス間通信）
- **起動形態**: エディタが子プロセスとして起動するため、親プロセス（エディタ）のみがアクセス可能
- **プロトコル**: LSP仕様に準拠したJSON-RPCのみを受け付け

代わりに、LSPプロトコルのライフサイクル管理により、正当なクライアントのみがサーバー機能を利用できる仕組みを備えている。

- **初期化ハンドシェイク**: `initialize`リクエストが完了するまで、他のコマンドは`serverNotInitialized`エラーで拒否される（`serverbase/source/served/serverbase.d` 149-154行目）
- **シャットダウン制御**: `shutdown` → `exit`の順序が強制され、不正な終了シーケンスを防止

### セッション管理

| 項目 | 設定値 | 備考 |
| --- | --- | --- |
| セッション有効期限 | パイプ接続の存続期間 | stdin/stdoutパイプが切断されればプロセス終了 |
| セッション固定化対策 | 該当なし | ネットワークセッションを使用しないため不要 |
| 初期化前リクエスト | `serverNotInitialized`エラーで拒否 | `serverbase.d` 149-154行目で実装 |
| シャットダウン管理 | `shutdownRequested`フラグで状態管理 | `serverbase.d` 92-96行目、348-364行目 |

## 認可設計

### 権限体系

| ロール | 権限 | 説明 |
| --- | --- | --- |
| LSPクライアント | 全LSPコマンド実行権限 | 初期化ハンドシェイク完了後に全機能にアクセス可能 |
| 未初期化クライアント | `initialize`/`shutdown`のみ | 初期化前は機能制限される |

### アクセス制御

serve-dのアクセス制御はLSPプロトコルのライフサイクルとファイルシステムスコープの2層で構成される。

**1. LSPプロトコルレベルのアクセス制御**

- `initialize`リクエスト未完了の場合、`shutdown`以外の全リクエストを`serverNotInitialized`エラーで拒否（`serverbase/source/served/serverbase.d` 149-154行目）
- JSON-RPCメッセージの形式検証により、不正なリクエストを排除

**2. ファイルシステムスコープの制限**

- `file://`スキームのURIのみを受け付け、他のスキームは拒否（`source/served/types.d` 358-359行目）
- 相対パスの使用を禁止し、絶対パスのみを受け付け（`protocol/source/served/lsp/uri.d` 15-29行目）

## 通信セキュリティ

| 項目 | 対策 |
| --- | --- |
| プロセス間通信 | stdin/stdoutパイプによるローカル通信（ネットワーク非公開） |
| HTTPダウンロード（非Windows） | HTTPS経由でGitHubからDCDバイナリをダウンロード（`source/served/commands/dcd_update.d` 159行目） |
| HTTPダウンロード（Windows） | WinINet APIを使用。ただし`RequestsSkipSSL`フラグによりSSL検証がスキップされる設定あり（`dub.json` 30行目）。**中間者攻撃のリスクあり** |
| HSTS | 該当なし（HTTPサーバーとして動作しないため不要） |

## データセキュリティ

### 暗号化

| 対象 | 暗号化方式 |
| --- | --- |
| 通信 | stdin/stdoutパイプ（ローカルプロセス間通信のため暗号化不要）。外部HTTPダウンロードはHTTPS使用 |
| 保存データ | 暗号化なし。永続データはインデックスキャッシュ・ビルドアーティファクトのみであり、機密情報を含まない |

### 機密情報管理

serve-dはユーザーの機密情報を直接扱わない設計となっている。

- **ソースコード内**: ハードコードされたパスワード・APIキー・シークレット等は存在しない
- **CI/CD**: GitHubの標準シークレット機構（`secrets.GITHUB_TOKEN`）を利用してリリースアップロードに使用（`.github/workflows/releases.yml` 57行目）
- **環境変数**: セキュリティ上の機密情報を環境変数で管理する仕組みは使用していない
- **`.gitignore`**: ビルド成果物（`.o`, `.a`, `.obj`, `.dll`, `.lib`, `.exe`, `bin/`, `build/`等）が適切に除外されている

## 入出力対策

| 脅威 | 対策 |
| --- | --- |
| XSS | 該当なし。Webコンテンツを生成・配信しないため不要 |
| SQLインジェクション | 該当なし。データベースを使用しないため不要 |
| CSRF | 該当なし。HTTPエンドポイントを公開せず、ブラウザからのリクエストを受け付けないため不要 |
| 不正JSON-RPC入力 | Content-Length検証、JSON形式検証、必須フィールド検証、paramsの型検証を実装（`lsp/source/served/lsp/jsonrpc.d` 505-669行目） |
| 不正URI入力 | `file://`スキーム以外の拒否（`protocol/source/served/lsp/uri.d` 49-64行目）、相対パスの拒否（同15-29行目）、非file:// URIの拒否（`source/served/types.d` 358-359行目） |
| 不正設定値 | クライアント設定レスポンスの形式検証（`serverbase/source/served/utils/serverconfig.d` 417-455行目） |
| 外部プロセスインジェクション | `git clone`, `dub build`, `tar`等の外部コマンドを実行。設定値（`git.path`, `dubPath`等）がユーザー設定から渡されるため、悪意のある設定による不正コマンド実行の可能性は理論的に存在するが、信頼されたエディタからの設定が前提 |

### JSON-RPC入力検証の詳細

`RPCProcessor.run()`（`lsp/source/served/lsp/jsonrpc.d` 478-577行目）で以下の多層バリデーションを実施:

1. **Content-Length検証**: 0以下の場合は`invalidRequest`エラーを返却（505-509行目）
2. **リクエスト形式検証**: JSON配列（バッチ）またはJSONオブジェクト（単一）のみ許可、それ以外は拒否（520-542行目）
3. **空バッチ拒否**: 空の配列によるバッチリクエストを拒否（533行目）
4. **必須フィールド検証**: `method`, `result`, `error`, `id`の組み合わせルールに違反した場合は`invalidRequest`エラー（598-609行目）
5. **paramsの型検証**: `params`がオブジェクトまたは配列以外の場合は`invalidParams`エラー（656-669行目）
6. **パースエラーハンドリング**: 不正なJSONに対して`parseError`を返却（544-563行目）

## 監査ログ

| ログ種別 | 記録内容 | 保持期間 |
| --- | --- | --- |
| 標準ログ | サーバー動作ログ（`std.experimental.logger`使用）。デフォルトでstderrに出力。`--logfile`オプションでファイル出力可能、`--loglevel`でレベル変更可能 | プロセス存続期間（ファイル出力時は明示的な保持期間なし） |
| パフォーマンストレース | 関数実行時間・GCメモリ使用量を`served_trace.log`に出力。`debug(PerfTraceLog)`有効時のみ動作 | プロセス存続期間 |
| クライアント通知ログ | `window/logMessage` LSP通知でエディタにログ送信（`lsp/source/served/lsp/jsonrpc.d` 353-361行目） | エディタ依存 |
| セキュリティ監査ログ | **未実装**。セキュリティイベントに特化した監査ログの仕組みは存在しない | - |

## 備考

### プロジェクト特性に基づくセキュリティ評価

serve-dはLSPサーバーという特殊な用途のアプリケーションであり、Webアプリケーションとは根本的に異なるセキュリティモデルを持つ。以下の特性により、一般的なWebセキュリティ対策の多くが適用対象外となる。

- **ネットワーク非公開**: stdin/stdoutパイプ通信のため、リモート攻撃面が存在しない
- **信頼されたクライアント前提**: エディタが唯一のクライアントであり、悪意あるクライアントは想定しない
- **データベース不使用**: SQLインジェクション等のデータベース関連脅威は対象外
- **Webコンテンツ非生成**: XSS/CSRF/CSP等のWeb固有の脅威は対象外

### 潜在的リスクと推奨事項

| リスク | 深刻度 | 詳細 | 推奨対策 |
| --- | --- | --- | --- |
| Windows環境でのSSL検証スキップ | 中 | `dub.json`の`RequestsSkipSSL`フラグにより、DCDバイナリダウンロード時にSSL証明書検証がスキップされる | SSL検証を有効化するか、ダウンロード後にチェックサム検証を追加する |
| 外部プロセス実行 | 低〜中 | ユーザー設定値（`git.path`, `dubPath`等）に基づく外部コマンド実行が存在する | 設定値のサニタイズ・許可リスト方式による検証の追加を検討する |
| 依存関係の脆弱性スキャン未実施 | 低 | CI/CDパイプラインに依存パッケージのセキュリティスキャンが組み込まれていない | D言語エコシステムで利用可能なセキュリティスキャンツールの導入を検討する |
| ディレクトリトラバーサル | 低 | `file://` URIからファイルパスへの変換時に`../`を用いたトラバーサルに対する明示的な防止策がない | パス正規化後のワークスペースディレクトリ内チェックの追加を検討する |

### 依存関係のセキュリティ

`dub.selections.json`により49パッケージの依存関係バージョンが固定され、再現可能なビルドが保証されている。主要な暗号関連依存として`openssl 3.4.0`、`botan 1.12.19`が間接依存として含まれるが、serve-d自体が直接暗号処理に使用しているわけではない。
