Token serverseitig prüfen

Das Token im Backend mit /v1/verify prüfen, mit Beispielen für PHP und Node.js.

So funktioniert die Prüfung

  1. 1Dein Backend liest smartcaptcha_token und smartcaptcha_sid aus dem abgeschickten Formular.
  2. 2Es schickt beides zusammen mit Site-Key, Secret und Action per POST an https://app.smartcaptcha.de/v1/verify.
  3. 3Antwortet die API mit ok: true, verarbeitest du das Formular. Sonst lehnst du es ab.
Anfrage
{ "siteKey": "sk_...", "secret": "sec_...", "token": "v4.local....", "sid": "scs_…", "action": "contact" }
Antwort
{ "ok": true, "score": 0.86, "decision": "allow", "reason": "ok", "plan": "growth", "threshold": 0.6 }

Beispiel PHP

php
<?php
$apiBase = 'https://app.smartcaptcha.de';
$siteKey = 'sk_...';
$secret  = 'sec_...';   // nur im Backend, nie im Frontend
$action  = 'contact';   // muss zur data-action des Widgets passen

// Auch ohne Token /v1/verify aufrufen: Bots posten das Formular oft direkt (ohne JavaScript).
// Die API lehnt dann mit "missing_token" ab und zählt den Block in deinem Dashboard.
$token = (string)($_POST['smartcaptcha_token'] ?? '');
$sid   = (string)($_POST['smartcaptcha_sid'] ?? '');

$payload = json_encode([
  'siteKey' => $siteKey,
  'secret'  => $secret,
  'token'   => $token,
  'sid'     => $sid,
  'action'  => $action,
], JSON_THROW_ON_ERROR);

$ch = curl_init($apiBase . '/v1/verify');
curl_setopt_array($ch, [
  CURLOPT_RETURNTRANSFER => true,
  CURLOPT_POST => true,
  CURLOPT_TIMEOUT => 6,
  CURLOPT_HTTPHEADER => ['Content-Type: application/json'],
  CURLOPT_POSTFIELDS => $payload,
]);
$res  = curl_exec($ch);
$code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

$data = json_decode((string)$res, true) ?: [];

if ($code !== 200 || empty($data['ok'])) {
  // Fail-closed: auch bei Netzwerkfehlern (code 0) nicht durchlassen.
  http_response_code(403);
  exit('Anfrage blockiert (' . ($data['reason'] ?? 'unknown') . ').');
}

// Mensch: Formular normal verarbeiten

Beispiel Node.js

javascript
// Node.js 18 oder neuer (fetch ist eingebaut), hier als Express-Route
app.post('/kontakt', express.urlencoded({ extended: false }), async (req, res) => {
  let data = {}
  try {
    const r = await fetch('https://app.smartcaptcha.de/v1/verify', {
      method: 'POST',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({
        siteKey: process.env.SMARTCAPTCHA_SITE_KEY,
        secret: process.env.SMARTCAPTCHA_SECRET, // nur im Backend
        token: req.body.smartcaptcha_token || '',  // auch leer schicken
        sid: req.body.smartcaptcha_sid || '',
        action: 'contact',
      }),
      signal: AbortSignal.timeout(6000),
    })
    data = await r.json()
  } catch {
    // Netzwerkfehler: unten wie eine Ablehnung behandeln (fail-closed)
  }
  if (!data.ok) return res.status(403).send('Anfrage blockiert.')

  // Mensch: Formular normal verarbeiten
  res.send('OK')
})

Zwei Regeln

Auch ohne Token prüfen

Prüfe ein fehlendes Token nicht nur lokal. Schick die Anfrage trotzdem mit leerem token an /v1/verify. Die API lehnt mit missing_token ab und zählt den Block im Dashboard. Sonst bleiben genau die Bots unsichtbar, die das Formular ohne Browser absenden. Gezählt wird nur mit gültigem Secret.

Fail-closed

Wenn die Prüfung fehlschlägt, auch bei einem Netzwerkfehler oder Zeitüberschreitung, nimm das Formular nicht an.

Noch Fragen? Wir helfen gern weiter.

Zum Kontaktformular

Stand: 5. Oktober 2026