Agent First BI for Power BI.
Your agents ask. Your Power BI answers, with one definition per metric.
How much did we sell last year, by month? I need it as a file.
search"net sales"net_salesget_metricnet_salesSUM(Sales[Net amount])execute_daxon Sales12 rows as you, csv_urlcurl -ocsv_urlnet_sales_by_month_2025.csv
- Agents and internal tools
- agents ask in plain words, as you. tools the same DAX, with an API key.
- Power BI Metrics Book
- metric net_sales, from 3 measures. result a CSV file, every row.
- Power BI
- datasets Sales, Finance, Marketing. access read, never changed.
Power BI has the numbers you trust. Your agents can't use them yet.
- Power BI reports hold the right numbers, for people to read.
- An agent on raw DAX can ask anything, and guesses what each measure means.
- Microsoft's own connectors are built for Fabric and the Microsoft stack.
Power BI Metrics Book gives any agent the definitions your reports use.
Three things break when an agent writes its own DAX
It picks the wrong measure
Net sales, Revenue and Net Sales are one calculation in three datasets. The agent can't tell.
Here: the sync finds they are one metric,
net_sales, and names its variants.It fills its context
A year of daily sales lands in the chat, and the agent loses the thread.
Here: the agent downloads the full result as a CSV file into its folder. Only a preview of up to 100 rows goes into the context.
It runs as someone else
A shared account answers with its own rights, not the rights of the person asking.
Here: every query runs with the asking person's own Power BI sign-in, so row-level security holds.
From an empty VM to your first agent query in about 30 minutes
Three commands start the stack. Then a setup in your browser checks each step before the next.
$ uv tool install powerbi-metrics-bookpbmb writes the deployment and runs the admin commands.
$ pbmb init ./deployment \
--public-base-url https://metrics.example.com
$ cd ./deploymentWrites compose.yml, .env with new random passwords, access/ for your own policies and an AGENTS.md for your agent.
$ docker compose up -d --waitThe api, the worker, Postgres and Cerbos start and report healthy.
$ docker compose exec api server setup-linkPrints a link. Open it in your browser to start the setup.
- Address
- The app registration
- The scanner
- What to sync
- Sign-in
- Who gets in
- Search
- Agents
- First sync
- Security
Each step gives the values to copy and checks the result with a real call before the next.
$ claude mcp add --transport http powerbi_metrics_book \
https://metrics.example.com/api/mcp
# then run /mcp, choose powerbi_metrics_book and sign inCodex and Cursor take the same address. The section below has both.
Not released yet. These commands work from 0.1, the first release. Until then, run it on the sample tenant.
Add one address to your agent
The MCP connector is the main way in. Each agent signs in as you, through your browser, so it reads only what your Power BI already lets you read.
Add the address
Your deployment's address with
/api/mcpon the end. One command in Claude Code or Codex, one file in Cursor.Sign in through your browser
Press Allow on the consent screen. It names you, the client and where it sends you back.
Ask
The agent searches the book, reads the metric's definition and runs its DAX as you. A big result stays on the server until the agent asks for it.
claude mcp add --transport http powerbi_metrics_book \
https://metrics.example.com/api/mcp
# then run /mcp, choose powerbi_metrics_book and sign in# ~/.codex/config.toml
[mcp_servers.powerbi_metrics_book]
url = "https://metrics.example.com/api/mcp"
# then sign in
codex mcp login powerbi_metrics_book// ~/.cursor/mcp.json
{
"mcpServers": {
"powerbi_metrics_book": {
"url": "https://metrics.example.com/api/mcp"
}
}
}The command line
For scripts, and for agents without MCP:pbmb login --url https://metrics.example.com
The REST API
For a job that runs without a person, with a service-account key and the same rules as everyone else.
Build internal tools on the same numbers
Your agent finds the data with you over MCP. Then your tool runs the same DAX with an API key. You never write Power BI sign-in code.
# once, as an admin
$ pbmb sa create sales-dashboard \
--owner data-team@example.com \
--role viewer --workspace <workspace id>
$ pbmb sa keys create sales-dashboard \
--expires-in-days 30
# then from your tool, with the DAX your agent wrote
$ curl -X POST "$PBMB_URL/api/v1/queries" \
-H "Authorization: Bearer $PBMB_API_KEY" \
-H "Content-Type: application/json" \
-d '{"dataset": "Sales", "dax": "EVALUATE ..."}'POST /api/v1/queries answered 201 with 12 rows. Numbers from the sample tenant's Sales dataset.A service account queries only after an admin turns onpowerbi.service_account_queries. It runs as the app's own service principal, so it never queries a dataset with row-level security.
Everything runs on one VM
You run it yourself, with Docker Compose on one VM of at least 2 vCPUs, 4 GB of memory and 40 GB of disk. The deploy guides say where to get one. One deployment serves one organisation and one Power BI tenant.
Where to run it
Each guide ends with pbmb admin status passing against the new address, and says who acts at each step.
Open source, under Apache 2.0
The code, the docs and the issues are on GitHub. Nothing is held back for a paid edition, because there is none.
Report a bug or ask for a feature
Open an issue on GitHub. The templates ask for what a fix needs.
Report a security issue
Privately, never in a public issue. The page says how, and what happens next.
Contribute
How to set up, run the whole stack on the sample tenant, check a change and open a pull request.
Metrics Book
The sister project, for a company that is not tied to Power BI. The two share one look and one set of words.
Need help with implementation or strategy?
Enum Studio builds and maintains Power BI Metrics Book, and helps companies set it up and build on it.