# ジョブとプラグイン: MQTTトピックの権限

**対象:** ジョブタスクまたは管理対象プラグイン向けにMQTTトピックの権限を構成する統合担当者向けです。

本ページは、MQTTブローカーが統合担当者が作成したコンポーネントに対してトピック権限をどのように適用するかをまとめたリファレンスです。MQTTがより広い統合フローのどこに位置するかの説明については、[カスタムジョブ統合ガイド](/keeperpam/jp/endpoint-privilege-manager/integrations/custom-job-guide.md)の手順3および[カスタムプラグイン統合ガイド](/keeperpam/jp/endpoint-privilege-manager/integrations/custom-plugin-guide.md)の手順2をご参照ください。

## 適用の仕組み

トピック権限はコンポーネントのJSONファイルで宣言され、実行時にブローカーによって適用されます。適用モデルは以下の4段階です。

**宣言:** ジョブはジョブルートオブジェクトの `mqttTopics` に許可トピックを宣言します。プラグインはプラグインJSONの `metadata.mqttTopics` に宣言します。

**接続:** コンポーネントがブローカーへ接続すると、ブローカーは起動済みプロセスのレジストリに対してクライアントを検証し、クライアントIDの形式から当該接続がどのジョブまたはプラグインに属するかを特定します。

**適用:** すべてのpublishとsubscribeが、そのコンポーネントの宣言済み許可リストに対してチェックされます。宣言されていないトピックへの呼び出しは拒否されます。MQTT接続自体は切断されず、個々の操作だけが失敗します。

**サイレントな拒否:** 拒否されたpublishまたはsubscribeは、多くの場合クライアントから見えるエラーになりません。接続レベルでは成功しているように見えるのにメッセージが届かない場合は、まずトピック宣言の漏れを確認してください。

## ジョブ

ジョブタスクのトピック権限は、タスク定義の内側ではなく、ジョブルートオブジェクトに宣言します。

```json
"mqttTopics": {
  "allowedPublications": ["KeeperLogger"],
  "allowedSubscriptions": []
}
```

<table data-header-hidden="false" data-header-sticky><thead><tr><th width="209.333251953125">フィールド</th><th>目的</th></tr></thead><tbody><tr><td><code>allowedPublications</code></td><td>タスクがpublishしてよいトピックです。バイナリがpublishするすべてのトピックを含める必要があります (<code>KeeperLogger</code>、<code>eventTopic</code>、カスタムトピックなど)。</td></tr><tr><td><code>allowedSubscriptions</code></td><td>タスクが subscribe してよいトピックです。ログのみpublishするジョブタスクでは多くの場合空です。</td></tr></tbody></table>

`mqttTopics` が少なくとも1エントリ付きで存在する場合、エージェントはタスク開始前に `KEEPER_JOB_ID` と `KEEPER_JOB_NAME` を環境変数として注入します。正しいMQTTクライアントIDの構成に必要です。

タスクがMQTTをまったく使わない場合は、`mqttTopics` ごと省略できます。その場合、`KEEPER_JOB_ID` と `KEEPER_JOB_NAME` は注入されません。

## プラグイン

管理対象プラグインのトピック権限は、プラグインJSONの `metadata` 配下に宣言します。

```json
"metadata": {
  "mqttTopics": {
    "publish": ["KeeperLogger", "MyPlugin/Responses/+"],
    "subscribe": ["MyPlugin/Commands/+"]
  }
}
```

<table data-header-hidden="false" data-header-sticky><thead><tr><th width="109.99993896484375">フィールド</th><th>目的</th></tr></thead><tbody><tr><td><code>publish</code></td><td>プラグインがpublishしてよいトピックです。</td></tr><tr><td><code>subscribe</code></td><td>主たる <code>Subscription.Topic</code> に加えて subscribe してよいトピックです。</td></tr></tbody></table>

主たる `Subscription.Topic` は `metadata.mqttTopics.subscribe` とは別フィールドです。両方とも subscribe の対象になります。主たる購読に加える追加トピックは `metadata.mqttTopics.subscribe` に宣言し、置き換えではなく併記してください。

## 並べて比較

