Webchatix-Dokumentation

Telegram-first Live-Chat: Besucher schreiben ins Website-Widget, Ihr Team antwortet aus Telegram und dem Web-Dashboard. Links die Abschnitte, rechts die Details.

In 5 Minuten

  1. Bot öffnen → /start — es entstehen ein Konto im Tarif Free und die erste Website.
  2. HTML-Snippet kopieren und auf der Website vor </body> einfügen.
  3. /panel — Einmal-Link ins Web-Dashboard (oder der Menüpunkt „Web-Dashboard“).
  4. Eine Person einladen: /invite oder Menü → „Team“ → ➕.
  5. Telegram-Gruppe verbinden: Bot zur Gruppe hinzufügen (oder dort /addgroup schreiben) und sie unter «Routen» einer Website zuweisen.
  6. Fallback für eine ganze Website in einer Gruppe: /bindsite site_key in der Gruppe.

Tarife und Zahlung

Die Registrierung ist offen: /start im Bot legt ein Konto im Tarif Free an. Bezahlte Tarife kauft man per Karte im Dashboard, Bereich Rechnungen — die Zahlung läuft über Stripe.

TarifWebsitesKunden / MonatPersonenPro Monat
free1301$0
basic2010005$10 ($8 bei Jahreszahlung)
unlimited∞∞∞$20 ($16 bei Jahreszahlung)

Die Preise gelten pro Monat. Die Jahreszahlung ist 20% günstiger und wird einmalig abgebucht ($96 und $192 im Jahr); im Dashboard ist das Jahr vorausgewählt.

Premium (ab Basic): Vorlagen, Active Invite, Visibility Rules, Notizen, Bewertungen.

Ein Kunde ist ein eindeutiger Besucher, der im laufenden Kalendermonat einen Chat begonnen hat; der Zähler startet am 1. neu.

So funktioniert die Zahlung

  • Dashboard → Rechnungen: aktueller Tarif, Verbrauch, Tarifwechsel, Liste der Zahlungen mit PDF-Links.
  • Kartendaten erreichen unsere Server nie — Zahlungsseite und Kundenportal gehören Stripe.
  • Einen Tarifwechsel mitten in der Periode rechnet Stripe anteilig ab; nach einer Kündigung bleibt der bezahlte Tarif bis zum Periodenende, danach fällt das Konto auf Free zurück.
  • An die E-Mail-Adresse aus demselben Bereich gehen Zahlungsbeleg, Hinweis auf eine fehlgeschlagene Abbuchung und die Erinnerung an die Verlängerung.

Bot-Menü

Das Hauptmenü nach /start / /menu. Die Schaltflächen stehen meist zu zweit in einer Reihe.

EintragFunktion
🌐 WebsitesWebsites des Kontos: Einstellungen, Online/Offline, Snippet, Löschen.
👥 TeamMitglieder des Kontos.
➕ EinladenCode und Deep-Link für eine neue Person.
💬 GruppenTelegram-Gruppen, die Anfragen erhalten: verbinden, Website zuweisen, trennen.
🔗 Web-DashboardMagic-Login-Link (einmalig, ~10 Min.).
🗺 RoutenWer Dialoge von welcher Website/Seite bekommt.
🔑 API-SchlüsselAPI-Schlüssel der Kontostatistik, Tagesübersicht aller Websites (heute), Schlüssel ersetzen (Owner/Admin).
⚙️ PanelSchnellzugriff: ops / sites / routes.
📝 VorlagenSchnellantworten (ab Basic).
💳 Tarife und ZahlungPreise, Kartenzahlung, Rechnungen (owner).
👑 EigentumEigentum an ein anderes Mitglied übergeben.
🗑 Konto löschenKaskadierendes Löschen nach Bestätigung per Name.

Website-Karte

  • Online / Offline — Widget pausieren (Chat offline).
  • Einstellungen — Branding-Felder, Invite, DSGVO usw. (2 Schaltflächen je Reihe).
  • Zuständigkeit — Routing auf eine Person oder Gruppe setzen.
  • Löschen — mit Bestätigung durch den Website-Namen.

Bot-Befehle

