Skip to main content

Analytics

VLPlay SDK ships pre-wired with AppsFlyer as the canonical event pipeline plus Firebase Analytics for crash + session data. There is no first-party VLPlay event API — the SDK doesn't post to a /api/v1/analytics/* endpoint of its own. Instead, it fires ~125 named events into AppsFlyer's funnel (lifecycle, login, register, third-party login, payment, anti-addiction, retention) which you view in the AppsFlyer dashboard, and a smaller set into Firebase for crash + session-time reporting.

This means your "analytics integration" is mostly: ensure your appsflyer_dev_key is correct, ensure the CMS appsFlyerTracking master kill-switch is on, and let the SDK do the rest. For game-specific events (level-up, IAP funnel, custom screens), call hitActivityFirebase on Android (which logs to Firebase Analytics) or any AppsFlyer SDK method directly from your code.

The 125 funnel events fire automatically — you don't need to opt in to each one. Disabling all event tracking is a single CMS toggle (appsFlyerTracking: false), which short-circuits every AppsFlyerHelper.trackXxx call so no events leave the device. This is the legal kill-switch for compliance with regional privacy regs.

What's Tracked Automatically

The SDK fires events into AppsFlyer at these lifecycle points:

Event groupEventsTrigger
Lifecycleaf_app_launch, sdk_start_initialization, sdk_initialized, sdk_first_initialized, show_login_scene_successSDK init, first launch
Login funnelaf_open_login, login_start, af_click_login, login_submit, login_success, login_completed, login_success_finalSign-in flow
Register funnelregister_start, register_input_account, register_submit, register_success, register_completed, af_complete_registrationNew-account flow
Third-party loginthird_login_clicked, third_login_invoked, third_login_callback_success/fail, third_login_completedFacebook / Google / Apple sign-in
Auto-loginauto_login_start, auto_login_success, auto_login_failRefresh-token-based auto-login on app launch
Payment funnelpurchase_initiated, product_selected, sdk_payment_init, open_payment_screen, sdk_payment_callback_success/fail/cancel, sdk_payment_validated, sdk_payment_validated_success/fail, sdk_payment_completed, af_purchaseV3 IAP 2-step flow
Logoutlogout_click, logout_success, logout_failSign-out
Delete accountdelete_account_entry_click, delete_account_confirm, delete_account_success/fail/cancelAccount deletion flow
Bind phonebind_check_required, input_phone, request_sms_code, request_sms_code_success/fail, bind_check_submit, bind_success, bind_completed, bind_fail, skip_bindPhone-OTP bind
Game eventsenter_gameplay, character_creation_started/finished, play_time, level_up, vip_level_up, level_achieved, ~67 totalLong-tail game-state events
Retentionaf_first_launch, check_retention, payment_success, content_viewDay-N return tracking

The full list lives in AppsFlyerHelper.java (Android) and AppsFlyerHelper.m (iOS). Each method follows the convention trackXxx(params...) and is gated on the appsFlyerTracking CMS flag.

Triggering Custom Game Events

For game-specific events (level-up, custom screen views, achievements), use the AppsFlyer SDK or Firebase Analytics directly. The VLPlay SDK exposes a small wrapper for Firebase:

import VLPlaySDK

// Built-in helper for AppsFlyer game events
SDKManager.default()?.hitActivity(
.levelUp, // APICategoryType enum
extendData: "{\"newLevel\":42}",
forUser: "username",
userId: "65a1f3b...",
completion: { _, _, _ in }
)

// Or use AppsFlyer SDK directly for full flexibility
import AppsFlyerLib
AppsFlyerLib.shared().logEvent(name: "tutorial_complete", values: [
"stage": "intro",
"duration_seconds": 87,
])

Note: As of SDK 1.0.0, the iOS hitActivity:* family is dead codeNetworkModal+Tracking.m has the BE call commented out and VLPlayEventLogging.m GA tracking is disabled. The methods stay for ABI compatibility but don't emit events. Use AppsFlyerLib directly for custom events on iOS until the next SDK release.

The AppsFlyer SDK is already initialized by VLPlay's bootstrap, so you can call AppsFlyerLib.shared() / getInstance() from anywhere after [SDKManager handleApplication:...] / VLPlaySDKManager.initApplication.

User Properties

Set persistent user properties to segment your analytics dashboard by player attributes. AppsFlyer automatically attaches the customer_user_id (= accountId) to every event after sign-in via the SDK's call to AppsFlyerLib.shared().customerUserID = id. Additional properties go through Firebase Analytics:

import FirebaseAnalytics

Analytics.setUserProperty("gold", forName: "vip_tier")
Analytics.setUserProperty("42", forName: "player_level")
Analytics.setUserProperty("vi", forName: "preferred_language")

User properties have a 25-property cap (Firebase limit). Don't set high-cardinality values (e.g. last_login_timestamp) — use events for those instead.

Disabling Tracking

If a player opts out of analytics (GDPR, CCPA, or VN PDPA), or your CMS sets appsFlyerTracking: false, the SDK short-circuits every trackXxx call and the AppsFlyer SDK enters anonymized mode. To explicitly verify the kill-switch is active:

let trackingOn = SDKManager.isFeatureEnabled(VLPlaySDKFeatureAppsFlyerTracking)
print("AppsFlyer tracking enabled:", trackingOn)

When the master kill-switch is OFF, the SDK still calls AppsFlyer's init (so the dev key is set), but no logEvent calls fire. AppsFlyer's automatic install attribution still works — it just doesn't see in-app events.

App Tracking Transparency (iOS)

iOS 14+ requires the App Tracking Transparency prompt to track players across apps + websites (IDFA access). The SDK exposes a helper:

AppDelegate.swift
import VLPlaySDK

func applicationDidBecomeActive(_ application: UIApplication) {
SDKManager.default()?.initATT()
}

initATT shows the system tracking prompt the first time it's called, then no-ops on subsequent calls. The Info.plist must declare NSUserTrackingUsageDescription (see iOS Installation).

If the player denies tracking, AppsFlyer continues to work but with reduced attribution accuracy (no IDFA). VLPlay funnel events still fire — only cross-app attribution is impacted.

Viewing the Data

Three dashboards expose VLPlay events:

  1. AppsFlyer Dashboard (app.appsflyer.com) — funnel + retention + LTV. Filter events with event_name to slice by funnel stage. Custom events from logEvent show up under the same dashboard.
  2. Firebase Console → AnalyticshitActivityFirebase events plus auto-collected events (screen views, session duration, crashes). Best for ad-hoc cohort analysis.
  3. VLPlay CMS Reports — server-side aggregation of Player, Purchase, and LoginHistory collections. DAU / MAU / NRU / RRPU / LTV. Ask your VLPlay rep for access.

What's Not Tracked

VLPlay SDK does not track:

  • Background location (no Always permission requested).
  • Microphone / camera content (only avatar selection, with player consent).
  • Contacts / calendar.
  • Other apps installed on the device.
  • Inputs other than the game's own taps (no key-logging).

The SDK collects the player's accountId, session start/end timestamps, IP address (one per session), device model + OS version, and IAP records. Full data inventory is in the VLPlay Privacy Policy linked in FAQ → Privacy & Compliance.

Performance

Events are logged synchronously into AppsFlyer's in-memory buffer and flushed in batches every 5 seconds (or sooner if 100+ events queue up). The SDK doesn't add measurable latency to the calling site — hitActivityFirebase and track* methods return in <1ms.

If your game is exceptionally chatty (1000+ events per minute), you can throttle by debouncing your own event firing. The SDK doesn't drop events, so every track call costs network on flush.