swiss-democracy-mcp
An MCP server providing access to Swiss direct democracy data, covering all federal popular votes since 1848 and elections since 1900.
README
swiss-democracy-mcp
Part of the Swiss Public Data MCP Portfolio — connecting AI models to Swiss institutional data sources.
An MCP server providing access to Swiss direct democracy data, covering all federal popular votes since 1848 and elections since 1900.
Demo Query
«Wie hat der Kanton Zürich bei der AHV 21 Initiative 2022 abgestimmt,
und welche Parteien unterstützten die Vorlage?»
→ democracy_search_votes(keyword="AHV 21", year_from=2022)
→ democracy_get_cantonal_results(vote_number="551")
→ democracy_get_party_positions(vote_number="551")
→ More use cases by audience →
Data Sources
| Source | Coverage | Auth |
|---|---|---|
| Swissvotes (Uni Bern) | All federal votes since 1848 · 874 columns · party positions · cantonal results | None ✓ |
| BFS / opendata.swiss | Real-time & archive (since 1981) · municipality level | None ✓ |
| SRGSSR Polis | Votes & elections since 1900 · municipality detail | OAuth2 key |
Tools
Phase 1 — Swissvotes (No Auth Required)
| Tool | Description |
|---|---|
democracy_search_votes |
Search all federal popular votes since 1848 by keyword, date range, legal form, outcome, policy domain |
democracy_get_vote_detail |
Full details for a specific vote: official title, parliamentary positions, national result, signatures |
democracy_get_party_positions |
Party recommendations (FDP, SP, SVP, Die Mitte, GPS, GLP, …) with campaign finance data |
democracy_get_cantonal_results |
Results for all 26 cantons: yes%, turnout, accepted flag |
democracy_list_vote_dates |
List all voting dates with number of proposals per date |
Phase 2 — BFS Real-Time (No Auth Required)
| Tool | Description |
|---|---|
democracy_bfs_list_vote_dates |
List all BFS voting dates (archive + current) |
democracy_bfs_get_vote_results |
Real-time or archived results at national, cantonal, or municipality level |
Phase 3 — SRGSSR Polis (API Key Required)
| Tool | Description |
|---|---|
democracy_polis_list_votations |
Historical votations since 1900 with municipality-level data |
democracy_polis_get_votation_detail |
Full Polis detail, optionally with all municipality results |
democracy_polis_list_elections |
National Council, Council of States, and cantonal elections since 1900 |
Installation
Claude Desktop (stdio)
Add to claude_desktop_config.json:
{
"mcpServers": {
"swiss-democracy": {
"command": "uvx",
"args": ["swiss-democracy-mcp"],
"env": {
"SRGSSR_CONSUMER_KEY": "your_key_here",
"SRGSSR_CONSUMER_SECRET": "your_secret_here"
}
}
}
}
The
SRGSSR_*variables are optional. Without them, all Swissvotes and BFS tools remain fully functional. Only the Polis tools require credentials.
Cloud / Render.com (Streamable HTTP)
pip install swiss-democracy-mcp
MCP_TRANSPORT=streamable_http MCP_PORT=8000 python -m swiss_democracy_mcp.server
Architecture
┌─────────────────────────────────────────────┐
│ Claude / LLM Host │
└──────────────┬──────────────────────────────┘
│ MCP (stdio / Streamable HTTP)
┌──────────────▼──────────────────────────────┐
│ swiss-democracy-mcp │
│ │
│ ┌─────────────────────────────────────┐ │
│ │ Swissvotes CSV Cache (24h TTL) │ │
│ │ All 874 columns, since 1848 │ │
│ └──────────────┬──────────────────────┘ │
│ │ │
│ ┌──────────────▼──────────────────────┐ │
│ │ BFS / opendata.swiss (no auth) │ │
│ │ Real-time & archive since 1981 │ │
│ └──────────────┬──────────────────────┘ │
│ │ │
│ ┌──────────────▼──────────────────────┐ │
│ │ SRGSSR Polis (OAuth2, optional) │ │
│ │ Votes & elections since 1900 │ │
│ └─────────────────────────────────────┘ │
└─────────────────────────────────────────────┘
Transport: stdio for Claude Desktop · Streamable HTTP for cloud/Render.com
Auth pattern: No-Auth-First — Swissvotes & BFS work without any credentials
Cache: Swissvotes CSV is loaded once at startup and cached for 24 hours
Portfolio Synergy
Combine with other servers in the Swiss Public Data MCP portfolio:
- zurich-opendata-mcp — add Zurich city-level statistics to vote analysis
- swiss-statistics-mcp — enrich with BFS demographic data by canton
- srgssr-mcp — link SRF news archive content to specific vote dates
Example multi-server query:
«Vergleiche die Abstimmungsresultate zur AHV-Reform mit der Altersstruktur der Kantone»
→ swiss-democracy-mcp + swiss-statistics-mcp
Safety & Limits
- Read-only: All tools perform HTTP GET requests only — no data is written, modified, or deleted upstream.
- No personal data: Swissvotes, BFS and SRGSSR Polis expose aggregate democratic data (vote results, party positions, cantonal/municipality tallies). No personally identifiable information (PII) is processed or stored by this server.
- Rate limits: Swissvotes is a single CSV downloaded once per 24h and cached in memory. BFS / opendata.swiss and SRGSSR Polis are public APIs without documented rate limits — keep
limitand date ranges conservative. The server enforces a 30s timeout per request. - Data freshness: Real-time BFS results reflect the upstream feed at query time (no local caching). Swissvotes is refreshed every 24h from the Uni Bern mirror.
- Terms of service: Data is subject to the ToS of each source — swissvotes.ch (CC BY 4.0, Uni Bern), opendata.swiss (mostly CC-BY / Open by Default), SRGSSR Polis (free tier, non-commercial use only). Always cite the upstream source in downstream products.
- No guarantees: This server is a community project, not affiliated with the University of Bern, the Federal Statistical Office, or SRG SSR. Availability depends on upstream APIs.
Known Limitations
- Swissvotes coverage: Cantonal-level results are available since 1848; municipality-level results only via SRGSSR Polis (since ~1990s depending on the vote).
- BFS archive: Real-time service covers federal votes since 1981 only.
- Polis tools: Require free registration at developer.srgssr.ch. Non-commercial use only.
- CSV cache: The Swissvotes dataset is ~several MB and is cached in memory for 24 hours. Memory footprint is accordingly higher than API-only servers.
Testing
# Unit tests (no network required)
PYTHONPATH=src pytest tests/ -m "not live" -v
# Live tests (require network access)
PYTHONPATH=src pytest tests/ -m "live" -v
Contributing
See CONTRIBUTING.md.
License
MIT — see LICENSE.
Data licenses:
- Swissvotes: Creative Commons BY 4.0
- BFS / opendata.swiss: Open use
- SRGSSR Polis: Non-commercial use only — see developer.srgssr.ch
Recommended Servers
playwright-mcp
A Model Context Protocol server that enables LLMs to interact with web pages through structured accessibility snapshots without requiring vision models or screenshots.
Magic Component Platform (MCP)
An AI-powered tool that generates modern UI components from natural language descriptions, integrating with popular IDEs to streamline UI development workflow.
Audiense Insights MCP Server
Enables interaction with Audiense Insights accounts via the Model Context Protocol, facilitating the extraction and analysis of marketing insights and audience data including demographics, behavior, and influencer engagement.
VeyraX MCP
Single MCP tool to connect all your favorite tools: Gmail, Calendar and 40 more.
graphlit-mcp-server
The Model Context Protocol (MCP) Server enables integration between MCP clients and the Graphlit service. Ingest anything from Slack to Gmail to podcast feeds, in addition to web crawling, into a Graphlit project - and then retrieve relevant contents from the MCP client.
Kagi MCP Server
An MCP server that integrates Kagi search capabilities with Claude AI, enabling Claude to perform real-time web searches when answering questions that require up-to-date information.
E2B
Using MCP to run code via e2b.
Neon Database
MCP server for interacting with Neon Management API and databases
Qdrant Server
This repository is an example of how to create a MCP server for Qdrant, a vector search engine.
Exa Search
A Model Context Protocol (MCP) server lets AI assistants like Claude use the Exa AI Search API for web searches. This setup allows AI models to get real-time web information in a safe and controlled way.