BefehlWerBedeutung
/start [CODE]alleOnboarding / Einladung einlösen.
/menumemberHauptmenü des Kontos.
/helpalleBefehlsübersicht für deine Rolle.
/panelmemberMagic-Link ins Web-Dashboard.
/newsite [Name | Origin]admin+Website anlegen (+ CORS-Origins).
/addgroupadmin+ in GruppeGruppe als Gruppen-Operator verbinden (ohne chat_id).
/bindsite KEYadmin+ in GruppeGruppe als Fallback-Chat verbinden.
/inviteadmin+Einladung ausstellen.
/op_me CODEalleEinladung annehmen.
/tplmemberListe / add / del / Senden per Reply + /tpl id.
/notememberNotiz zum Dialog (ab Basic).
/releasememberDialog freigeben (+ Bewertung anfragen).
/langalleSprache der Bot-Oberfläche: en / pl / de / ru / uk / be / ar.
/setrole id roleownerowner|admin|operator.
/crm on|offownerCRM-Brücke des Kontos ein-/ausschalten.
/deleteaccountownerKonto löschen.
/idim Chatchat_id anzeigen.

Web-Dashboard

Tenant-Login: der Link aus /panel oder ein Token auf /account/login/.

BereichWozu
ÜbersichtZähler und letzte Dialoge; Firmenname; CRM-Brücke für owner — Schalter und Webhook-Link (leer — der gemeinsame aus config).
WebsitesAnlegen, Snippet, vollständige Widget-Einstellungen.
TeamMitglieder, Einladungen, Rollen, Gruppen.
RoutenAssignments: Website → Person/Gruppe.
DialogeVerlauf, Release, Notizen, Bewertung.
StatistikBesuche, Bots, Formulare und Chat für alle Websites oder eine; Seiten; Code nur für Statistik; API-Schlüssel des Kontos.
VorlagenCRUD für Vorlagen + Bewertungsübersicht (ab Basic).

Website-Einstellungen

Verfügbar im Bot („Einstellungen“) und im Web unter Websites → Zahnrad.

FeldBedeutung
Name / Titel / UntertitelKopfzeile des Chats.
Begrüßung / LogoErste Nachricht und Marke.
Online von–bis, TZ, PauseStatus Online/Offline.
Eskalation (Min.)Alarm, wenn keine Antwort kommt.
Farbe / Position / AbständeDer Widget-Button.
Sprache / Tonen|pl|de|ru|uk|be|ar und eine mp3-URL.
Allowed originsCORS: Domains per Komma oder *.
Invite *Einladung als Sprechblase (ab Basic).
Visibility JSONWo Button/Invite erscheinen (ab Basic).
DSGVOEinwilligungs-Checkbox vor dem ersten Senden.
KI-AntwortAntwortet dem Besucher, wenn N Minuten niemand geantwortet hat (Standard: 3).

KI-Antwort (Gemini)

Der Besucher schreibt, die Operatoren schweigen — nach der eingestellten Zahl von Minuten antwortet Google Gemini im Chat. Der Besucher sieht die Antwort im Widget, die Operatoren bekommen in Telegram eine Karte „KI hat geantwortet“ mit demselben Text, damit niemand dasselbe wiederholt.

  • Pro Website aktivierbar: Websites → Zahnrad → KI-Antwort. Dort stehen auch die Verzögerung und das Feld „Was die KI über die Firma wissen soll“ — Öffnungszeiten, Versand, was nicht versprochen werden darf.
  • Eine Antwort des Menschen setzt den Zähler zurück; einen vom Operator übernommenen (claim) Dialog rührt die KI nicht an.
  • Die KI-Antwort hebt die Eskalation nicht auf: Der Admin wird weiterhin benachrichtigt, dass kein Mensch geantwortet hat.
  • Das Modell antwortet kurz, erfindet keine Preise oder Termine und gibt auf direkte Nachfrage zu, ein automatischer Assistent zu sein.
  • Der API-Schlüssel wird einmal pro Installation gesetzt: gemini_api_key in config/config.php (Schlüssel aus Google AI Studio, mit kostenlosem Kontingent). Ohne Schlüssel bewirkt die Checkbox nichts.

Visibility-Beispiel

{"include":["/pricing","/contacts"],"exclude":["/admin"],"desktop":true,"mobile":true}

Widget auf der Website

<script async src="https://webchatix.online/widget/webchatix.js"
  data-site-key="SITE_KEY"></script>

Steuerung von der Seite aus:

webchatix("show");   // Button anzeigen
webchatix("hide");   // ausblenden
webchatix("open");   // Chat öffnen
webchatix("close");  // Panel schließen
webchatix("form", "report"); // Formularabsendung zählen (Statistik)

Die Widget-Sprache kommt aus data-lang, dann aus dem <html lang> der Seite, dann aus dem Browser; unterstützt sind en / pl / de / ru / uk / be / ar, Rückfallsprache ist Englisch. Nach Änderungen an den Einstellungen die Kundenseite neu laden (die Widget-Version steht im Query ?v=).

