
LLMファーストの欺瞞フレームワーク: "話し返すハニーポット!™"
# honeyprompt

`honeyprompt` のご紹介 – ウェブ開発者によって/のために作られた、LLMファーストの欺瞞フレームワークです。
[@alectrocute](https://github.com/alectrocute) の個人的な情熱プロジェクトです。
主要なクラウド・ローカル LLM プロバイダーすべてに対応。SSH、HTTP、TLS、TCP、telnet などに対応しています。
小さなコンテナ(そして単一の静的バイナリ)として提供され、すべての設定は1つの `honeyprompt.yaml` に集約されます。
プラグインのコンパイルは不要、データベースの実行も不要。拡張が容易で、低スペックなハードウェアでもデプロイできます。
## デモインスタンス
デモインスタンスは `172.233.151.216` で利用可能です。認証不要のウェブパネルはこちら:
<http://172.233.151.216:9090>。これは安価な Linode VPS 上で動作する honeyprompt の公開インスタンスで、唯一の LLM プロバイダー/モデルとして `openrouter/free` を使用しています。
## クイックスタート
2026年現在、最も簡単なセットアップ方法として、Docker と OpenRouter/`openrouter/free` の LLM プロバイダーをお勧めします。
主要なクラウド・ローカル LLM プロバイダーすべてに対応しています。3つのファイルと1つのコマンドで、完全なデフォルトデプロイ(7つの LLM バックド・デコイ、耐久性のあるイベントストレージ、オペレーターパネル)が立ち上がります。
**1. デフォルトの設定、Compose ファイル、env テンプレートを取得:**
```bash
# Docker をお持ちでない場合:
# curl -fsSL get.docker.com -o get-docker.sh && sh get-docker.sh
mkdir honeypot && cd honeypot
wget https://raw.githubusercontent.com/alectrocute/honeyprompt/main/honeyprompt.yaml
wget https://raw.githubusercontent.com/alectrocute/honeyprompt/main/compose.yaml
wget -O .env https://raw.githubusercontent.com/alectrocute/honeyprompt/main/.env.example
```
(リポジトリをクローンして `cd` しても同じ3つのファイルです。)
**2. `.env` を記入します。** 必須の値は2つです:
```dotenv
OPENROUTER_API_KEY=sk-or-... # 専用キーに支出制限を設定
HONEYPROMPT_PANEL_PASSWORD=changeme # パネルのBasic認証パスワード
```
**3. 起動します:**
```bash
docker compose up -d
```
**4. 試します:**
```bash
ssh -p 2222 root@localhost # パスワード: root — その後何か入力
curl http://localhost:2375/v1.54/containers/json # "露出した" Docker API
```
**5. 動作を確認します** – 読み取り専用パネル (<http://127.0.0.1:9090>) に `admin` とパネルパスワードでサインイン。すべての接続、認証情報、コマンドがライブでストリーミングされます。リモートホストにデプロイする場合は、[`compose.yaml`](https://github.com/alectrocute/honeyprompt/blob/main/compose.yaml) で `:9090` ポートを公開する必要があります。これは本番デプロイには推奨されません。
> 本番デプロイでは `latest` ではなく番号付きリリースをピン留めしてください — `.env` で `HONEYPROMPT_IMAGE` を設定。
ダウンロードした [`honeyprompt.yaml`](https://github.com/alectrocute/honeyprompt/blob/main/honeyprompt.yaml) は完全に注釈付きの見本です。以下に対応するプロファイルが含まれています:
- **汎用の企業向けウェブサーバー** — ポート80、最大の網;`/` は即座に標準の nginx ウェルカムページを返し、それより深いパスは LLM にフォールスルーし、攻撃者を引き続けるために構築された本格的な HTML/CSS 社内ページ、ログインフォーム、管理パネルを返します。
- **MCP / エージェントゲートウェイ** — Streamable HTTP ディスカバリー、OAuth メタデータ、JSON-RPC ツールコール、魅力的な本番ツール。
- **Docker Engine API 29.5** — 実際のクラウドワームが使用する認証なしポート2375の表面。
- **Kubernetes API v1.36** — 名前空間、ワークロード、Secret、ConfigMap、RBAC のディスカバリー。
- **Ubuntu 26.04 AI ビルドインフラ** — SSH、GPU ワークロード、Docker、kubeconfig、CI 状態、プロバイダー資格情報。
- **Redis 8.8** — 認証情報窃取、永続化、横方向移動に使われる一般的な RESP プローブ。
- **産業用エッジ / OT** — 意図的にレガシーな Telnet 管理プレーン。現代の防御でも古いインフラに対する攻撃を捕捉する必要があるため。
### LLM を使用しない場合の実行
> [!IMPORTANT]
> LLM を使用する場合でも、最も頻繁に使用されるパスを特定し、それらに静的ルールを追加してください。
> これにより、大量の LLM トークンを節約でき、LLM 呼び出しのコストに見合わないリクエストへの応答が高速化されます。
> 例:`whoami`、ヘルスチェック、favicon、バージョンプローブなど。
以下の最小限の `honeyprompt.yaml` は、2つの静的ルールと LLM なしで SSH ボックスを偽装します:
```yaml
panel:
enabled: true
address: "0.0.0.0:8080"
events:
buffer: 2000
file: /data/events.jsonl # 耐久性のある攻撃者アクティビティ
services:
- protocol: ssh
address: "0.0.0.0:2222"
description: "Ubuntu 26.04 LTS build runner"
serverName: "gpu-runner-07"
passwordRegex: "^(root|admin|123456)$" # どのパスワードが「機能する」か
commands:
- regex: "^whoami$"
handler: "root"
- regex: "^(.+)$"
handler: "bash: command not found"
```
```bash
docker run --rm \
-p 2222:2222 -p 8080:8080 \
-v "$(pwd)/honeyprompt.yaml:/etc/honeyprompt/honeyprompt.yaml:ro" \
-v honeyprompt-data:/data \
alectrocute/honeyprompt:latest
```
## デプロイメント
永続的なデプロイには、同梱の [`compose.yaml`](https://github.com/alectrocute/honeyprompt/blob/main/compose.yaml) を使用してください。
[デプロイメントガイド](https://github.com/alectrocute/honeyprompt/blob/main/DEPLOYMENT.md) では、Docker Hub リリース、必要な GitHub シークレット、ポートとファイアウォールの設定、SSH 経由のパネルアクセス、アップグレード、ロールバック、イベントストレージ、分離について説明しています。
## LLMファーストの欺瞞(なぜ今なのか) – 簡単に
ハニーポットに求められることは一つだけです:攻撃者が入力を続けるのに十分な説得力を長く保つこと。攻撃者が実行するすべてのコマンドはインテリジェンスです—彼らが使うツール、再利用する認証情報、あなたがパッチを当てていないと想定するCVE。静的なハニーポットは、作者が想定していなかったコマンドが実行された瞬間にキャラクターを破綻させます。honeyprompt はその瞬間を LLM に任せるので、シェルは `dmesg | tail` や `cat /etc/shadow` にも本物のように応答し、セッションは継続します。
このプロジェクトにインスピレーションを与えた、Adel Karimi 氏の素晴らしい DEF CON 32 での Galah(初の?)LLM ハニーポットに関するプレゼンテーションをご覧ください:<https://www.youtube.com/watch?v=XGsm4Qcc_Ag>
## ログに記録されるもの:2つの独立したストリーム
この部分は事前に理解しておく価値があります。なぜなら、この2つは意図的に分離されているからです:
- **欺瞞イベント**: すべての攻撃者とのやり取り:接続、認証試行、各コマンドまたはリクエスト、honeyprompt が返した応答、応答したプロバイダーとモデル、およびその所要時間。これがあなたの脅威インテリジェンスです。ライブパネル用に制限付きのインメモリバッファに保持され、すべてをディスクに永続化できます。
- **運用ログ**: 起動、バインドしたポート、プロバイダーの障害、シャットダウン、内部エラー。これはランタイムが誤動作したときに読みます。攻撃者のアクティビティとは無関係です。
これらは別々に設定します:
```yaml
# ハニー:攻撃者アクティビティ
events:
buffer: 2000 # パネル用に最近のイベントをメモリに保持
file: /data/events.jsonl # すべてのイベントを JSON Lines として永続化
# ランタイム自身の診断
logging:
level: info # debug | info | warn | error
format: text # コンソールでの表示形式:text(人間向け)または json
file: /data/honeyprompt.log # オプション;ディスク上では常に JSON
```
`events.jsonl` は1行に1つの自己完結型 JSON オブジェクト — `tail -f`、SIEM への送信、`jq` での再生に最適です。上記の Docker コマンドは名前付きボリューム `honeyprompt-data` を `/data` にマウントするため、イベントはコンテナ交換後も保持されます。両方のファイルは追記され、クリーンシャットダウン時にフラッシュされます。
`format` は運用ログのコンソールへの表示方法にのみ影響します。運用ログファイル(有効時)は常に構造化 JSON で、解析が容易です。
## ウェブパネル

オプションの読み取り専用ダッシュボード。欺瞞イベントをリアルタイムでストリーミングし、プロトコル別に分類し、ワンクリックですべてを JSON でエクスポートします:
```yaml
panel:
enabled: true
address: "0.0.0.0:8080"
auth: # オプションの Basic 認証
username: admin
password: "${HONEYPROMPT_PANEL_PASSWORD}"
```
ダッシュボードはプレーンな HTML、CSS、JavaScript([`src/panel/assets`](https://github.com/alectrocute/honeyprompt/blob/main/src/panel/assets))で、バイナリに埋め込まれています。`auth` を未定義のままにすると認証が無効になります。
## プロバイダー
各プロバイダーは独自のモジュールで、独自のタイムアウト、リトライ、レート制限、ヘッダーを持ちます。API キーは環境変数から取得されます。デフォルトで以下に対応:
| プロバイダー | `type` | 備考 |
| -------------------------- | ------------------- | ---------------------------------------------- |
| Ollama | `ollama` | ローカルモデル;デフォルトは `localhost:11434` |
| llama.cpp | `llamacpp` | ローカルの `server` OpenAI エンドポイント |
| OpenAI | `openai` | `OPENAI_API_KEY` |
| Azure OpenAI | `azure` | `azure.deployment` + `azure.apiVersion` が必要 |
| OpenRouter | `openrouter` | `OPENROUTER_API_KEY` |
| Anthropic | `anthropic` | `ANTHROPIC_API_KEY` |
| Google Gemini | `google` | `GEMINI_API_KEY` |
| OpenAI 互換の何か | `openai-compatible` | `baseUrl` をゲートウェイに向ける |
### ロードバランシングとフェイルオーバー
プロバイダーを設定し、`pool.strategy`(`round-robin`、`weighted`、`random`、または `failover`)を選ぶと、honeyprompt はトラフィックをそれらに分散します。選択したプロバイダーがタイムアウトするか、リトライ可能なエラーを返した場合、honeyprompt は透過的に次のプロバイダーにフェイルオーバーします — ダウンしたバックエンドがハニーポットをオフラインにすることは決してありません。リトライ不可能なエラー(例えば不正な API キー)はカスケードを停止し、静かにクォータを消費する代わりに問題を通知します。
サービスは、独自のプロバイダーサブセットを指定しない限り、グローバルプールを使用します:
```yaml
llm:
enabled: true
providers: [local-ollama] # 1つの名前:このサービスをこのプロバイダーに強制
```
複数の名前をリストすると、そのサブセット内でのみロードバランシングとフェイルオーバーが維持されます:
```yaml
llm:
enabled: true
providers: [openai-primary, openrouter-backup]
```
### 名前付きプール
複数のサービスが同じプロバイダーグループを共有する必要がある場合、またはサブセットがグローバルとは異なる戦略を必要とする場合は、**名前付きプール**を定義します。プールには名前、戦略、順序付きプロバイダーリストがあり、サービスはプロバイダーを指定する場所ならどこでもその名前で参照できます:
```yaml
pools:
- name: cheap-first
strategy: failover # ローカルモデルを最初に試し、有料APIにフォールバック
order: [local-ollama, openrouter]
- name: spread
strategy: round-robin
order: [openrouter, openai]
services:
- protocol: ssh
# ...
llm:
enabled: true
providers: [cheap-first] # プロバイダーの代わりにプール名
- protocol: http
# ...
llm:
enabled: true
providers: [spread]
```
プール名は `providers` の唯一のエントリでなければなりません — プールと個々のプロバイダーを同一リストに混在させることはできません。どの戦略が優先されるかが不明確になるためです。プール名はプロバイダー名と同じ名前空間に存在し、衝突してはいけません。
## フックによる応答の拡張
「正規表現に一致させる」または「モデルに問い合わせる」だけでは不十分な場合、フックを使用してリクエストパスとレスポンスパスに独自の TypeScript を挿入できます。フックは、モデルに到達する前にプロンプトを書き換えたり、攻撃者に届く前に応答を書き換えたりできます。
```ts
import { registerHook } from "./src/engine/hooks.ts";
registerHook({
name: "fake-latency-notice",
transformResponse(response, ctx) {
if (ctx.protocol === "ssh" && /rm -rf/.test(ctx.input)) {
return "rm: cannot remove '/': Operation not permitted\n";
}
return response;
},
});
```
任意のサービスの `hooks:` リストから名前で参照します。組み込みの `redact-secrets` フックはサンプル設定で有効になっており、モデルが実際の認証情報を外部に漏らすことがないようにします。
## メトリクス
Prometheus メトリクスはパネルの `/metrics` で提供されます(認証なしなので、スクレイパーはそのまま動作します):
```
honeyprompt_events_total{protocol="ssh"} 412
honeyprompt_llm_requests_total{provider="openai",protocol="ssh"} 118
honeyprompt_auth_attempts_total{protocol="ssh"} 87
honeyprompt_engine_errors_total{protocol="http"} 0
```
## ソースからのビルド
貢献したい場合、またはネイティブバイナリが必要な場合は、[Deno](https://deno.com) 2.x が必要です — 唯一の依存関係です。
```bash
deno task check # 型チェック
deno task lint
deno task fmt
deno task test # 単体テスト + 統合テスト
deno task start -- --config honeyprompt.yaml # ローカルで実行
deno task dev -- --config honeyprompt.yaml # ファイル監視付きで実行
deno task compile # -> ./dist/honeyprompt (自己完結型バイナリ)
```
`deno compile` はランタイム、パネルアセット、すべてを1つの実行ファイルに焼き付け、依存関係はありません。Linux、macOS、Windows 向けのプリビルドバイナリは、タグ付けされたすべての[リリース](../../releases)に添付されています。
CI はプッシュのたびにフォーマット、リント、型チェック、テスト、設定検証、クロスプラットフォーム `compile`、Docker ビルドを実行します。`vX.Y.Z` のタグ付けによりリリースバイナリが作成され、証明書とSBOM付きのマルチアーキテクチャイメージが [`alectrocute/honeyprompt`](https://hub.docker.com/r/alectrocute/honeyprompt) に公開されます。
## CLI
```
honeyprompt run [--config <path>] 設定されたすべてのサービスを起動(デフォルト)
honeyprompt validate [--config <path>] 設定を解析して検証し、終了 — CI に最適
honeyprompt version
honeyprompt help
```
`--config` はデフォルトで `./honeyprompt.yaml`、または `$HONEYPROMPT_CONFIG` が設定されていればそれを使用します(コンテナでは `/etc/honeyprompt/honeyprompt.yaml` に設定されます)。
## ユーザーと貢献者への警告
これは、**あなたが所有しているか、テストする権限がある**インフラ上で攻撃者を誘い、研究するためのツールです。デコイサービスを公開することは、それでもサービスを公開することを意味します。隔離されたホストで実行し、パッチを適用し続け、プローブされても困らないものだけに向けてください。欺瞞は、実際のものを実際に保護する代わりにはなりません。
このプロジェクトに貢献したい場合、AI エージェントを使用したり、生成コードに大きく依存したりすることはまったく問題ありませんが、あなたが提供するコードのすべての行について個人的に質問されます。もし即座に AI なしでの理解を示せなければ、**あなたの貢献全体**が拒否され、破棄されます。
## ライセンス
[MIT](https://github.com/alectrocute/honeyprompt/blob/main/LICENSE)。