Entwickler · API v1.0.0

NotiPilot Device API — Entwicklerdokumentation

API-Version: 1.0.0 · Base path: /api/v1

Mit NotiPilot registrieren Sie die Geräte Ihrer mobilen App, teilen sie in Segmente ein und senden über das NotiPilot-Dashboard Push-Benachrichtigungen an diese Geräte. Ihre mobile App kommuniziert dabei nur mit zwei Endpoints:

Endpoint Wann wird er aufgerufen?
POST /api/v1/register-device Nach Erteilung der Benachrichtigungsberechtigung, bei jedem App-Start und wenn sich der Push-Token ändert
POST /api/v1/identify-device Wenn sich der Nutzer anmeldet (um das Gerät mit Ihrer eigenen Nutzer-ID zu verknüpfen)

Benachrichtigungen werden über das NotiPilot-Dashboard versendet; die mobile App muss selbst nichts senden.

Plattform-Leitfäden

Plattform Für wen?
Expo Expo-Apps (Managed Workflow / Development Build)
React Native Bare- / CLI-React-Native-Projekte
Flutter Flutter-Apps (Android + iOS)
Ionic Ionic- + Capacitor-Apps
Firebase Projekte, die bereits Firebase Cloud Messaging nutzen (alle Technologien)
Shopify Betreiber einer mobilen App für ihren Shopify-Shop (Kundenzuordnung, E-Commerce-Segmente)
Android Native Android — Java
Kotlin Native Android — Kotlin (View / Jetpack Compose)
iOS Native iOS — Apple-Developer- / APNs-Einrichtung und Objective-C
Swift Native iOS — Swift (UIKit / SwiftUI)

Versionsunterstützung und Versionierungsrichtlinie


1. Wie funktioniert es?

Mobile App ──(Expo Push Token + Geräteinformationen)──▶ NotiPilot API
                                                              │
NotiPilot-Dashboard ──(Titel, Nachricht, Segment)──▶ Expo Push Service ──▶ FCM (Android) / APNs (iOS) ──▶ Gerät

NotiPilot 1.0.0 nutzt für die Zustellung den Expo Push Service. Daraus ergibt sich:

  • Jedes Gerät benötigt einen Expo Push Token (ExponentPushToken[...]). In Expo- und React-Native-Apps erhalten Sie diesen Token direkt über expo-notifications. In nativen Android-/iOS-Apps wird der FCM-/APNs-Token des Geräts in einen Expo-Token konvertiert (die jeweiligen Leitfäden beschreiben das Schritt für Schritt).
  • Ihre App benötigt ein Expo-(EAS-)Projekt, in das die FCM-V1- / APNs-Zugangsdaten hochgeladen wurden (eas credentials).
  • Beim Anlegen Ihrer App im NotiPilot-Dashboard geben Sie die Expo Project ID und den Expo Access Token an.

Sie können auch direkt einen FCM- oder APNs-Token an die API senden (provider: "fcm" | "apns"). Diese Geräte werden registriert und erscheinen in Segmenten, in Version 1.0.0 werden Benachrichtigungen jedoch nur an Geräte mit Expo-Token zugestellt. Die direkte Zustellung über FCM/APNs ist auf der Roadmap.

2. Bevor Sie beginnen

  1. Legen Sie Ihre App im NotiPilot-Dashboard über den Bildschirm App hinzufügen an.
  2. Tragen Sie im Feld Expo Project ID Ihre EAS-Projekt-ID ein (UUID, app.json → extra.eas.projectId).
  3. Tragen Sie im Feld Expo Access Token den Token ein, den Sie unter expo.dev → Access Tokens erstellt haben. (Pflicht, wenn in Ihrem Expo-Projekt „Enhanced Security for Push Notifications“ aktiviert ist.)
  4. Die app_id, die Ihre mobile App an die API sendet, muss exakt mit der im Dashboard eingetragenen Expo Project ID übereinstimmen. Wird eine nicht registrierte app_id gesendet, antwortet die API mit 404 unknown_app.

3. Allgemeine Regeln

Thema Wert
Base URL https://app.notipilot.com/api/v1
Protokoll Nur HTTPS
Request-Body Content-Type: application/json, UTF-8
Authentifizierung Nicht erforderlich. Da die Device API in die mobile App eingebettet ist, verwendet sie keinen geheimen Schlüssel; die app_id ist kein geheimer Wert. Die Autorisierung erfolgt dadurch, dass die app_id im Dashboard registriert ist.
Rate Limit 300 Requests pro Minute und IP. Bei Überschreitung werden 429 und der Header Retry-After zurückgegeben.
Versions-Header Jede Antwort enthält den Header X-NotiPilot-API-Version: 1.0.0.

