io.github.woonstadrotterdam/monumenten
OfficialThis server lets AI assistants look up Dutch address identifiers and check monumental/heritage statuses of properties.
Convert Dutch addresses to BAG verblijfsobject IDs, using postal code + house number or street + house number + city.
Handle address variations such as house letters (30A) and suffixes (30-2).
Check whether a verblijfsobject is a rijksmonument (national monument), including monument number, URL, and source.
Check whether a property lies within a nationally protected cityscape (rijksbeschermd stads- of dorpsgezicht) and get its name.
Check municipal monument status and its legal basis.
Get the current province of the property.
Return structured results for use by AI assistants, with clear errors for validation or lookup failures.
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@io.github.woonstadrotterdam/monumentenIs Coolsingel 30 in Rotterdam a rijksmonument?"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
Monumenten MCP Server ποΈ
A Model Context Protocol (MCP) server that enables AI assistants to check monumental status of Dutch addresses relevant for woningwaardering (rent-point system). Connects to the Dutch BAG (Basisadministratie Adressen en Gebouwen) data and Ministry of Cultural Heritage (Rijksdienst voor het Cultureel Erfgoed) to identify national monuments, nationally protected cityscapes, and municipal monuments.
Built on the MCP Python SDK v2 (MCPServer). Tools return structured results; validation and lookup failures raise ToolError (is_error=true) so the model can retry.
Requires Python 3.11+.
This MCP server is based on themonumenten package. For more information, see the monumenten package.
What This Does
This MCP server allows AI assistants to:
π Find verblijfsobject IDs - Convert Dutch addresses to BAG identifiers (
verblijfsobject_id)ποΈ Check monumental status - Determine if a property is protected as cultural heritage
π Support flexible address input - Search by postal code + house number or full address
π Handle address variations - Support house letters and suffixes (30A, 30-2, etc.)
Available Tools
Tool | Parameters | Result |
|
| Structured |
|
| Structured monumental status (provincie, rijksmonument, rijksbeschermd stads-/dorpsgezicht, municipal monument; |
Related MCP server: homedata-mcp
Quick Setup
Add to your AI assistant's MCP configuration:
{
"mcpServers": {
"monumenten": {
"command": "uvx",
"args": ["mcp-monumenten"]
}
}
}For local development:
{
"mcpServers": {
"monumenten": {
"command": "uv",
"args": ["run", "--project", "/path/to/mcp-monumenten", "mcp-monumenten"]
}
}
}Streamable HTTP (mcp-monumenten --http) listens on http://127.0.0.1:8000/mcp by default.
Claude Code plugin
Requires uv. Then:
/plugin marketplace add woonstadrotterdam/mcp-monumenten
/plugin install monumenten@woonstad-rotterdamOr add the server directly: claude mcp add monumenten -- uvx mcp-monumenten.
Usage Examples
Finding Monumental Status
"What is the monumental status of Coolsingel 30, Rotterdam?"
The AI will:
Convert the address to a BAG verblijfsobject ID
Check monument registries
Report rijksmonument status, rijksbeschermd stads-/dorpsgezicht, or municipal monument designation
"Is 1234AB 30-2 a rijksmonument?"
The AI can handle:
Postal code + house number format
House number suffixes (30-2, 30A, etc.)
Direct verblijfsobject ID lookups
Address Flexibility
The server handles Dutch address formats:
1234AB 30- Basic postal code + house number1234AB 30-2- With house number suffix1234AB 30A- With house letterCoolsingel 30, Rotterdam- Full street address
Installation
Via uvx (Recommended)
uvx mcp-monumentenLocal Development
git clone https://github.com/woonstadrotterdam/mcp-monumenten.git
cd mcp-monumenten
uv sync
uv run --project . mcp-monumentenData Sources
Kadaster - BAG (Basisadministratie Adressen en Gebouwen) - Official Dutch address registry
RCE (Rijksdienst voor het Cultureel Erfgoed) - National monuments registry
License
MIT License - see LICENSE file for details.
Available Tools
2 toolsget_monumental_statusARead-only
Get the monumental status of a verblijfsobject.
Always mention the source for the Rijksmonument status if it is a Rijksmonument. (RCE = Rijksdienst voor het Cultureel Erfgoed.) Reply in the user's language. provinciaal_monument is not looked up.
| Name | Required | Description | Default |
|---|---|---|---|
| bag_verblijfsobject_id | Yes | The verblijfsobject ID (16 digits) |
Output Schema
| Name | Required | Description |
|---|---|---|
| provincie | No | Current Dutch province of the verblijfsobject. Null if the provincie lookup failed. |
| rijksmonument | No | |
| rijksmonument_url | No | |
| rijksmonument_bron | No | |
| provinciaal_monument | No | Provincial monument. Always null: this status is not looked up. It only exists in Noord-Holland and Drenthe, and is mutually exclusive with rijksmonument and gemeentelijk_monument. If provincie is one of those or unknown, and the other monument flags are not true, tell the user this was not checked, in the user's language. Do not report it as false. |
| rijksmonument_nummer | No | |
| gemeentelijk_monument | No | |
| bag_verblijfsobject_id | Yes | |
| rijksbeschermd_gezicht | No | Nationally protected town or village scape (rijksbeschermd stads- of dorpsgezicht). false does not mean the address is outside a municipal or provincial beschermd stadsgezicht; those are not looked up. |
| rijksbeschermd_gezicht_naam | No | |
| grondslag_gemeentelijk_monument | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
The annotations already provide readOnlyHint=true and openWorldHint=true, so the description is not burdened with basic safety disclosure. It adds useful behavioral context: always cite the RCE source for Rijksmonument status, reply in the user's language, and do not expect provinciaal_monument to be resolved. This adds genuine value beyond the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The purpose is front-loaded in a single clear sentence, and the additional instructions are terse and each earns its place. The structure is slightly loose due to the parenthetical abbreviation and the mixing of output formatting with tool behavior, but there is no filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Given the single fully documented parameter corrections and the presence of an output schema, the description covers the important non-obvious behaviors: source citation, language handling, and the provinciaal_monument limitation. An explicit pointer to the sibling for obtaining the ID would improve completeness, but that is more of a usage-routing enhancement than a critical gap.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%: the schema already describes bag_verblijfsobject_id as the 16-digit verblijfsobject ID. The description does not add further meaning about the parameter, so the baseline 3 is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly identifies the action and resource: it gets the monumental status of a verblijfsobject. The sibling get_verblijfsobject_id is clearly a different operation, but the description does not explicitly contrast the two, so it falls just short of a 5.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description implies when to use the tool (when a verblijfsobject ID is known and monumental status is needed) and explicitly states that provinciaal_monument is not looked up. However, it does not mention the sibling get_verblijfsobject_id or explain when that alternative should be used, leaving the routing largely implicit.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_verblijfsobject_idARead-only
Get verblijfsobject ID using address.
Use postal_code + house_number OR street + house_number + city. Additional filters like house_letter and house_suffix can be provided for more precise matching.
| Name | Required | Description | Default |
|---|---|---|---|
| city | No | City name for search mode 2, e.g. 'Rotterdam' | |
| street | No | Street name for search mode 2, e.g. 'Coolsingel' | |
| postal_code | No | Dutch postal code for search mode 1, e.g. '1234AB' | |
| house_letter | No | House letter, e.g. 'A' in '30A' | |
| house_number | Yes | The house number, e.g. '30' | |
| house_suffix | No | House number suffix/addition, e.g. '2' in '30-2' |
Output Schema
| Name | Required | Description |
|---|---|---|
| matches | Yes |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true and openWorldHint=true, so the read-only nature is covered. The description adds behavioral context about search modes and filtering precision, but it does not disclose potential behavior such as multiple matches, no-match handling, or whether the result is unique. Given the annotation coverage, a 3 is appropriate.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is extremely conciseβfour short linesβand front-loads the purpose. Each sentence serves a clear function: stating the outcome, giving the two search modes, and noting optional filters. There is no repetition or wasted text.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The tool has 6 parameters, an output schema, and 100% schema description coverage, so the description need not explain return values. It adequately explains how to invoke the tool via the two search modes and optional filters. The only minor gap is a lack of explicit guidance about when to prefer the sibling tool, but that is not critical for correct invocation.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the baseline is 3. The description adds significant meaning by explaining the valid parameter combinations (postal_code+house_number vs street+house_number+city) and clarifying that house_letter and house_suffix are precision-enhancing filters. This goes beyond the schema's individual field descriptions and helps the agent choose the right parameters.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with 'Get verblijfsobject ID using address,' which states a specific verb, resource, and purpose. It clearly distinguishes the tool from its only sibling, get_monumental_status, since that tool concerns monumental status rather than ID lookup. No ambiguity remains about what the tool does.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description provides clear usage instructions by specifying two valid search modes: postal_code + house_number OR street + house_number + city. It also notes that house_letter and house_suffix are additional filters for 'more precise matching.' However, it does not explicitly contrast with the sibling tool or state when not to use this tool, leaving that to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
1 tool update
v3.0.1- Changed
get_monumental_status3 fields changed- added
Output schema / properties / provinciaal_monumentAdded value: +{ + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "default": null, + "description": "Provincial monument. Always null: this status is not looked up. It only exists in Noord-Holland and Drenthe, and is mutually exclusive with rijksmonument and gemeentelijk_monument. If provincie is one of those or unknown, and the other monument flags are not true, tell the user this was not checked, in the user's language. Do not report it as false.", + "title": "Provinciaal Monument" +} - added
Output schema / properties / provincieAdded value: +{ + "anyOf": [ + { + "type": "string" + }, + { + "type": "null" + } + ], + "default": null, + "description": "Current Dutch province of the verblijfsobject. Null if the provincie lookup failed.", + "title": "Provincie" +} - added
Output schema / properties / rijksbeschermd_gezicht / descriptionAdded value: +"Nationally protected town or village scape (rijksbeschermd stads- of dorpsgezicht). false does not mean the address is outside a municipal or provincial beschermd stadsgezicht; those are not looked up."
2 tool updates
v3.0.0- First observed
get_monumental_status - First observed
get_verblijfsobject_id
TDQS
Scored across 2 tools
The two tools have clearly distinct purposes: one resolves an address to a verblijfsobject ID, and the other retrieves monumental status for a verblijfsobject. There is no overlap or ambiguity between them.
Both tools follow a consistent get_<object>_<attribute> pattern, though the second tool's name (get_verblijfsobject_id) describes the return value rather than the resource attribute, which is a minor deviation.
Two tools is on the thin side for a server, but the narrow domain (looking up monumental status by address) makes the count defensible. It is borderline but not unreasonable.
The two tools form a complete workflow: address β verblijfsobject ID β monumental status. However, there is no direct lookup by verblijfsobject ID, no monument details endpoint, and no support for provinciaal monument lookups, leaving some gaps.
Maintenance
Related MCP Connectors
Address validation & geocoding for AI agents: 240+ countries, UK PAF, free US/CA enrichment
MCP server for structured Dutch vehicle data and license plate intelligence. Access RDW-based vehicle specifications, registration details, APK information, fuel and emissions data, weights, dimensions, ownership-related signals and other vehicle knowledge through KentekenKompas.nl. Built for AI assistants, agents and applications that need reliable, machine-readable information about vehicles registered in the Netherlands.
Dutch property report by address: build year, energy label, neighbourhood, monument, schools.
Resolve any government entity worldwide and submit service requests. Open civic data for AI agents.
Related MCP Servers
- AlicenseNot gradedqualityDmaintenanceEnables natural language search and exploration of the Dutch WWII Oorlogsbronnen archives, allowing users to query historical documents, photographs, and personal accounts through AI assistants.9 npm15MIT
- AlicenseAqualityDmaintenanceEnables AI assistants to query UK property data including EPCs, sale history, planning, flood risk, council tax, demographics, and more via the Homedata API.18MIT
- AlicenseAqualityFmaintenanceEnables querying over 3,200 Dutch statutes (AVG, Wetboek van Strafrecht, Burgerlijk Wetboek, etc.) with verbatim, citation-grounded text from official sources, directly from MCP-compatible AI assistants.1848 npm13Apache 2.0
- AlicenseAqualityAmaintenanceEnables AI agents to query the Swiss Federal Register of Buildings and Dwellings (GWR/RegBL) β including building lookups, address geocoding, construction statistics, and housing pipeline analysis β through MCP tools.91MIT