Claude-OSINT(elementalsouls/Claude-OSINT・GitHubスター2,441・MIT)は、外部からの見え方を調べる手順書をClaude Codeのスキル形式に畳み込んだパックです。ソフトウェアというよりClaudeに読ませる方法論のテキストで、SKILL.mdの合計は54万文字を超えます。

この種のパックを評価するとき、機能一覧を眺めても分かりません。知りたいのは「入れたら何が常に載るのか」「どういうときに勝手に起動するのか」「止めてくれる仕組みは何なのか」の3点です。この記事はその3点を実測しました。偵察そのものは一切行っていません——数えたのはファイル・frontmatter・トークン数で、起動条件はこのリポジトリと無関係なダミースキルでA/Bを取っています。

Claude-OSINTのSKILL.mdを9本数え、disable-model-invocationが0件であることを確認し、ダミースキルのA/BでtriggersとdescriptionのどちらがSkill起動を決めるかを比べるターミナル操作
スキル数と自動起動抑止の有無を数え、triggers:description のどちらが起動を決めるかをダミースキル2本のA/Bで確かめた実測

30秒でわかる Claude-OSINT

何ができるか:ドメイン・クラウド資産の棚卸し、メール偽装耐性の判定、IdP構成の把握、リスクの金額換算、継続監視——の手順書を9本のSKILL.mdでClaudeに渡す
何を解決するか:「自社が外からどう見えているか」を調べるとき、毎回やり方を思い出す/指示し直す手間
何を代替するか:SpiderFoot等のスキャナを人手で回して結果を読む工程の一部(置き換えではなく別物。後述の比較表)
実測でわかったことtriggers: は起動条件として機能しない。実際に起動を決めるのは description で、9本すべてに自動起動の抑止指定が無い

この記事のポイント

・ダミースキルのA/Bで、triggers: に書いた語では起動せず description に書いた語で起動することを確認した(対照群つき)
・常駐するのは description のみで9本合計 3,332トークン。本文は 148,514トークンで、offensive-osint 1本が44%を占める
・安全弁は「コードとして動くもの」と「文章でのお願い」に分かれる。認可の確認は後者で、ランタイムの disable-model-invocation0/9本

エージェント側の道具立てを俯瞰したい場合はAIエージェントフレームワーク比較2026|LangGraph・CrewAI・Dify等9種をStar数・実コードで検証を先に読むと、スキルパックがどの層の話なのか整理しやすくなります。

Claude-OSINTとは——偵察の手順書を9本のSKILL.mdに畳んだスキルパック

中身はマークダウンです。実行ファイルはごく一部で、大半は「こういう順序で、こういう観点で調べる」という方法論のテキストです。9つのディレクトリは役割が分かれています。

スキル 役割 本文行数
osint-methodology 全体の考え方(6段階のパイプライン・重大度の基準) 520
offensive-osint 具体的な調査対象の辞書(パス・ポート・観点の一覧) 4,734
org-attack-surface 法人名から保有ドメイン・ネットブロックを辿る帰属手順 1,063
identity-provider-recon IdP/テナント構成の把握 1,003
continuous-exposure-monitoring 再スキャンと差分の継続運用 817
cloud-saas-exposure クラウドストレージ・供給網の露出 809
exposure-risk-quantification 検出結果をFAIRベースで金額とグレードに換算 750
email-domain-security SPF/DMARC/DKIMから偽装耐性を判定 608
osint-autopilot 上記を一気通貫で最後まで走らせる実行ランブック 94

注目したいのは上6本の名前です。org-attack-surfacecloud-saas-exposureemail-domain-securityexposure-risk-quantificationcontinuous-exposure-monitoring は、いずれも「自分の資産がどれだけ外に出ているか」を測る側の語彙です。攻撃手法そのものを名乗っているのは offensive-osint の1本だけで、パックの重心は露出面の把握にあります。自社ドメインの棚卸しに使うなら、この5本が主役になります。

なお本記事では、offensive-osint に収録されている検出用の正規表現や検索文字列そのものは載せません。件数と性質だけを数えます

READMEの「8スキル」とディレクトリの9本——どちらが正しいのか

リポジトリ説明は「8 Claude skills」と名乗りますが、skills/ 配下のSKILL.mdは9本あります。数え間違いかと思いましたが、リポジトリに同梱された検査スクリプトを走らせると答えが出ました。

# リポジトリ自身が持つ「ドキュメント内の数字」検査を実行する
python3 scripts/check_doc_counts.py
#   Ground truth: 9 skill dirs (8-skill library = 6 depth + 2 core).
#   Checked 11 doc assertion(s): 0 error(s).

意図的な数え方でした。9ディレクトリのうち「ライブラリ」として数えるのは8本(深掘り6本+コア2本)で、osint-autopilotライブラリではなく実行ランブックとして別枠になっています。READMEの構成図にも osint-autopilot は登場しません。

