fega-schmitt-mcp
# fega-schmitt-mcp
[](https://github.com/the78mole/fega-schmitt-mcp/actions/workflows/publish.yml)
[](LICENSE)
[](https://github.com/astral-sh/uv)
[](https://github.com/astral-sh/ruff)
> **Status:** Preis-/Verfügbarkeitsabfrage (SOAP) sowie Webshop-Zugriff (Suche, Artikeldetails,
> Warenkörbe, Bestellungen, ...) implementiert, noch nicht auf PyPI veröffentlicht.
Ein **dünner** [MCP](https://modelcontextprotocol.io)-Server, der KI-Assistenten (z. B. Claude)
Zugriff auf Daten von **FEGA & Schmitt Elektrogroßhandel** gibt — Preis- und
Verfügbarkeitsabfragen für Artikel sowie Zugriff auf die Webshop-Weboberfläche (Suche,
Artikeldetails, Warenkörbe, Bestellungen, Aktionsangebote).
Die gesamte Protokoll-/API-Logik (SOAP, Auth, Fehlercodes, XML, Webshop-Scraping) lebt **nicht**
in diesem Repo, sondern in der eigenständigen Python-Library
[`fega-schmitt-client`](https://github.com/the78mole/fega-schmitt-client)
(Repo unter `GIT/Python/`, auf [PyPI](https://pypi.org/project/fega-schmitt-client/) veröffentlicht).
Dieses Repo bildet nur die Brücke zwischen MCP-Protokoll und dieser Library.
```mermaid
graph LR
Host["MCP-Host<br/>(Claude Desktop / Claude Code / ...)"] -->|stdio, JSON-RPC| MCP["fega-schmitt-mcp<br/>(dieses Repo)"]
MCP -->|Python-Aufruf| LIB["fega-schmitt-client<br/>(eigenes Repo + PyPI-Paket)"]
LIB -->|SOAP/HTTPS| API["FEGA & Schmitt<br/>Preis-/Verfügbarkeitsservice"]
LIB -->|HTTPS, Scraping| SHOP["FEGA & Schmitt<br/>Webshop-Frontend"]
style MCP fill:#2b6cb0,color:#fff
```
> **Suchst du die Python-Library oder das CLI-Tool?**
> Siehe [`fega-schmitt-client`](https://github.com/the78mole/fega-schmitt-client) — die
> eigenständige Library, die dieser MCP-Server verpackt.
## Warum zwei Pakete?
- **`fega-schmitt-client`**: reine Python-Library, kein MCP-/KI-spezifischer Code. Eigenständig
nutzbar (Skripte, andere Services), unabhängig testbar, unabhängig versionierbar.
- **`fega-schmitt-mcp`** (dieses Repo): übersetzt die Library-Funktionen in MCP-Tools
(stdio-Transport, Tool-Schemas, Fehler-Serialisierung für MCP-Clients). Enthält selbst keine
SOAP-/XML-Logik.
## Tools
### SOAP-Preisservice
| Tool | Beschreibung |
|------|-------------|
| `get_price_availability` | Preis und Verfügbarkeit für bis zu 999 Artikel je Anfrage. Eingabe: Liste von Artikelnummern mit Menge und optionaler Mengeneinheit. Ausgabe je Artikel: Verfügbarkeitsstatus, Nettopreis, Listenpreis, Zu-/Abschläge, Lagerzuordnung. Fehlerfälle (unbekannte Artikelnummer, ungültige Mengeneinheit, Mengenüberlauf) werden je Position gemeldet, ohne die gesamte Anfrage abzubrechen. |
### Webshop (best-effort, nicht offiziell dokumentiert)
Diese Tools sprechen die Kunden-Weboberfläche (`shop.fega.de`) statt einer dokumentierten
Schnittstelle an — siehe [`fega-schmitt-client`/docs/extensions.md](https://github.com/the78mole/fega-schmitt-client/blob/main/docs/extensions.md)
für Details/Vorbehalte je Methode. Nutzen dieselben Zugangsdaten wie `get_price_availability`.
| Tool | Beschreibung |
|------|-------------|
| `web_search_articles` | Artikelsuche über Artikelnummer, EAN, Herstellerteilenummer oder Freitext (ein gemeinsames Suchfeld). |
| `web_get_article` | Alle bekannten Artikeldetails in einem Aufruf: EAN, Herstellernummer(n), Kategorie, eigene Artikelnummer, Attribute, Bilder, Schnittkosten sowie Artikelnummern von Zubehör/Varianten/Alternativen/Cross-Sell. |
| `web_set_article_number` | Eigene (kundenspezifische) Artikelnummer für einen Artikel setzen. |
| `web_get_cable_lengths` | Verfügbare Kabellängen (Trommeln/Reststücke) eines Kabelartikels je Lagerstandort. |
| `web_list_articles_by_category` | Artikel einer UWG-Warengruppe auflisten. |
| `web_get_favorites` | Gespeicherte Favoritenliste abrufen. |
| `web_get_deal_campaigns` | Aktive Aktionsangebote-Kampagnen auflisten. |
| `web_get_deal_articles` | Artikel einer Aktionsangebote-Kampagne abrufen. |
| `web_get_daily_deals` | Tagesangebote abrufen. |
| `web_get_second_choice_articles` | "2. Wahl"/B-Ware-Artikel abrufen. |
| `web_get_cart` | Inhalt eines Warenkorbs (Standard: aktuell aktiver) abrufen. |
| `web_get_cart_list` | Alle Warenkörbe des Kunden auflisten. |
| `web_get_order_list` | Bestellübersicht abrufen. |
| `web_get_order` | Positionen einer einzelnen Bestellung abrufen. |
## Installation
### Voraussetzungen
- Python ≥ 3.10
- [uv](https://docs.astral.sh/uv/)
### Dependencies installieren
```bash
uv sync
```
### Server starten (Entwicklung)
```bash
export FEGA_CUSTOMER_NUMBER=9920
export FEGA_SHOP_PASSWORD=...
uv run fega-schmitt-mcp
# oder
uv run python -m fega_schmitt_mcp.server
```
### Mit dem MCP Inspector testen
```bash
uv run mcp dev src/fega_schmitt_mcp/server.py
```
## Konfiguration in VS Code / Claude Desktop
Server in der MCP-Konfiguration eintragen (`.vscode/mcp.json` bzw. `claude_desktop_config.json`):
**Installation von PyPI:**
```json
{
"servers": {
"fega-schmitt": {
"command": "bash",
"args": ["-l", "-c", "uvx fega-schmitt-mcp"],
"env": {
"FEGA_CUSTOMER_NUMBER": "9920",
"FEGA_SHOP_PASSWORD": "..."
}
}
}
}
```
**Installation von GitHub:**
```json
{
"servers": {
"fega-schmitt": {
"command": "bash",
"args": [
"-l",
"-c",
"uvx --from git+https://github.com/the78mole/fega-schmitt-mcp.git fega-schmitt-mcp"
],
"env": {
"FEGA_CUSTOMER_NUMBER": "9920",
"FEGA_SHOP_PASSWORD": "..."
}
}
}
}
```
**Lokale Entwicklung (Workspace-Checkout):**
```json
{
"servers": {
"fega-schmitt": {
"command": "bash",
"args": ["-l", "-c", "uv --directory ${workspaceFolder} run fega-schmitt-mcp"],
"env": {
"FEGA_CUSTOMER_NUMBER": "9920",
"FEGA_SHOP_PASSWORD": "..."
}
}
}
}
```
> **Hinweis:** `bash -l` lädt das Login-Shell-Profil, damit `uvx`/`uv` in `~/.local/bin` gefunden
> werden, ohne dass eine zusätzliche `env`/`PATH`-Konfiguration nötig ist.
## Umgebungsvariablen
| Variable | Default | Beschreibung |
|----------|---------|--------------|
| `FEGA_CUSTOMER_NUMBER` | – (erforderlich) | FEGA & Schmitt-Kundennummer (`PARTNER_PURCHASER`) |
| `FEGA_SHOP_PASSWORD` | – (erforderlich) | Shop-Kennwort (`LEGITIMATION_ID`) |
| `FEGA_ENDPOINT` | `https://soap.fega.de/priceavail.php` | Abweichende SOAP-Service-URL, z. B. für Tests gegen einen Mock-Server |
| `FEGA_SHOP_BASE_URL` | `https://shop.fega.de` | Abweichende Webshop-Basis-URL für die `web_*`-Tools |
| `FEGA_TIMEOUT` | `30` | HTTP-Timeout in Sekunden (gilt für beide Backends) |
Fehlen `FEGA_CUSTOMER_NUMBER`/`FEGA_SHOP_PASSWORD`, liefert das Tool `{"error": ...}` statt eine
Exception zu werfen — Secrets werden nie geloggt oder im Code hinterlegt (siehe
[docs/architecture.md](docs/architecture.md), Abschnitt 3).
## Beispiel
```text
get_price_availability(items=[
{"material_number": "0815", "quantity": "200", "unit": "MTR"},
{"material_number": "4711"},
])
```
liefert:
```json
{
"results": [
{
"line_item_number": 1,
"material_number": "0815",
"status": "ok",
"return_code": "I720",
"return_code_text": "OK",
"availability_status": "V",
"warehouse_number": "10",
"warehouse_name": "Zentrallager",
"price_amount": "12.50",
"net_amount": "13.20",
"list_amount": "15.00",
"surcharges": [{"code": "CU", "text": "Kupferzuschlag", "amount": "0.70"}]
},
{
"line_item_number": 2,
"material_number": "4711",
"status": "error",
"return_code": "E999",
"return_code_text": "Bitte pruefen Sie Ihre Anmeldedaten",
"availability_status": null,
"warehouse_number": null,
"warehouse_name": null,
"price_amount": null,
"net_amount": null,
"list_amount": null,
"surcharges": []
}
]
}
```
Webshop-Beispiel:
```text
web_get_article(material_number="0815")
```
liefert (gekürzt):
```json
{
"material_number": "0815",
"ean": "4012345678901",
"own_article_number": "MEIN-0815",
"category": {"id": "UWG_14_87", "name": "Leitungsschutzschalter"},
"attributes": {"Nennspannung": "230 V"},
"images": [{"url": "https://shop.fega.de/img/0815-1.jpg", "is_primary": true}],
"accessories": ["1000"],
"variants": ["1001", "1002"],
"alternatives": [],
"cross_sell": ["1004"]
}
```
## Über FEGA & Schmitt
FEGA & Schmitt ist ein deutscher Elektrogroßhändler. Details zu den verfügbaren Schnittstellen
(SOAP-Preisservice, IDS-Branchenstandard, UGL4-Branchenstandard, Webshop-Frontend) siehe die
Architekturbeschreibung der Library:
[`fega-schmitt-client`/docs/architecture.md](https://github.com/the78mole/fega-schmitt-client/blob/main/docs/architecture.md).
## Lokale Entwicklung
```bash
# Projektumgebung einrichten
uv sync
# Linting & Formatting
uv run ruff format .
uv run ruff check --fix .
# Tests
uv run pytest
```
## Offene Punkte
- Test-/Produktivzugangsdaten für den SOAP-Service (siehe `fega-schmitt-client`-Repo)
- Zielumgebung des MCP-Servers (lokal per stdio, oder als gehosteter Dienst?)
- Endgültiger PyPI-/Paketname (`fega-schmitt-mcp` ist ein Arbeitstitel)
- PyPI Trusted Publishing muss einmalig manuell auf pypi.org eingerichtet werden (Workflow-Datei
`publish.yml`, Environment `pypi`), bevor der Release-Workflow tatsächlich veröffentlichen kann
## Related Projects
| Project | Description |
|---------|-------------|
| [fega-schmitt-client](https://github.com/the78mole/fega-schmitt-client) | Python-Library, die dieser MCP-Server verpackt. Enthält die gesamte SOAP-/Protokoll-Logik sowie ein eigenständiges CLI. |
## Lizenz
MIT, siehe [LICENSE](LICENSE).
TDQS
Scored across 15 tools
Most tools target clearly distinct resources: pricing, article details, categories, deals, carts, and orders. The only mild ambiguities are cart list vs. cart contents and the several deal-related tools, but the descriptions sufficiently clarify boundaries.
The dominant pattern is web_get_* and web_list_*, and all names use snake_case. The main inconsistency is get_price_availability lacking the web_ prefix, plus variation between list and get for list-like operations (web_get_cart_list vs. web_list_articles_by_category).
With 15 tools, the server is at the upper edge of a well-scoped count, and each tool covers a distinct product, pricing, promotion, cart, or order capability. No tool feels redundant or gratuitous.
The read-side coverage is strong: search, details, pricing, categories, deals, carts, favorites, and orders are all represented. However, there are no tools to create, update, or delete cart items, place orders, or otherwise advance a purchasing workflow, which is a notable gap for a commerce-oriented server.