Wenn die Website eine Content-Security-Policy setzt, erlauben Sie die Widget-Domain in drei Direktiven: script-src, style-src und connect-src. Das Widget lädt sein Aussehen aus der separaten Datei webchatix.css, ein 'unsafe-inline' in style-src ist dafür also nicht mehr nötig.

Besuchsstatistik und API

Das Widget zählt die Besuche der Website, auf der es installiert ist. Die Statistik wird ohne Zeitlimit als Tageszähler gespeichert (Tage in UTC); ein Bericht kann jeden Zeitraum abdecken. Abrufbar sind die Daten über eine API mit dem geheimen Kontoschlüssel — ein Schlüssel öffnet alle Websites des Kontos.

FeldWas gezählt wird
unique_visitorsEindeutige Besucher — über das Widget-Cookie (ohne Cookie — über IP + Browser pro Tag). Über einen Zeitraum ohne Doppelzählung: eine Person in einer Woche zählt einmal.
visitsEinstiege — die erste Seite nach 30 Minuten Inaktivität sowie die erste Seite eines Besuchers am Tag.
page_viewsSeitenaufrufe durch Menschen, einschließlich SPA-Navigation (history.pushState).
bot_hitsSeitenabrufe durch Bots: Suchmaschinen (Googlebot, Bingbot, YandexBot…), KI-Crawler (GPTBot, ClaudeBot, PerplexityBot…), soziale Netzwerke, SEO-Tools, Headless-Browser. Sie zählen weder zu Aufrufen noch zu eindeutigen Besuchern.
form_submitsFormularabsendungen auf den Seiten der Website (das Ereignis submit, auch Formulare, die die Website per fetch sendet). Feldwerte werden nicht übertragen — nur der Formularname: #id, name oder der action-Pfad. Absendungen durch Bots zählen nicht.
chat_messagesNachrichten von Besuchern im Webchatix-Chat (Text und Fotos).
chat_visitorsWie viele Besucher im Chat geschrieben haben — pro Unterhaltung, über den Zeitraum ohne Doppelzählung.
ads_googleKlicks aus Google Ads: Die URL der Einstiegsseite enthält gclid, gbraid, wbraid oder gad_source, oder utm_source=google mit bezahltem utm_medium (cpc, ppc, paid…). Einmal pro Einstieg gezählt: Neuladen verdoppelt den Klick nicht.
ads_yandexKlicks aus Yandex Direct: Die URL enthält yclid oder utm_source=yandex mit bezahltem utm_medium. Ebenfalls einmal pro Einstieg.

Das normale Chat-Snippet erfasst die Statistik bereits — Sie müssen nichts hinzufügen.

Installation nur für die Statistik (ohne Oberfläche)

Das Attribut data-mode="stats" installiert das Widget ohne Button, Chatfenster und Styles: Das Skript sendet pro Seite nur einen leichten Hit. Das Pixel in <noscript> ist optional — es erfasst Bots, die kein JavaScript ausführen, aber Bilder laden.

<script async src="https://webchatix.online/widget/webchatix.js"
  data-site-key="SITE_KEY" data-mode="stats"></script>
<noscript><img src="https://webchatix.online/wx-api.php?action=track&site_key=SITE_KEY"
  width="1" height="1" alt="" style="position:absolute"></noscript>

SITE_KEY ist der öffentliche Website-Schlüssel — derselbe wie im Chat-Snippet (Bot: „📋 Installationscode“, Dashboard: „Websites“). Das ist nicht der API-Schlüssel wxs_…: Der ist geheim und gehört nie in den Seitencode.

Ist für die Website Allowed origins gesetzt, werden Hits von Seiten anderer Domains nicht gezählt.

Formulare ohne <form>-Tag

Ein normales <form> erfasst das Widget selbst — über das Ereignis submit, auch wenn die Website es per fetch sendet. Oft besteht ein Formular aber nur aus Feldern und einem <button type="button">, und das JavaScript der Website sendet die Daten; dann gibt es kein submit-Ereignis und die Absendung wird nicht gezählt. Für solche Formulare gibt es zwei Wege.

1. Das Attribut data-wx-form am Absende-Button: Ein Klick zählt als Absendung des Formulars mit diesem Namen. Ein deaktivierter Button (disabled) zählt nicht, ein Doppelklick ergibt eine Absendung.

<button type="button" class="get_report" data-wx-form="report">…</button>