ただし、導入判断の観点では見過ごせません。「8スキル」に数えられていない9本目こそが、パイプラインを止めずに最後まで走らせる役割だからです。その本文にはこう書かれています。

・停止して確認するのは3つの場面のみ(認可・能動的な検証段階・スコープ外の別ドメイン発見)
それ以外の段階は質問せずに走り切る
・認可については「まだ表明されていなければ一度だけ確認して進む」

インストールすると9本すべてが入ります。数え方の議論とは別に、入るのは9本という事実は押さえておく価値があります。

実測:triggers: は起動条件ではない(ダミースキルのA/B)

各SKILL.mdのfrontmatterには triggers: というキーがあり、external reconrun OSINT といった語が並んでいます。一見すると「この語を言うと起動する」設定に見えます。実際にそうなのかを確かめました。

Claude-OSINT自体を読み込ませて試すと、起動しても偵察の話が始まってしまいます。そこでこのリポジトリとまったく無関係なダミースキルを2本用意し、造語 flimwazzle で切り分けました。

A(zorptrix-alpha)description は無関係な内容。triggers: にだけ flimwazzle を書く
B(zorptrix-beta)triggers: を持たず、description に「flimwazzle と言われたら使う」と書く

flowchart TD Q["入力: flimwazzle"] --> R{"Claude Code が
どのスキルを選ぶか"} R -->|"A: triggers: にだけ記載"| NA["起動しない
(対照群でも0件)"] R -->|"B: description に記載"| YB["即座に起動
Skill(zorptrix-beta)"] NA --> C["結論: triggers: は routing に使われない"] YB --> C

結果です(claude -p の stream-json 出力から、Skillツールの呼び出しだけを抜き出しました)。

設置したスキル 入力 Skillツールの呼び出し
A と B を併置 flimwazzle B のみzorptrix-beta
A のみ(対照群) flimwazzle なし。「一致するコマンドやスキルが無い」と応答

対照群まで取ると疑いようがありません。triggers: はドキュメントであって、ランタイムの routing には使われていません。 起動を決めているのは description の文面です。

これは「設定が間違っている」という話ではなく、読む側が起動条件を知りたいときにどこを読むべきかの話です。Claude-OSINTのdescriptionは長く、たとえば offensive-osint は2,778文字あり、末尾は「認可された外部偵察で具体的な調査パス・正規表現・スコアリング規則が必要なときに使う」で終わります。osint-autopilot はさらに広く「OSINT / recon / attack-surface を実行してと言われたら常に」です。入れておくと、この語彙に触れた会話でロードされ得ると理解しておくのが正確です。

「一覧に出ている」と「発火する」は別:スキルが一覧に載っていても実際に起動するとは限らず、逆に載っているだけで発火することもあります。判定は本文の言い回しではなく、--output-format stream-jsonSkillツールの呼び出しが記録されているかで行うのが確実です。上の表もその方法で取っています。

常駐コストを測る——descriptionだけで3,332トークン、本文は148,514トークン

スキルの仕組み上、description は毎セッション常に載り、本文は呼ばれたときだけ読まれます。そこで両方を測りました。

Claude-OSINTの常駐トークン数3,332と、スキル別の本文トークン数の内訳。offensive-osintが65,481で最大
tiktoken cl100k_base で計測。常駐するのはdescriptionのみで、本文は呼ばれたときだけ読まれる
区分 文字数 トークン数(cl100k_base)
description 9本合計(常駐 15,010 3,332
SKILL.md 本文 9本合計(呼ばれたときだけ 545,370 148,514
うち offensive-osint 単体 225,577 65,481

読み方は次のとおりです。

常駐3,332トークンは軽い。9本入れっぱなしでも、通常の作業セッションを圧迫する量ではありません
一方、本文を1本読ませると重いoffensive-osint の65,481トークンは、多くのモデルで一度に扱えはしても、その後のやり取りの余地を大きく削ります
・したがって実運用では「9本入れておく」より「必要な1〜2本だけ入れる」ほうが扱いやすい構成になります。露出面の棚卸しが目的なら org-attack-surfaceemail-domain-security だけでも成立します

トークナイザを明記する理由:同じテキストでもトークナイザが違えば数値は変わり、その差は対象ごとに一定ではありません。上の数値はすべて tiktoken の cl100k_base で数えたもので、他の数え方(各ベンダーの count_tokens API など)とは直接比較できません。他所の数値と並べるときは、必ず同じ物差しで測り直してください。

同じ「エージェントに能力を足す」形式でも、パックごとに設計思想はかなり違います。作業を録画してスキルに変換するSkill Recorder徹底解説|作業を録画してAIエージェントのスキルに変えるMicrosoft公式OSSや、開発プロセスを型に落とすmattpocock/skills完全ガイド|Claude Code用スキル集で開発プロセスを自動化と読み比べると、Claude-OSINTが「巨大な参照辞書を1本抱えている」珍しい形だと分かります。

「強制される仕組み」と「文章でのお願い」を分けて数える

このパックを入れる判断で一番大事なのがここです。安全弁には、コードとして必ず動くものと、Claudeへの文章上のお願いの2種類があります。 両者を混ぜて数えると、実際より安全に見えてしまいます。

ランタイムが強制しないものと、コードとして動くものを分けて並べた比較図
認可の確認は本文中の散文で、ランタイムのゲートではない。一方、引数ガードと識別子スキャナはコードとして動く

ランタイムが強制しないもの(=文章上のお願い)

認可の確認:SECURITY.mdは「対象は自分が保有するか書面で許可を得た資産か」を尋ねる soft scope-check を挙げますが、これはSKILL.md本文に書かれた指示文です。該当する語が本文にあるのは9本中5本で、一気通貫で走らせる osint-autopilot には含まれていません(同スキルは代わりに「Hard gates」の1番目として認可に触れますが、そこにも「ここでは通常すでに署名済み」という但し書きが付いています)
自動起動の抑止disable-model-invocation の指定は 0/9本。この指定があるスキルはランタイムが呼び出しを実際に拒否しますが、このパックは使っていません
ツール制限allowed-tools の宣言も 0/9本。スキル側からツールを絞ってはいません(Claude Code側の許可設定は別にかかります)
triggers::前節のとおり起動条件として機能しません

コードとして動くもの

引数ガード:同梱スクリプトの入口3つが、ドット付きホスト名の正規表現に合わない引数を拒否します(次節で実行)
識別子の混入検知scan_identifiers.py は追跡下の全テキストファイルの1〜2語シングルをハッシュ化し、SHA-256の拒否リストと突き合わせます。拒否リストが無い/空なら成功ではなくエラー終了(fail-closed)で、顧客名が誤ってリポジトリに入るのを防ぎます。docstringには過去に実際に混入した経緯まで書かれています
依存の少なさsecret_scan.py は外部ライブラリを使わず、標準ライブラリ(json/os/re/sys)だけで動きます
用途の明示的な除外:SECURITY.mdが、能動的な侵害・横展開・AD攻撃・マルウェア開発・C2フレームワーク・実在PIIの収録を範囲外と宣言しています

整理すると、「やってはいけないこと」は文章で丁寧に書かれている一方、それを機械が拒否する仕組みは用意されていないという形です。Claude Code側のツール実行許可が最後の砦になるので、このパックを入れる環境こそ、コマンド実行の自動承認を緩めないのが妥当な運用です。

同梱スクリプトの引数ガードを実際に走らせる

コードとして動く安全弁のうち、引数ガードはネットワークを使わずに検証できます。リポジトリには自己検査スクリプトが同梱されているので、そのまま実行しました。

# 依存(openpyxl のみ)を入れてから、同梱の自己検査を走らせる
python3 -m venv .venv && .venv/bin/python -m pip install -r requirements.txt
PATH="$PWD/.venv/bin:$PATH" bash test_domain_guard.sh
#   PASS: domain guard holds on all three entry points

結果は PASS でした。.. / . / ../../tmp/pwned / -rf / --help / a b / example.com;id / nodot / example..com / -example.com / example.com. の11種を3つの入口に与える計33パターンすべてで、ガード自身のエラー文言が返り、拒否された入力が一時HOMEに何も書き出していないことも確認できました。この自己検査は「単に非ゼロ終了した」ではなく「ガード固有のエラー文字列が出た」を判定条件にしており、無関係な理由で落ちた場合に空振りで合格しない作りになっています。

依存を入れずに走らせると誤った失敗が出るopenpyxl が無い環境で自己検査を走らせると、入口の1つ(build_xlsx.py)が5行目の import で落ち、ガードに到達する前に別のエラーで死ぬため FAIL と表示されます。ガードが壊れているわけではなく、宣言された依存を入れてから走らせる必要があります。実際、導入後に再実行したら3入口すべてPASSしました。

そして最も重要な但し書きです。このガードが検査しているのは「文字列がホスト名の形をしているか」であって、「その相手を調べてよいか」ではありません。 正しい形のドメインであれば、それが誰のものであっても通ります。認可の判断は最後まで人間の側にあります。

Claude-OSINTの入れ方——9本まとめてではなく、必要な1〜2本だけ置く

スキルは単なるマークダウンなので、導入は ~/.claude/skills/ にディレクトリを置くだけです。公式手順は全部入りを勧めていますが、前節のトークン数を踏まえると目的に応じて絞るほうが扱いやすくなります

git clone https://github.com/elementalsouls/Claude-OSINT.git
cd Claude-OSINT
mkdir -p ~/.claude/skills

# 公式手順(全部入り)。コメントは「8 skills」だが実際に9ディレクトリ入る
# cp -r skills/* ~/.claude/skills/

# 自社の露出面を測る目的なら、この2本だけで足りる(本文は合計 27,000 トークン弱)
cp -r skills/org-attack-surface skills/email-domain-security ~/.claude/skills/

# 入ったスキルと、自動起動の抑止指定の有無を確認する
ls ~/.claude/skills/
grep -rl "disable-model-invocation" ~/.claude/skills/ || echo "抑止指定なし(description一致で自動ロードされ得る)"

公式手順が勧める「コアの2本」は osint-methodologyoffensive-osint の組み合わせですが、これは本文だけで73,738トークンになります。露出面の棚卸しが目的なら、上の org-attack-surfaceemail-domain-security のほうが3分の1以下で済みます。

インストール手順の sync-skill-content.sh は現状なにもしない:公式手順は clone 直後に ./scripts/sync-skill-content.sh を一度走らせるよう指示しますが、このスクリプトが読み込む docs/full-skills/リポジトリに存在しません--check で走らせると「Source missing … Skipping」と表示して終了コード0で終わります。ただしこれは「中身が空のまま」という意味ではありません——skills/ 配下のSKILL.mdは既に実体を持っており(offensive-osint は4,734行)、READMEが挙げる行数ともほぼ一致します。この一手間は現在の版では省いて構いません

誰のための道具か——自社の露出面を測る使い方と、踏んではいけない線

向いている使い方

自社ドメインの棚卸し:法人名から保有ドメイン・ネットブロックを辿る org-attack-surface、公開ストレージを見る cloud-saas-exposure、偽装耐性を判定する email-domain-security は、いずれも「自分の資産が外からどう見えるか」を測るための手順です
買収・分社後の資産把握:忘れられたドメインやサブドメインが残っていないかの確認
経営層への説明exposure-risk-quantification は検出結果を金額とA〜Fのグレードに換算する手順を持っており、技術的な指摘を意思決定の言葉に翻訳する用途に向きます

踏んではいけない線

許可の無い相手に向けて実行しない。 これが唯一かつ絶対の線です。前述のとおり、それを機械的に止める仕組みはこのパックにありません
・委託先・子会社・SaaS事業者の資産は「自社の一部」に見えても別の主体です。書面での許可範囲を先に確定させてください
・日本では対象と手法によって不正アクセス禁止法などに触れ得ます。この記事は法的助言ではありません——実施前に法務・専門家へ確認してください

同種のツールとの位置づけ

  Claude-OSINT SpiderFoot等のスキャナ
形態 Claudeに読ませる手順書(マークダウン) 収集を実行するソフトウェア
実行主体 Claudeが手順を組み立てて実行 モジュールを選んで人が回す
再現性 会話に依存し揺れる 同じ設定なら同じ結果
状況への適応 得意(自然言語で組み替えられる) 設定の範囲内
導入コスト ファイルを置くだけ インストールと依存解決
監査のしやすさ 何をしたかは会話ログを追う 実行ログが構造化されている

置き換え合戦ではなく、再現性が要る工程はスキャナ、組み替えが要る工程はスキルパック、と分ける読み方が実態に近いはずです。スキャナ側は本体の開発が止まっているものも多く(SpiderFoot本家 smicallef/spiderfoot は、既定ブランチ master の最終コミットが2023年11月5日、最新リリースはv4.0で2022年4月。なお pushed_at は2026年を示しますが、これは既定ブランチ以外への push でも動くため生存判定には使えません)、その空白を「手順書+汎用エージェント」で埋めようとしているのがこのパックの立ち位置だと理解すると分かりやすくなります。

最後に導入形態の注意です。ライセンスはGitHub上の表示こそMITですが、リポジトリには LICENSE(MIT・コード用)と LICENSE-CONTENTCC BY 4.0・396行)の2つが置かれています。手順書のテキスト側はCC BY 4.0なので、自社リポジトリへ取り込んで再配布するなら表示義務が付きます。社内標準として配る前に、この点だけは確認しておいてください。

参照ソース

elementalsouls/Claude-OSINT — GitHub リポジトリ(SKILL.md 9本・LICENSELICENSE-CONTENTscripts/ 配下。本記事の件数とトークン数はすべてここを数えたもの)
Claude-OSINT SECURITY.md(用途の範囲と除外事項、soft scope-check の記述)
Claude Docs — Agent Skills(SKILL.md の frontmatter で有効なキーと、description が呼び出し判断に使われる仕組み)
Claude Docs — Skills in Claude Code(スキルの配置場所と読み込みのされ方)