<table data-header-hidden><thead><tr><th width="202.333251953125"></th><th width="236.4444580078125"></th><th></th></tr></thead><tbody><tr><td></td><td>ジョブ (<code>Jobs/*.json</code>)</td><td>プラグイン (<code>Plugins/*.json</code>)</td></tr><tr><td>宣言の場所</td><td>ジョブルートの <code>mqttTopics</code></td><td>プラグインJSON内の <code>metadata.mqttTopics</code></td></tr><tr><td>Publishのフィールド名</td><td><code>allowedPublications</code></td><td><code>publish</code></td></tr><tr><td>Subscribeのフィールド名</td><td><code>allowedSubscriptions</code></td><td><code>subscribe</code></td></tr><tr><td>主たる購読</td><td>該当なし</td><td><code>Subscription.Topic</code> として別途宣言</td></tr><tr><td>MQTTクライアントIDの形式</td><td><code>{KEEPER_JOB_ID}_{Token}_{Pid}</code></td><td><code>{PluginName}_{Pid}</code> または <code>{PluginName}_{UserName}_{Pid}</code></td></tr><tr><td>環境変数</td><td><code>mqttTopics</code> 設定時に <code>KEEPER_JOB_ID</code>、<code>KEEPER_JOB_NAME</code> を注入</td><td>環境変数では注入しない。プラグインは自身の <code>id</code> から識別を読み取る</td></tr></tbody></table>

## MQTTクライアントID

ブローカーはクライアントIDの形式によって接続をジョブまたはプラグインに関連付け、正しい権限セットを適用します。形式が誤っていると、トピック宣言が正しくても権限チェックに失敗します。

**ジョブタスク向け:**

```
{KEEPER_JOB_ID}_{ExecutableToken}_{ProcessId}
```

* `KEEPER_JOB_ID` — エージェントが注入する環境変数から取得
* `ExecutableToken` — バイナリの短い安定識別名。アンダースコアやパス文字は含めない
* `ProcessId` — 現在のOSプロセスIDの10進表記
* ジョブの `id` — アンダースコアを含めない。ブローカーは `_` で分割してジョブID部分を取り出す

例: `my-scanner_SecretScanner_48292`

**管理対象プラグイン向け:**

```
{PluginName}_{ProcessId}                      (サービスアカウント)
{PluginName}_{UserName}_{ProcessId}           (ユーザーセッション)
```

* `PluginName` — プラグインの `id` と一致させる
* プラグインではジョブの3要素形式のクライアントIDを使わない。形式に応じてブローカー側で異なる権限ロジックが適用される

## ワイルドカード

<table data-header-hidden="false" data-header-sticky><thead><tr><th width="106.333251953125">パターン</th><th width="275.333251953125">範囲</th><th>用途</th></tr></thead><tbody><tr><td><code>+</code></td><td>ちょうど1レベルのトピックに一致</td><td>種別ごとにサブトピックが変わるコマンド/応答パターン。例: <code>Commands/+</code> は <code>Commands/scan</code> と <code>Commands/reset</code> に一致するが <code>Commands/a/b</code> には一致しない</td></tr><tr><td><code>#</code></td><td>プレフィックス以下のすべてのレベルに一致</td><td>広い監視やログパターン。必要な場合に限り慎重に利用</td></tr></tbody></table>

本番では明示的なトピック文字列を優先してください。ワイルドカードは開発時には便利ですが、ブローカーが強制できる範囲は狭くなります。コマンド集合が限定的なら、トピックを列挙するのがよいでしょう。

```json
"publish": [
  "KeeperLogger",
  "MyPlugin/Responses/scan",
  "MyPlugin/Responses/reset"
]
```

## KeeperLogger

`KeeperLogger` は構造化ログ配信用の既知のトピックです。構造化ログメッセージをpublishするジョブタスクまたはプラグインは、publishリストにこれを含める必要があります。ペイロードは `RequestMessage` のJSON形式に従う必要があります。形式の詳細とコード例はカスタムジョブ統合ガイドの[手順5](https://claude.ai/integration/custom-job-guide#step-5-publish-log-messages-to-keeperlogger)をご参照ください。

管理者がコンポーネント向けに明示的に権限を拡張していない限り、製品内部のトピック (ポリシー、API など) にはpublishしないでください。

## よくある失敗

<table data-header-hidden="false" data-header-sticky><thead><tr><th>症状</th><th>原因</th><th>対処</th></tr></thead><tbody><tr><td>Publishがサイレントに失敗する</td><td>トピックが <code>allowedPublications</code> / <code>publish</code> にない</td><td>正しい宣言リストにトピックを追加する</td></tr><tr><td>Subscribe がサイレントに失敗する</td><td>トピックが <code>allowedSubscriptions</code> / <code>subscribe</code> にない</td><td>正しい宣言リストにトピックを追加する</td></tr><tr><td><code>eventTopic</code> のpublishが拒否される</td><td><code>eventTopic</code> 文字列が <code>allowedPublications</code> に含まれていない</td><td>正確に一致する <code>eventTopic</code> 文字列を <code>allowedPublications</code> に追加する (文字列は完全一致が必要)</td></tr><tr><td>宣言は正しいのに権限チェックが失敗する</td><td>クライアントIDの形式が誤っている (ジョブ用形式をプラグインに使うなど)</td><td>コンポーネント種別に合ったクライアントID形式か確認する</td></tr><tr><td>MQTT接続そのものが拒否される</td><td>プロセスが起動済みプロセスのレジストリにない</td><td>手動ではなくエージェント (ジョブランナーまたはオーケストレーター) がバイナリを起動しているか確認する。起動時の再試行を追加する</td></tr></tbody></table>


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.keeper.io/keeperpam/jp/endpoint-privilege-manager/reference/job-and-plugin-mqtt-topic-permissions.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