2. Ein Aufruf aus dem Code der Website — wenn die Absendung z. B. erst nach erfolgreicher Prüfung der Felder zählen soll. Funktioniert mit dem normalen Widget und mit data-mode="stats". Kann Ihr Code vor dem Laden des Widgets laufen, setzen Sie den Platzhalter darüber — die Aufrufe landen in einer Warteschlange und gehen nicht verloren.

// nach erfolgreicher Prüfung der Felder
webchatix("form", "report");

// Platzhalter — über den Aufrufen, falls der Code vor dem Widget läuft
window.webchatix = window.webchatix || function () {
  (webchatix.q = webchatix.q || []).push(arguments);
};

Das Attribut data-wx-form an einem <form> oder an dessen Submit-Button setzt den Formularnamen im Bericht statt #id / name / action.

API-Schlüssel

Der Schlüssel wxs_… gilt für das ganze Konto. Wo Sie ihn finden und ersetzen: im Telegram-Bot — Schaltfläche 🔑 API-Schlüssel im Hauptmenü (dort auch eine Übersicht aller Websites), im Dashboard — Websites → Zahnrad. „Schlüssel ersetzen“ erzeugt einen neuen, der alte funktioniert sofort nicht mehr. Owner und Admins des Kontos sehen und ersetzen ihn.

Der Schlüssel ist geheim: Der öffentliche site_key taugt nicht zum Lesen, und der Schlüssel selbst gehört nicht in den Seitencode — fragen Sie die Statistik von Ihrem Server ab. Die Statistik einer Website gibt es auch im Bot: 🌐 Websites → Website → 📊 Statistik.

Der Schlüssel wird auf eine dieser Arten übergeben: Header X-Stats-Key: wxs_…, Header Authorization: Bearer wxs_… oder Parameter ?key=wxs_….

Zwei Schlüssel

SchlüsselWo verwendetÖffentlich?
SITE_KEY — Website-SchlüsselChat-Snippet, data-mode="stats", das Pixel wx-api.php?action=track — alles, was im Seitencode steht und nur Hits schreibtja
wxs_… — API-Schlüssel des Kontosstats-api.php: Statistik lesen (action=stats) und serverseitige Hits (action=hit) — nur von Ihrem Server. Einer für alle Websites des Kontos.nein, geheim

Ein API-Schlüssel im Pixel oder Seitencode ist für jeden Besucher über „Quelltext anzeigen“ sichtbar — er könnte Ihre Statistik lesen und verfälschen. Ist der Schlüssel nach außen gelangt, ersetzen Sie ihn.

GET /stats-api.php?action=stats

Parameter: site_key — nur diese Website des Kontos (ohne — alle Websites); der Zeitraum — days (die letzten N Tage bis heute, 1–366, Standard 7) oder from und to (Daten JJJJ-MM-TT einschließlich, höchstens 366 Tage; ist nur ein Datum angegeben, wird das andere um days Tage gezählt); limit — wie viele Seiten in der Top-Liste jeder Website (1–1000, Standard 50).

curl -H "X-Stats-Key: wxs_…" "https://webchatix.online/stats-api.php?action=stats&days=7&limit=20"
curl -H "X-Stats-Key: wxs_…" "https://webchatix.online/stats-api.php?action=stats&site_key=SITE_KEY"
curl -H "X-Stats-Key: wxs_…" "https://webchatix.online/stats-api.php?action=stats&from=2026-01-01&to=2026-03-31"
{
  "ok": true,
  "account": {"id": 42, "name": "My company"},
  "timezone": "UTC",
  "from": "2026-10-12",
  "to": "2026-10-18",
  "totals": {"unique_visitors": 412, "visits": 530, "page_views": 1874, "bot_hits": 961,
             "form_submits": 23, "chat_messages": 57, "chat_visitors": 14,
             "ads_google": 48, "ads_yandex": 31},
  "days": [
    {"date": "2026-10-18", "unique_visitors": 61, "visits": 74, "page_views": 255, "bot_hits": 140,
     "form_submits": 4, "chat_messages": 9, "chat_visitors": 3,
     "ads_google": 6, "ads_yandex": 4}
  ],
  "sites": [
    {
      "site_key": "SITE_KEY",
      "name": "My site",
      "totals": {"unique_visitors": 300, "visits": 391, "page_views": 1402, "bot_hits": 700,
                 "form_submits": 15, "chat_messages": 40, "chat_visitors": 9,
                 "ads_google": 35, "ads_yandex": 20},
      "days": [ … ],
      "pages": [{"path": "/pricing/", "page_views": 310, "bot_hits": 88, "form_submits": 6}],
      "bots": [{"bot": "Googlebot", "hits": 402}, {"bot": "GPTBot", "hits": 97}],
      "forms": [{"form": "#contact", "submits": 15}]
    }
  ]
}