Aus Gründen der Abwärtskompatibilität funktionieren auch die (unversionierten) Adressen /api/register-device und /api/identify-device genauso wie v1. Verwenden Sie für neue Integrationen /api/v1.

4. Endpoints

4.1 POST /api/v1/register-device

Registriert oder aktualisiert ein Gerät (Upsert). Der Zuordnungsschlüssel ist die Kombination aus app_id + device_uid; wiederholte Aufrufe für dasselbe Gerät sind unbedenklich.

Request-Felder

Feld Typ Pflicht Beschreibung
app_id string (≤255) ✅ Expo Project ID aus dem Dashboard
device_uid string (≤191) ✅ Pro Installation dauerhafte, eindeutige Geräte-ID (siehe Geräte-ID)
token string (≤512) ✅ Push-Token. Format für Expo-Token: ExponentPushToken[...]
platform "android" | "ios" | "web" ✅ Plattform des Geräts
provider "expo" | "fcm" | "apns" – Wird automatisch aus dem Token-Format erkannt, falls nicht angegeben
external_id string (≤191) | null – Nutzer-ID aus Ihrem eigenen System. Mit null wird die Zuordnung aufgehoben (Logout-Szenario)
attributes object – Segmentierungsmerkmale (siehe Attributes)
tags string[] – Freie Tags (maximal 50, jeweils ≤64 Zeichen)
consent_marketing boolean – Einwilligung in Marketing-Benachrichtigungen. Standard: true

Beispiel-Request

Terminal
curl -X POST "https://app.notipilot.com/api/v1/register-device" \
  -H "Content-Type: application/json" \
  -d '{
    "app_id": "1c2d3e4f-5a6b-7c8d-9e0f-112233445566",
    "device_uid": "8f14e45f-ceea-467a-9575-0b3f5c6b2a11",
    "token": "ExponentPushToken[xxxxxxxxxxxxxxxxxxxxxx]",
    "platform": "android",
    "attributes": {
      "locale": "tr",
      "country": "TR",
      "city": "Istanbul",
      "app_version": "2.4.0"
    },
    "tags": ["beta"]
  }'

Erfolgreiche Antwort — 200 OK

JSON
{
  "success": true,
  "message": "Device registered successfully",
  "device_id": 1234,
  "expo_token_id": 567,
  "provider": "expo"
}

4.2 POST /api/v1/identify-device

Verknüpft das Gerät mit Ihrer eigenen Nutzer-ID (external_id) und aktualisiert optional Attributes/Tags. Rufen Sie den Endpoint auf, wenn sich der Nutzer anmeldet.

Feld Typ Pflicht Beschreibung
app_id string ✅ Expo Project ID aus dem Dashboard
device_uid string ✅ Derselbe Wert wie bei register-device
external_id string (≤191) ✅ Ihre Nutzer-ID
attributes object – Wird mit den vorhandenen Attributes zusammengeführt
tags string[] – Ersetzt die vorhandenen Tags, falls angegeben
consent_marketing boolean –
token, platform string – Wurde das Gerät noch nicht registriert, erfolgt mit diesen beiden Feldern eine vollständige Registrierung
Terminal
curl -X POST "https://app.notipilot.com/api/v1/identify-device" \
  -H "Content-Type: application/json" \
  -d '{
    "app_id": "1c2d3e4f-5a6b-7c8d-9e0f-112233445566",
    "device_uid": "8f14e45f-ceea-467a-9575-0b3f5c6b2a11",
    "external_id": "user_98765",
    "attributes": { "gender": "female" }
  }'
JSON
{ "success": true, "message": "Device identified", "device_id": 1234 }

Ist das Gerät noch nicht registriert und wurde kein token gesendet, wird das Gerät ohne Token angelegt ("auto_registered": true). Dieses Gerät erhält keine Benachrichtigungen, bis über register-device ein Token gesendet wird.

4.3 GET /api/v1/version

Health-Check und Versionsinformationen.

JSON
{ "success": true, "api_version": "1.0.0", "min_supported_version": "1.0.0" }

5. Attributes und Segmente

Das NotiPilot-Dashboard erzeugt aus den attributes-Werten der Geräte automatisch Segmente (z. B. „Türkischsprachige“, „Istanbul“, „Türkei + Istanbul“). Standortbasierte Segmente entstehen nur für Geräte, die country und city senden. Senden Sie diese Felder nicht, wird das Gerät nur bei Kampagnen an „Alle Nutzer“ berücksichtigt.

Standardschlüssel (werden vom Dashboard erkannt und beschriftet):

Schlüssel Format Beispiel
locale ISO-639-1-Sprachcode (Kleinbuchstaben) "tr", "en", "de"
country ISO-3166-1-alpha-2-Ländercode (Großbuchstaben) "TR", "DE", "NL"
city Städtename in einheitlicher Schreibweise "Istanbul", "Ankara"
gender male | female | other "female"

