原型 · 预览版:收录官方注册中心里的全部服务器,每 30 分钟同步一次。评价和账户功能将在后续阶段推出。
PopNx MCP为使用 AI 的人准备的 MCP 服务器 · 用大白话讲清楚

FragDenStaat

作者:notDIRK版本 0.1.0i★ –i在你的电脑上运行
注册名称io.github.notDIRK/fds-mcp

安装

概览

作者提供的说明(英文原文)

Freedom-of-information requests for Germany via FragDenStaat.de, the froide FOI portal.

PopNx MCP 的三大支柱

这三项永远不会合并成一个分数:意见、测量和人气是不同的东西。

它能帮你做什么

我们还没有为它写通俗的介绍。下面是我们从注册中心读取到的事实。

  • 连接方式: 在你的电脑上运行
  • 传输方式: stdio
  • 分类: 其他
  • 你需要填写:FDS_TOKEN

安装

选择你使用的 AI 应用,然后复制设置。

安装之前

  • 基础检查:1 项中通过 1 项
  • 在你的电脑上运行,拥有你的用户账户的权限(文件、网络、应用)。
  • 需要你自己填写: FDS_MCP_BASE_URL, FDS_TOKEN

标为机密的值是你账户的钥匙。千万不要分享给别人,也不要粘贴到聊天里。

你需要

  • PyPI已安装 Python 的 uv(用于 uvx 命令)

你用的是哪个应用?

在上方选择你的应用。我们会记住它,下次按钮会显示“安装到 …”。

打开 Claude Desktop → Settings → Developer → Edit Config,把下面的内容粘贴到 claude_desktop_config.json

{
  "mcpServers": {
    "fds": {
      "command": "uvx",
      "args": [
        "fds-mcp"
      ],
      "env": {
        "FDS_MCP_BASE_URL": "your-value",
        "FDS_TOKEN": "your-value"
      }
    }
  }
}

在终端中运行这条命令

claude mcp add fds --env FDS_MCP_BASE_URL=your-value --env FDS_TOKEN=your-value -- uvx fds-mcp

运行前请先填写空着的值。

在 Cursor 中打开

或者自己复制设置

粘贴到项目中的 .cursor/mcp.json,或 ~/.cursor/mcp.json

{
  "mcpServers": {
    "fds": {
      "command": "uvx",
      "args": [
        "fds-mcp"
      ],
      "env": {
        "FDS_MCP_BASE_URL": "your-value",
        "FDS_TOKEN": "your-value"
      }
    }
  }
}

浏览器会先询问是否打开应用,然后应用会显示设置并请你确认。密钥的值会留空,由你自己填写。

在 VS Code 中打开

或者自己复制设置

粘贴到项目中的 .vscode/mcp.json

{
  "servers": {
    "fds": {
      "type": "stdio",
      "command": "uvx",
      "args": [
        "fds-mcp"
      ],
      "env": {
        "FDS_MCP_BASE_URL": "your-value",
        "FDS_TOKEN": "your-value"
      }
    }
  }
}

浏览器会先询问是否打开应用,然后应用会显示设置并请你确认。密钥的值会留空,由你自己填写。

这个服务器在你的电脑上运行,而 ChatGPT 只能连接互联网上的服务器。请选择其他应用。

你的选择通过 Cookie 保存在这台设备上,无需账户。

需要你填写的值

  • FDS_MCP_BASE_URL env
    Which froide instance to use. Defaults to https://fragdenstaat.de
  • FDS_TOKEN 机密 env
    OAuth bearer token. Only needed for the tools that read your own requests or submit one; the four search tools work without it.

这些设置是根据作者在注册中心的条目生成的。如果 README 的写法不同,请以 README 为准。

它能做什么

它在你的电脑上运行;安装后,工具列表会显示在你的 AI 应用中。

基础检查i

我们检查的是任何人都能看到的信息;我们没有阅读代码。不适用的检查项不计入总数。 · 检查于 2026年11月8日

  • ✓ 通过

    作者与仓库一致

    注册名称已通过 GitHub 账户 notDIRK 验证,该账户拥有此仓库

  • … 尚未检查

    仍在维护

    我们还没有从 GitHub 读取这个仓库

  • … 尚未检查

    有许可证

    我们还没有从 GitHub 读取这个仓库

  • – 不适用

    端点有响应

    它在你的电脑上运行,没有互联网端点

  • – 不适用

    使用 OAuth 登录

    在你的电脑上运行,改用本地设置

  • … 尚未检查

    工具描述中没有隐藏指令

    它在你的电脑上运行;我们只能读取互联网端点的工具列表