totals und days sind die Summe über die Websites der Antwort; Besucher werden pro Website gezählt. sites enthält den Bericht jeder Website: days — ein Eintrag pro Datum (Tage ohne Besuche mit Nullen), pages — Top-Seiten (Pfad ohne Query-String) nach Aufrufen plus Bot-Abrufen, bots — Abrufe pro Bot-Name, forms — Absendungen pro Formularname.

POST /stats-api.php?action=hit — serverseitige Hits

Die meisten Such-Bots führen kein JavaScript aus, daher sieht das Widget sie nicht. Um auch sie zu zählen, kann das Backend der Website die empfangenen Anfragen selbst melden: Felder site_key (welche Website des Kontos; Pflicht), url (oder ein Pfad), ua — der User-Agent, optional ip, referrer, visitor_id. Als Paket: {"site_key": "…", "hits": [ … ]}, bis zu 500 Hits pro Anfrage; der site_key eines Hits überschreibt den gemeinsamen. Ob Bot oder Mensch, entscheidet ua.

curl -X POST "https://webchatix.online/stats-api.php?action=hit" \
  -H "X-Stats-Key: wxs_…" -H "Content-Type: application/json" \
  -d '{"site_key": "SITE_KEY", "url": "https://example.com/pricing/", "ua": "Mozilla/5.0 (compatible; bingbot/2.0)", "ip": "203.0.113.7"}'
# → {"ok": true, "views": 0, "bots": 1, "skipped": 0}

Fehler

HTTPerrorUrsache
401key_requiredKein Schlüssel übergeben.
403invalid_keyDer Schlüssel ist falsch oder wurde ersetzt.
403plan_requiredDer API-Schlüssel funktioniert in den Tarifen Basic und Unlimited.
403disabledDas Konto ist gesperrt.
400too_many_hitsMehr als 500 Hits in einer Anfrage.
400unknown_sitesite_key fehlt oder gehört zu einem anderen Konto.
400bad_periodUngültiger Zeitraum: Datum nicht im Format JJJJ-MM-TT, from nach to oder länger als 366 Tage.

Gespeichert werden nur Zähler und anonymisierte Besucher-Hashes — keine IPs, Adressen oder User-Agents im Klartext.

Rollen im Team

  • owner — volle Kontrolle, Tarifanfragen, Kontolöschung, CRM, Eigentumsübergabe.
  • admin — Websites, Einladungen, Routen, Einstellungen.
  • operator — Antworten in Dialogen, Notizen/Vorlagen je nach Tarif.

Ein Telegram-Konto = ein eigenes Konto. In fremden Konten kann man per Einladung als operator mitarbeiten.

Gruppen

Nicht nur Personen, auch eine Telegram-Gruppe kann Operator sein: Die Anfrage kommt als Karte in den Chat, beantworten kann sie jedes Mitglied per Reply. Verbinden: Bot zur Gruppe hinzufügen (Menü → 💬 Gruppen → „Gruppe verbinden“) oder dort /addgroup schreiben — keine chat_id nötig, der Bot ermittelt sie selbst. Gruppen zählen nicht zum Operator-Limit des Tarifs.

Dialoge

  • Die Kundennachricht geht an Telegram (Gruppe/Person gemäß Route).
  • Übernehmen — Claim; eine Systemnachricht landet im Verlauf.
  • Übergeben — nur an ein aktives Mitglied desselben Kontos.
  • Freigeben / Release — Sie können den Besucher um eine Bewertung bitten.
  • Notizen — für das Team sichtbar, nicht für Kundinnen und Kunden (ab Basic).
  • Vorlagen — Reply auf den Dialog + /tpl id oder Vorlagen-Button → Reply.

Sicherheit und DSGVO

  • Konten sind über account_id isoliert.
  • Der Magic-Link gilt einmalig; die Ausgabe ist limitiert.
  • Suspend schaltet Widget, Bot und Tenant-Dashboard ab.
  • CORS: setzen Sie allowed_origins (kein * in Produktion ohne Grund).
  • Die DSGVO-Checkbox erscheint vor der ersten Kundennachricht.
  • Upload-Kontingent je nach Tarif (max_upload_mb).
  • Höchstens 10 neue Websites pro Stunde und Konto.