Sie können auch eigene Schlüssel hinzufügen (app_version, plan, favorite_team …).

Regeln

  • Maximal 50 Schlüssel. Schlüssel bestehen aus den Zeichen A-Z a-z 0-9 _ . - und sind maximal 64 Zeichen lang.
  • Werte können String, Zahl, Boolean oder null sein. String-Werte sind maximal 255 Zeichen lang.
  • Verwenden Sie in Werten nicht die Zeichen , und : (sie dienen in Segmentschlüsseln als Trennzeichen).
  • Zusammenführen (Merge): Die gesendeten Attributes werden mit den vorhandenen Werten zusammengeführt; nicht gesendete Schlüssel bleiben erhalten. Um einen Schlüssel zu löschen, senden Sie seinen Wert als null.
  • Wenn Sie das Feld attributes gar nicht senden, bleiben die gespeicherten Attributes unverändert.
  • Legen Sie keine personenbezogenen Daten wie E-Mail-Adressen, Telefonnummern oder Ausweisnummern in Attributes ab. Verwenden Sie für die Nutzerzuordnung external_id.

Woher bekomme ich Stadt und Land? Die Regionseinstellung des Geräts (locale → Land) erfordert keine Standortberechtigung und ist immer verfügbar. Für die Stadt eignen sich die im Nutzerprofil hinterlegte Stadt (die zuverlässigste Methode), Reverse Geocoding bei erteilter Standortberechtigung oder eine IP-basierte Standortermittlung in Ihrem eigenen Backend. Auch ohne Standortberechtigung sollten Sie zumindest country und locale senden.

6. Wie sollte die Geräte-ID erzeugt werden?

Für das Feld device_uid:

  • Erzeugen Sie beim ersten App-Start eine UUID v4 und speichern Sie sie dauerhaft (Android: SharedPreferences/DataStore, iOS: Keychain, Expo: expo-secure-store).
  • Sie darf sich bei App-Updates nicht ändern; nach Deinstallation und Neuinstallation der App ist eine Änderung normal.
  • Verwenden Sie keine IMEI, MAC-Adresse oder Werbe-ID (IDFA/GAID).

7. Fehlerantworten

Alle Fehlerantworten haben dieselbe Struktur:

JSON
{
  "success": false,
  "error": "validation_failed",
  "message": "Validation failed",
  "errors": { "platform": "Must be one of: android, ios, web" }
}
HTTP error Bedeutung Was ist zu tun?
400 invalid_json Body ist kein gültiges JSON Request korrigieren, nicht erneut versuchen
400 validation_failed Ein oder mehrere Felder sind ungültig; Details in errors Request korrigieren, nicht erneut versuchen
404 unknown_app app_id ist bei NotiPilot nicht registriert Expo Project ID im Dashboard prüfen
429 rate_limited Rate Limit überschritten Nach retry_after Sekunden erneut versuchen
500 server_error Serverseitiger Fehler Mit Exponential Backoff erneut versuchen

Empfohlenes Vorgehen auf Client-Seite: Nur bei 429 und 5xx (sowie bei Netzwerkfehlern) erneut versuchen; 4xx-Fehler protokollieren.

8. Empfohlener Ablauf

  1. App wird geöffnet → device_uid wird gelesen (bzw. erzeugt, falls nicht vorhanden).
  2. Benachrichtigungsberechtigung wird angefragt (Pflicht unter Android 13+ und iOS).
  3. Bei erteilter Berechtigung wird der Push-Token abgerufen → register-device wird aufgerufen (zusammen mit locale/country/city).
  4. Nutzer meldet sich an → identify-device wird aufgerufen (mit external_id).
  5. Nutzer meldet sich ab → register-device wird mit "external_id": null aufgerufen.
  6. Push-Token wird erneuert (onNewToken / Token-Listener) → register-device wird erneut aufgerufen.

9. Inhalt der Benachrichtigung

Eine über das Dashboard gesendete Benachrichtigung besteht aus title, body und optional einem JSON-Feld data. Der Inhalt von data wird an Ihre App übergeben; nutzen Sie ihn für Szenarien wie Deep Links, zum Beispiel:

JSON
{ "screen": "product", "product_id": "12345" }

Unter Android werden Benachrichtigungen an den Kanal default gesendet (channelId: "default"); legen Sie in Ihrer App einen Benachrichtigungskanal mit dieser ID an.

10. Änderungsprotokoll

Version Datum Änderungen
1.0.0 2026-09 Erste stabile Version. Base path /api/v1, Endpoint version, einheitliches Fehlerformat (error-Codes), Rate Limit, Validierung der app_id, Merge-Verhalten für Attributes.