与“其他”中的其他服务器比较i

  • 星标数多于此分类中其他 18498 个服务器的 0%
  • 发布到注册中心的时间比此分类中其他 18498 个服务器的 32% 更新
  • 基础检查结果等于或优于此分类中其他 18498 个服务器的 100%

与注册中心里这个分类中所有活跃的服务器比较。只有当发布者拥有该仓库时,星标数才计入。

常见问题

FragDenStaat 安全吗?

它在 1 项适用的基础检查中通过了 1 项。我们没有阅读代码。在添加密钥或令牌之前,请先看看这个服务器要求哪些权限,并使用只具备所需权限的密钥。

它需要哪些密钥或代码?

你需要填写:FDS_TOKEN

它在我的电脑上运行还是在云端?

它在你的电脑上运行。你的 AI 应用会在需要时启动它,数据不会经过作者的服务器(除非它自己调用在线服务)。

它还在维护吗?

GitHub 仓库最后更新于–,最新版本(0.1.0)于2个月前进入注册中心。

哪些应用可以使用它?

支持 MCP 的应用,例如 Claude Desktop、Claude Code、Cursor 和 VS Code。你的电脑上还需要有 Python (uv)。

有什么可以替代它?

同一分类中有:Spec Driven Development, Remote Desktop Commander, Readfirst

替代选择

同一分类中其他作者的服务器,按星标数排序。

如何看卡片:↓ 每周下载量i★ GitHub 星标i三大支柱:评价 · 检查 · 使用情况i更新 = 最新版本发布到注册中心的时间i

Spec Driven Development

MCP Server that facilitates spec-driven development workflows, not just Vibe Coding.

作者:formulahendry起步阶段↓ 66/周★ 44014个月前更新

在你的电脑上运行

Remote Desktop Commander

Remote Desktop Commander: use files, terminal and processes on your own computers from any AI app.

作者:desktop-commander正在增长★ 2113天前更新

在云端运行✓ desktopcommander.app

Readfirst

What to read and check before changing a file: project rules, risks, checks and tests per file.

作者:jeonghun917正在增长↓ 5325/周今天更新

在你的电脑上运行

作者的 README

打开 README

按原文从作者的仓库复制。PopNx MCP 没有审查或背书其内容。HTML、图片和脚本已被移除。链接会离开本站。

fds-mcp — FragDenStaat.de for AI assistants

