tenavis
v0.3.0
Published
Power Platform / Copilot Studio の市民開発資産を棚卸しし、リスクを診断する読み取り専用CLI
Maintainers
Readme
Tenavis
日本語
Power Platform / Copilot Studio の市民開発資産を棚卸しし、リスクを診断する読み取り専用 CLI。
社内で誰がどんなアプリ・フロー・エージェントを作ったのか、それが全社に公開されていないか、退職者が持ったままになっていないか — Tenavis はテナントを読むだけで一覧化し、リスクの高いものから順に提示します。設定変更は一切行いません。インストールから30分以内に「自社テナントの市民開発の全貌と上位リスク」を把握することを目標にした、情シス担当者・Power Platform 管理者のための診断ツールです(無料版)。
必要なもの
| 項目 | 内容 |
| -------- | ------------------------------------------------------------------------------------------------------ |
| OS | Windows / macOS |
| Node.js | 22 以上(node --version で確認。未導入なら nodejs.org から LTS 版) |
| 権限 | 実行ユーザーの委任権限の範囲で棚卸しします。テナント全体を見るには Power Platform 管理者相当が必要 |
| 事前作業 | Entra アプリ登録(全体管理者が1回だけ。約10分) |
| ブラウザ | サインインに使用(ブラウザを開けない環境では --auth device-code) |
1. 準備: Entra アプリ登録
Tenavis は BYO(Bring Your Own)アプリ方式です。製品として共有のクライアント ID を同梱せず、利用する組織が自分のテナントにアプリ登録を1回だけ作成します。これにより「どのアプリが何を読んだか」が自組織の監査ログに残ります。クライアントシークレットは作成しません(漏えいする資格情報を持たない設計)。
手順
Microsoft Entra 管理センター → ID > アプリケーション > アプリの登録 → 新規登録
- 名前:
Tenavis(任意) - サポートされているアカウントの種類: この組織ディレクトリのみ(単一テナント) を推奨
- リダイレクト URI: プラットフォームに「モバイル アプリケーションとデスクトップ アプリケーション」を選び
http://localhostを指定(ポート番号は付けない)
- 名前:
認証(Authentication) → 下部の 詳細設定 > パブリック クライアント フローを許可する を はい にして保存
--auth device-codeを使う場合は、リダイレクト URI にhttps://login.microsoftonline.com/common/oauth2/nativeclientも追加します
API のアクセス許可 → アクセス許可の追加 で、以下を**すべて「委任されたアクセス許可」**として追加
| API | 追加する委任アクセス許可 | 用途 | 省略した場合 | | ----------------------------------- | ------------------------------------------------------------------------------------------------------------------------------- | ------------------------------- | --------------------------------------------- | | Power Platform API |
EnvironmentManagement.Environments.Read/PowerApps.Apps.Read/PowerAutomate.Flows.Read/ResourceQuery.Resources.Read| 環境・アプリ・フロー・DLP | スキャン全体が実行できません(必須) | | Microsoft Graph |User.Read.All| 所有者の在籍突合 | 退職者が所有する資産を検出できません | | Dataverse(表示名: Dynamics CRM) |user_impersonation| Copilot Studio エージェント読取 | エージェントの認証設定を確認できません | | Power Apps Service | 表示される委任アクセス許可(User impersonation 系) | アプリの共有状況・接続一覧 | Everyone 共有の判定と接続一覧が取得できません |💡 API が名前で見つからない場合は、検索ボックスに appId(GUID)を貼り付けてください。 Power Platform API は
8578e004-a5c6-46e7-913e-12f58912df43、Power Apps Service は475226c6-020e-4fb2-8a90-7a972cbfc1d4です。同じ画面で 「(テナント名)に管理者の同意を与えます」 をクリックして承認
User.Read.Allは管理者同意が必須です。省略すると在籍突合が動作しません
概要 ページで次の2つを控える(どちらも秘密情報ではありません)
- アプリケーション(クライアント)ID
- ディレクトリ(テナント)ID
2. クイックスタート
# ID を環境変数に設定(macOS / Linux)
export TENAVIS_CLIENT_ID=<your-client-id>
export TENAVIS_TENANT_ID=<your-tenant-id>
# Windows PowerShell の場合
# $env:TENAVIS_CLIENT_ID = "<your-client-id>"
# $env:TENAVIS_TENANT_ID = "<your-tenant-id>"
# 環境一覧が出れば準備完了(ブラウザでサインインします)
npx tenavis envs
# 棚卸し + リスク診断
npx tenavis scan
# 共有・保管用の HTML レポート(1ファイル完結)
npx tenavis scan --format html --out tenavis-report.html--client-id / --tenant-id フラグで直接指定することもできます。生成された HTML はブラウザで直接開けます(外部への通信は発生しません)。
コマンド一覧
tenavis login サインイン(既定: ブラウザ認証)
tenavis envs 環境一覧の表示
tenavis scan [オプション] 棚卸し + リスク評価
tenavis explain <ルールID> ルールの意図を表示| オプション | 説明 |
| ----------------------------- | -------------------------------------------------------------- |
| --format console | 既定。画面にサマリと上位リスクを表示 |
| --format html | 自己完結1ファイルのレポート(共有・保管向け) |
| --format json | 棚卸しの生データ + 検出結果(他ツール連携向け) |
| --format sarif | 検出結果のみ(SARIF 2.1.0) |
| --out <ファイル> | 出力をファイルへ書き出し(全形式に対応) |
| --auth device-code | ブラウザを開けない環境用(テナント側で例外設定が必要な場合あり) |
| --client-id / --tenant-id | Entra アプリ登録の ID(環境変数でも指定可) |
npx tenavis explain sharing/everyone # ルールの意図と判定条件を表示検出するリスク
標準ルールセットの10ルールを評価します。
| 重大度 | ルール | 内容 |
| ------ | ---------------------------- | ------------------------------------------------ |
| 重大 | sharing/everyone | 組織全体(Everyone)に共有されたアプリ |
| 重大 | owner/departed | 無効化されたアカウントが所有する資産 |
| 重大 | agent/no-auth | 認証なしで公開された Copilot Studio エージェント |
| 重大 | dlp/uncovered-env | DLP ポリシーが適用されていない環境 |
| 警告 | connector/http-in-default | 既定環境での HTTP 系コネクタ使用 |
| 警告 | connector/personal-storage | 個人向けストレージ系コネクタへの接続 |
| 警告 | env/default-sprawl | 既定環境の資産数が閾値超過(乱立度) |
| 情報 | flow/broken | 失敗停止したまま放置されたフロー |
| 情報 | app/stale | 180日以上未更新かつ共有中のアプリ |
| 情報 | env/unmanaged-prod | Managed Environments でない本番環境 |
無料版の表示制限: 評価は全件に対して行いますが、詳細表示は重大度の高い上位10件までです。残りは件数のみ表示されます。
セキュリティ特性
- 読み取り専用: 書き込み系 HTTP メソッド(POST / PUT / PATCH / DELETE)は HTTP レイヤのガードで拒否します。この動作は自動テストで継続的に担保しています
- テレメトリなし: 利用状況・棚卸し結果を外部へ送信する仕組みはありません。通信先は Microsoft の認証・管理系 API のみです
- トークンを平文で保存しない: アクセストークンは OS のセキュアストレージまたはメモリ上のみで保持します
- HTML レポートは自己完結: 外部 CDN・画像・フォント・スクリプトを一切参照しません。レポートを開いてもインターネット通信は発生しません
- 資格情報を作成しない: アプリ登録にクライアントシークレット・証明書を作りません
⚠️ 出力ファイルの取り扱い
棚卸し結果には自社の内部情報が含まれます。社外への共有前に必ず内容を確認してください。
--format jsonの出力には、環境の Dataverse URL・環境 ID(既定環境の ID はテナント ID を含みます)・所有者のメールアドレスなど、テナントを識別できる情報が含まれます。他ツール連携で ID が必要なため意図的にそのまま出力していますTENAVIS_DEBUG=1を付けた実行のログには、API の生レスポンス(所有者名などの個人情報や一時的な署名付き URL)が含まれます。共有端末・共有ログ基盤では使用しないでください- 画面表示と HTML レポートではテナント ID を伏字にしています(
Default-***)。HTML に所有者名は含まれません
既知の制限
誤った安心につながらないよう、検出できない条件を明記します。
| 項目 | 状況 | | ----------------------------- | -------------------------------------------------------------------------------------------- | | フローの所有者の在籍突合 | 対応済み。ただしアプリケーションユーザー等の人でないユーザーが所有するフローは対象外です | | リスクの該当資産名 | 表示します(先頭3件+残件数)。ただし件数・真偽値で判定するルールでは件数のみです | | Everyone 共有の検出 | 実環境で確認済み。ただしセキュリティグループ経由の広範な共有は対象外です | | カスタムコネクタの検出 | コネクタ ID だけでは標準コネクタと区別できないため、HTTP 系のみを対象にしています | | フローの「失敗停止」判定 | 実環境で「停止」状態の値を観測できておらず、空振りの可能性があります | | Copilot Studio の公開チャネル | 取得に必要な API の検証ができていないため対象外です | | 常時監視・スケジュール実行 | 無料版は単発スキャンのみです |
困ったときは
AADSTS530035 が出てサインインできない
--auth device-code を使った場合にテナントのポリシーでブロックされています。既定のブラウザ認証(オプション指定なし)ではこのエラーは発生しませんので、まずそちらをお試しください。デバイスコードが必要な場合は、条件付きアクセスの「デバイス コード フローのブロック」ポリシーから実行者を除外するか(Entra ID P1 が必要)、セキュリティの既定値群を無効化する必要があります。
「取得できなかった項目」に 404 の警告が出る
cloudFlows ... 404 は、その環境に Dataverse データベースが無いことを意味します。Dataverse の無い環境にクラウドフローは存在しないため異常ではありません。スキャンは続行されます。
退職者が所有する資産が1件も出ない
Microsoft Graph の User.Read.All に管理者の同意が与えられていない可能性があります。同意が無い場合、Tenavis は誤検知を避けるため在籍突合そのものを行いません(「取得できなかった項目」に users の警告が出ます)。
アプリの共有状況が出ない / エージェントが出ない それぞれ Power Apps Service、Dataverse の委任アクセス許可が不足しています。上記「1. 準備」の権限表を確認してください。
ライセンス
本ソフトウェアの使用には**使用許諾契約(EULA)**が適用されます。全文は本パッケージに同梱の EULA.md をご覧ください(node_modules/tenavis/EULA.md)。無償・非独占・自組織テナントの診断目的での使用を許諾するものです。再配布・改変は制限されます(組織内のミラー・キャッシュは許容)。
同梱している OSS の権利表示は THIRD-PARTY-NOTICES.md にあります。
お問い合わせ: [email protected]
English
A read-only CLI that inventories citizen-developed Power Platform / Copilot Studio assets and diagnoses their risks.
Who built which apps, flows and agents inside your organisation? Are any of them shared with everyone? Are any still owned by people who have left? Tenavis answers these questions by only reading your tenant and presenting the highest-severity risks first. It never changes any setting. It is a diagnostic tool for IT administrators, designed so that you can see the whole picture of citizen development in your tenant within 30 minutes of installing it (free edition).
The Japanese text above is the authoritative version. This English section is provided for convenience; if the two differ, the Japanese wording governs. The EULA itself is written in Japanese and Japanese is its governing language.
Requirements
| Item | Details |
| ------------ | ----------------------------------------------------------------------------------------------------------------------------------------------- |
| OS | Windows / macOS |
| Node.js | 22 or later (check with node --version; get the LTS build from nodejs.org) |
| Permissions | Tenavis reads only within the delegated permissions of the signed-in user. Seeing the whole tenant requires a Power Platform administrator role |
| Prerequisite | One Entra app registration (done once by a global administrator, about 10 minutes) |
| Browser | Used for sign-in (use --auth device-code where no browser is available) |
1. Setup: Entra app registration
Tenavis uses a bring-your-own (BYO) app model. No shared client ID ships with the product; your organisation registers one app in its own tenant. As a result, every read Tenavis performs is attributable in your own audit logs. No client secret is created, so the registration holds no credential that could leak.
Steps
In the Microsoft Entra admin center, go to Identity > Applications > App registrations and choose New registration.
- Name:
Tenavis(any name works) - Supported account types: Single tenant is recommended
- Redirect URI: choose the Mobile and desktop applications platform and enter
http://localhost(no port number)
- Name:
Open Authentication and set Advanced settings > Allow public client flows to Yes, then save.
- If you plan to use
--auth device-code, also addhttps://login.microsoftonline.com/common/oauth2/nativeclientas a redirect URI.
- If you plan to use
Under API permissions > Add a permission, add all of the following as delegated permissions:
| API | Delegated permissions | Used for | If omitted | | ------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------- | -------------------------------------------------------- | | Power Platform API |
EnvironmentManagement.Environments.Read/PowerApps.Apps.Read/PowerAutomate.Flows.Read/ResourceQuery.Resources.Read| Environments, apps, flows, DLP | The scan cannot run at all (required) | | Microsoft Graph |User.Read.All| Checking whether owners still work here | Assets owned by departed users are not detected | | Dataverse (shown as Dynamics CRM) |user_impersonation| Reading Copilot Studio agents | Agent authentication settings cannot be checked | | Power Apps Service | The delegated permission offered (user impersonation) | App sharing status and connections | Everyone-sharing and the connection list are unavailable |💡 If an API does not appear by name, paste its appId (GUID) into the search box. Power Platform API is
8578e004-a5c6-46e7-913e-12f58912df43; Power Apps Service is475226c6-020e-4fb2-8a90-7a972cbfc1d4.On the same page, select Grant admin consent for (tenant).
User.Read.Allrequires admin consent; without it the owner reconciliation will not run.
From the Overview page, note these two values (neither is a secret):
- Application (client) ID
- Directory (tenant) ID
2. Quick start
# Set the IDs as environment variables (macOS / Linux)
export TENAVIS_CLIENT_ID=<your-client-id>
export TENAVIS_TENANT_ID=<your-tenant-id>
# On Windows PowerShell
# $env:TENAVIS_CLIENT_ID = "<your-client-id>"
# $env:TENAVIS_TENANT_ID = "<your-tenant-id>"
# If the environment list appears, you are ready (a browser opens for sign-in)
npx tenavis envs
# Inventory and risk diagnosis
npx tenavis scan
# A single-file HTML report for sharing or archiving
npx tenavis scan --format html --out tenavis-report.htmlYou can also pass --client-id / --tenant-id directly. The generated HTML opens straight in a browser and performs no outbound requests.
Commands
tenavis login Sign in (browser-based by default)
tenavis envs List environments
tenavis scan [options] Inventory and evaluate risks
tenavis explain <ruleId> Explain what a rule checks| Option | Description |
| ----------------------------- | ----------------------------------------------------------------------------- |
| --format console | Default. Prints a summary and the top risks |
| --format html | Self-contained single-file report |
| --format json | Raw inventory plus findings (for tool integration) |
| --format sarif | Findings only (SARIF 2.1.0) |
| --out <file> | Write the output to a file (all formats) |
| --auth device-code | For environments without a browser (your tenant policy may need an exception) |
| --client-id / --tenant-id | Entra app registration IDs (environment variables also work) |
Detected risks
Tenavis evaluates ten rules from its bundled baseline rule set.
| Severity | Rule | What it finds |
| -------- | ---------------------------- | ---------------------------------------------------------- |
| Error | sharing/everyone | Apps shared with the entire organisation |
| Error | owner/departed | Assets owned by a disabled account |
| Error | agent/no-auth | Copilot Studio agents published without authentication |
| Error | dlp/uncovered-env | Environments with no DLP policy applied |
| Warning | connector/http-in-default | HTTP-family connectors used in the default environment |
| Warning | connector/personal-storage | Connections to consumer storage connectors |
| Warning | env/default-sprawl | Asset count in the default environment above the threshold |
| Info | flow/broken | Flows left suspended after failures |
| Info | app/stale | Shared apps untouched for 180+ days |
| Info | env/unmanaged-prod | Production environments without Managed Environments |
Free-edition display limit: every finding is evaluated, but only the top 10 by severity are shown in detail. The rest are reported as a count.
Security characteristics
- Read-only: write methods (POST / PUT / PATCH / DELETE) are rejected at the HTTP layer, and automated tests keep it that way
- No telemetry: nothing about your usage or results is sent anywhere. Tenavis talks only to Microsoft authentication and management APIs
- Tokens are never stored in plain text: they live in the OS secure storage or in memory only
- Self-contained HTML report: no external CDN, image, font or script is referenced, so opening a report causes no network traffic
- No credentials created: the app registration has no client secret or certificate
⚠️ Handling output files
Scan results contain internal information about your organisation. Review them before sharing outside your company.
--format jsonoutput contains tenant-identifying information such as Dataverse URLs, environment IDs (the default environment ID contains your tenant ID) and owner e-mail addresses. This is deliberate, because integrations need those IDs- Logs produced with
TENAVIS_DEBUG=1contain raw API responses, including personal data such as owner names and temporary signed URLs. Do not use it on shared machines or shared logging platforms - Console output and the HTML report mask the tenant ID (
Default-***), and the HTML report contains no owner names
Known limitations
Stated explicitly so that a clean report is not mistaken for a clean tenant.
| Area | Status | | --------------------------------- | ---------------------------------------------------------------------------------------------------------- | | Flow owner reconciliation | Supported, except for flows owned by application or system users (they are not people) | | Named assets behind a risk | Shown (first 3 plus a count), except for rules that evaluate counts or booleans | | Everyone-sharing detection | Verified against a real tenant, but broad sharing via security groups is out of scope | | Custom connector detection | Connector IDs alone cannot distinguish custom from standard connectors, so only the HTTP family is covered | | Detecting failed/suspended flows | The "suspended" state value has not been observed on a real tenant, so this rule may not fire | | Copilot Studio published channels | Out of scope; the required API could not be verified | | Continuous monitoring | The free edition performs one-off scans only |
Troubleshooting
Sign-in fails with AADSTS530035
Your tenant blocks the device code flow. This happens only with --auth device-code; the default browser sign-in is unaffected, so try that first. If you do need device code, either exclude the user from the "Block device code flow" conditional access policy (requires Entra ID P1) or disable security defaults.
A 404 warning appears under "items that could not be retrieved"
cloudFlows ... 404 means that environment has no Dataverse database. Environments without Dataverse cannot contain cloud flows, so this is not an error. The scan continues.
No assets owned by departed users are reported
Admin consent for Microsoft Graph User.Read.All may be missing. Without it, Tenavis skips owner reconciliation entirely rather than risk false positives, and reports a users warning.
App sharing status or agents are missing The Power Apps Service or Dataverse delegated permission is missing. See the permission table in step 1.
License
Use of this software is governed by an End User License Agreement (EULA). The full text is bundled with this package as EULA.md (node_modules/tenavis/EULA.md). It grants a free, non-exclusive licence to use the software for diagnosing your own organisation's tenant; redistribution and modification are restricted (mirroring or caching within your organisation is permitted). The EULA is written in Japanese and Japanese is its governing language.
Attribution for bundled open-source software is in THIRD-PARTY-NOTICES.md.
Contact: [email protected]
