seepuls/docs/CITY_SOURCE_KONSTANZ.md
Till JS ff9d5a8fd6
Some checks are pending
CI / validate (push) Waiting to run
Kuratiere drei Konstanz-Venues + fixe Grey-eventSource + Konstanz-city-Runbook
Lücken-Analyse gegen party-news.de zeigte: Venues, die wir crawlen
könnten, fehlten oder hatten tote/keine Quellen.

- grey-konstanz: eventSource-URL von greyclub.de/events (404) auf die
  Startseite grey-konstanz.de korrigiert (rendert die Events inline).
- logans-city-konstanz, vauna-vlora-konstanz, pfiff-konstanz: neu
  kuratiert (Adresse/Geo gegen Primärquellen + Nominatim verifiziert,
  Beschreibungen als Kurz-Zitat ≤200 Zeichen, Compliance-Veto ).
  pfiff websiteUrl=null, da pfiff-konstanz.de eine Casino-Spam-
  Domain-Übernahme ist. Keine der drei hat eine crawlbare Programm-
  Seite → Anker für city-scope/Submission.
- docs/CITY_SOURCE_KONSTANZ.md: Runbook für die scope='city'-Quelle
  veranstaltungen.konstanz.de/region/ (offizieller MTK-Kalender,
  robots-geprüft) — Anlage via Admin-API, da city-Quellen keinen
  YAML-Pfad haben.

Quellen als Lead aus party-news.de, jede gegen die Primärquelle
verifiziert; keine Event-Inhalte/DB-Teile übernommen (AGGREGATOR_POLICY).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-05 22:02:15 +02:00

4.1 KiB

City-Scope-Quelle Konstanz — Runbook

Wie der stadtweite Sammelkalender für Konstanz als scope='city'- Event-Quelle angelegt, geprüft und aktiviert wird.

Warum kein YAML? Anders als Venue-Quellen (scope='venue', kuratiert als YAML in apps/api/src/data/curated/venues/<slug>.yml mit eventSource:-Block) werden city-Quellen bewusst nur über die Admin-API angelegt — siehe CURATOR.md. Ein stadtweiter Kalender ist keine Venue, deshalb gibt es keinen Import-Pfad.

Verifizierte Quelle

Feld Wert
url https://veranstaltungen.konstanz.de/region/
city Konstanz
regionSlug bodensee
countryCode DE
parserHint firecrawl-llm (Default — Seite ist server-rendertes HTML ohne JSON-LD)
crawlIntervalHours 24 (Default)

Quelle ist der offizielle MTK / Stadt-Konstanz-Tourismuskalender, kein kommerzieller Mitbewerber-Aggregator. Geprüft am 2026-06-05:

  • robots.txt (veranstaltungen.konstanz.de): User-agent: * blockt nur Infra-Pfade (/includes/, /export/, /apps/, /login/ …); /region/ ist erlaubt, kein Crawl-Delay gesetzt → unser SEEPULS_CRAWL_INTERVAL_MS (≥ 1,1 s) reicht (AGGREGATOR_POLICY §1).
  • Inhalt: rendert datierte Events server-seitig (HTML, kein JS nötig); am Prüftag 17 Datums-Vorkommen ab heute auf der ersten Seite.
  • Abdeckung: ganze Region → löst bestehende Venues auf (Logan's/Pfiff/Vauna …) und legt für unbekannte Orte automatisch pending-review-Venues an (Reviewer-Gate).

Verworfen: www.konstanz.de/.../veranstaltungskalender (Stadt-Verwaltung) hat Crawl-delay: 30 → zu zäh für den gleichen Inhalt.

Anlage-Sequenz

Die Admin-Routen unter /api/v1/admin/* sind per jwtAuth() geschützt — braucht ein gültiges mana-auth-Admin-JWT (kein Service-Key).

API=https://api.seepuls.com
TOKEN=<dein mana-auth Admin-JWT>

# 1 — anlegen (startet inaktiv: active=false)
curl -s -X POST "$API/api/v1/admin/event-sources" \
  -H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
  -d '{"url":"https://veranstaltungen.konstanz.de/region/","city":"Konstanz","regionSlug":"bodensee","countryCode":"DE"}'
# → {"id":"es_…","scope":"city","active":false,"next_step":"probe-then-activate"}

# 2 — Probe: Preview OHNE DB-Write (newItems=0), zeigt extrahierte Events
#     inkl. gelesenem venue_name/venue_address (Auflösung erst beim echten Run)
curl -s -X POST "$API/api/v1/admin/event-sources/<id>/probe" \
  -H "Authorization: Bearer $TOKEN" \
  | jq '.preview[] | {title, starts_at, venue_name, venue_address}'

# 3 — wenn die Probe stimmt: scharf schalten
curl -s -X PATCH "$API/api/v1/admin/event-sources/<id>" \
  -H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
  -d '{"active":true}'

# (optional) sofortiger Crawl statt auf den 24h-Cron warten:
curl -s -X POST "$API/api/v1/admin/event-sources/<id>/run" \
  -H "Authorization: Bearer $TOKEN" | jq

Reihenfolge & Folgewirkung — vor dem Aktivieren beachten

  1. Erst Venue-Import, dann city-Quelle. Die drei kuratierten Venues (logans-city-konstanz, vauna-vlora-konstanz, pfiff-konstanz) müssen importiert sein (pnpm --filter ./apps/api db:import-venues, läuft beim Deploy), bevor der erste city-Crawl läuft. Sonst legt die Venue-Auflösung eigene pending-review-Rows an und die Events hängen am falschen Ort.
  2. Moderations-Rückstau. Ein Regions-Kalender bringt viele neue pending-review-Venues (alles, was noch nicht kuratiert ist). Gewollt, aber jemand muss durchsehen. Die Probe (Schritt 2) zeigt vorher, was reinkäme — Sampling-Reviewer-Stop wie im Curator-Workflow.

Compliance

city-Crawl unterliegt der vollen AGGREGATOR_POLICY: robots.txt-Lookup pro Crawl (geloggt in crawl_jobs.robots_check_passed), ≥ 1,1 s Delay, User-Agent mit Kontakt-Mail, sichtbare Attribution (Quell-Domain + accessedOn) im Frontend, Take-Down-Endpoint. Vor dem Live-Cut: mana-compliance-Pre-Live-Veto (steht in AGGREGATOR_POLICY „Offene Punkte").