An [MCP](https://modelcontextprotocol.io) server for [FragDenStaat.de](https://fragdenstaat.de), the German freedom-of-information platform built on [froide](https://github.com/okfde/froide).

*Deutsche Fassung*

Prepare a German freedom-of-information request by asking for it in plain language. Your assistant finds the authority that has to answer and proves why it is the right one, names the act that applies and the deadline it sets, tracks the requests you already sent, collects the replies and their attachments, and writes a new request to a local file that you read before anything leaves your machine.

What is MCP, and what does it do here?

MCP, the Model Context Protocol, is the standard that lets an AI assistant use outside tools — roughly what an extension does for a browser. fds-mcp is one such tool. Install it once and Claude, or any other MCP client, gains 15 tools that speak to FragDenStaat.de, the German freedom-of-information platform built on froide.

Four of them need no account and no token: searching authorities, reading an act, and working out who is responsible for a given place all work straight away.

Other froide instances

froide is the Django software underneath FragDenStaat.de, and its own README names a second production portal: fragdenstaat.at. Point this server at one with

export FDS_MCP_BASE_URL=https://fragdenstaat.at

Only https origins without a path or credentials are accepted, and the host allowlist that keeps the bearer token from following a link to a stranger is derived from this value — so with .at configured, fragdenstaat.de is a foreign host and is refused.

What that buys you, measured against fragdenstaat.at on 2026-09-05 and kept as live tests:

search_authorities, get_authority, get_lawwork, with no account
check_jurisdictioncannot work there — /api/v1/georegion/ holds 0 rows on .at against 24,216 on .de. Nothing this client can fix
the token-bound toolsneed an OAuth application registered on that instance
the pre-send rule setencodes German FOI law and is not portable. Treat submitting through another instance as unverified
What it looks like

You: Who has to answer a freedom-of-information request about the city of Bonn, and

under which act?

The assistant calls check_jurisdiction("Bonn"), gets the region chain and

Kommunalverwaltung Bonn (authority 3495), then get_authority(3495) for the acts that

apply and their deadlines — and reports the API URLs it used, so you can check the answer

instead of believing it.

Submitting is possible too, but it is deliberately the hardest thing this server does.


⚠️ POST /api/v1/request/ sends immediately and irreversibly

FragDenStaat's REST API has no draft mode, no preview and no undo. The moment a POST /api/v1/request/ succeeds, the e-mail is on its way to the authority, the request is public (by default) under CC0, and it cannot be recalled.

Worse, MakeRequestSerializer has no `law_type` field. The API therefore always files under publicbody.default_law, and because froide sorts by ("-meta", "-priority") that is almost always the *combined meta act* — not the specific act you meant. For a municipality in Rhineland-Palatinate, asking for the LTranspG (law 16) through the API silently files under "LTranspG, VIG" (law 18) instead.

Because of this, the recommended exit of this server is `build_submit_url`, which hands you a prefilled web form with the correct law_type and lets you press send yourself. submit_request exists, defaults to dry_run=True, and refuses unless five independent gates all agree — see Safety model.


Documentation

  • What the API can and cannot do — every limit we hit, how we measured it, the dead ends we tried, and the mistakes we made along the way
  • OAuth setup, with screenshots — registering the application, scopes, the redirect-URI rules, and what to do when the local HTTPS listener is blocked
  • README.de.md and docs/oauth-setup.de.md — the same documents in German. US English is the source; the German version follows it.

Installation

pip install fds-mcp

Or run it without installing anything, straight from PyPI:

uvx fds-mcp serve

From a checkout, for development:

git clone https://github.com/notDIRK/fds-mcp.git

cd fds-mcp pip install -e ".[dev]"

Requires Python 3.10 or newer.

Register it with your MCP client

The server speaks stdio. For Claude Code:

claude mcp add fds -- fds-mcp serve

For a client that reads a JSON config:

{

"mcpServers": { "fds": { "command": "fds-mcp", "args": ["serve"] } } }

Or without installing it at all:

{

"mcpServers": { "fds": { "command": "uvx", "args": ["fds-mcp", "serve"] } } }

The four green tools work immediately, with no account and no token.


OAuth setup

The yellow and red tools need an OAuth 2.0 bearer token. FragDenStaat supports exactly two authentication schemes for its API — OAuth2 and session cookies. There is no personal API key and no Basic Auth (froide's own docs/api.rst claims otherwise; it is out of date).

1. Register an application

Log in and open https://fragdenstaat.de/account/applications/register/. All account pages are protected by recent_auth_required, so you may be asked for your password again.

FieldValue
Nameanything, e.g. fds-mcp
Client typepublic (PKCE is then mandatory)
Authorization grant typeauthorization-code
Redirect URIhttps://localhost:8765/callback

Only the schemes `https` and `fragdenstaat` are accepted. http://localhost/... is rejected at registration time — this is OAUTH2_PROVIDER.ALLOWED_REDIRECT_URI_SCHEMES on the server. That is why the default redirect is an HTTPS loopback listener with a self-signed certificate that fds-mcp generates for you (via openssl), and why the fallback is fragdenstaat://callback with a manual paste.

2. Configure and log in
fds-mcp configure --client-id <your-client-id>

fds-mcp login

login runs Authorization Code + PKCE (S256), opens your browser, and catches the redirect on https://localhost:8765/callback. Your browser will warn about the self-signed certificate — that is the local listener; accept it.

Without a browser or without openssl:

fds-mcp login --manual     # uses fragdenstaat://callback, you paste the URL back

Tokens land in ~/.config/fds-mcp/tokens.json with mode 0600. Refresh happens automatically; refresh tokens are valid for 180 days.

fds-mcp status     # config, token and throttle state

fds-mcp whoami # the authenticated account fds-mcp logout --revoke

Scopes

fds-mcp requests read:user read:request make:request by default. Override with fds-mcp configure --scopes "read:user read:request" if you never want to submit.

ScopeNeeded for
read:useridentifying your own account (/api/v1/user/)
read:requestyour own, including non-public, requests
make:requestPOST /api/v1/request/ — submitting
write:message, write:attachmentdocumenting postal mail (not yet implemented)

Nothing here grants deletion. If you drop make:request, submit_request can never work, and everything else still does.


Tools

ToolTierAuthSide effect
search_authorities(query, jurisdiction=None, limit=20)🟢 greennonenone
get_authority(id)🟢 greennonenone
get_law(id)🟢 greennonenone
check_jurisdiction(place_name)🟢 greennonenone
list_my_requests(status=None, limit=50)🟡 yellowtoken, read onlynone
get_request(id)🟡 yellowtoken, read onlynone
get_messages(request_id)🟡 yellowtoken, read onlynone
list_attachments(message_id)🟡 yellowtoken, read onlynone
download_attachment(attachment_id, target_dir)🟡 yellowtoken, read onlywrites a local file
check_deadlines()🟡 yellowtoken, read onlynone
build_reply_draft(request_id, text, subject=None, path=None)🟡 yellowtoken, read onlywrites a local YAML file if path is given
create_request_draft(...)🔴 rednonewrites a local YAML file, no network at all
validate_draft(path)🔴 rednonereads the API for L01–L05
build_submit_url(path)🔴 rednonewrites a local .body.txt sidecar
submit_request(path, confirmation_token)🔴 redtoken + make:requestsends the request, irreversibly
send_reply_via_browser(draft_path, confirmation_token)🔴 red, opt-ina logged-in browser profilesends the reply, irreversibly

All four red tools take dry_run: bool = True.

send_reply_via_browser is the sixteenth tool and is not registered unless FDS_MCP_BROWSER_SEND=1 is set. Without that variable it does not appear in the tool list at all. Read Sending replies before you switch it on.

check_jurisdiction returns its evidence

It walks /georegion/?name= up its part_of chain and asks /publicbody/?regions= at every level, then returns the region chain, the matching authorities, and the list of API URLs it used. That matters in Rhineland-Palatinate, where an *Ortsgemeinde* is often not listed on FragDenStaat at all while the *Verbandsgemeindeverwaltung* that administers it is.

build_submit_url is two-step for long requests

Measured on 2026-09-05: fragdenstaat.de answers GET URLs above roughly 4096 bytes with HTTP 400 (4086 bytes → 200, 4106 bytes → 400). A typical 4000-character request exceeds that once URL-encoded. Above the limit the tool returns a short URL that prefills subject and law_type, plus the body in a .body.txt file next to your draft, which you paste into the form.

What FragDenStaat's API cannot do

These are frontend-only, with no REST equivalent. The server does not pretend otherwise:

  • replying to an authority — POST /api/v1/message/ only creates *postal* messages (OnlyPostalMessagesWritable), and subject/content are read-only serializer fields. E-mail replies go through /anfrage/ /send/message/, a CSRF-protected Django view that ignores bearer tokens. See Sending replies;
  • choosing the legal basis — no law_type in the serializer;
  • drafts — RequestDraft is not registered in the API router;
  • setting status, resolution, tags or the law after the fact; publishing a request; filing an objection or escalating to the state information commissioner.

Sending replies

An e-mail reply to an authority cannot be sent through the FragDenStaat API. Not with a different payload, not with an extra scope, not with a better token. Three measurements, taken on 2026-09-05 and kept honest by tests/test_api_contract.py:

  1. POST /api/v1/message/ with kind: "email" answers HTTP 400 and reports, under the key kind: *"Nachrichten dieser Art können nicht über die API erstellt werden."* That is froide's OnlyPostalMessagesWritable.
  2. The identical call with kind: "post" also answers 400 — the probe deliberately carries an unresolvable request URI, so nothing can be created either way — but it carries no `kind` error. That is the calibration. Without it the first measurement would prove nothing: a 400 could just as well come from the invalid URI, from the e

只显示了开头部分;其余内容请在仓库中阅读

问 PopNx