sankofa_flutter 0.2.0 copy "sankofa_flutter: ^0.2.0" to clipboard
sankofa_flutter: ^0.2.0 copied to clipboard

Sankofa Flutter SDK — Deploy (OTA patches via KBC interpreter), Analytics, Replay, Catch, Switch, Config, and Pulse, with offline queueing and Ed25519-signed envelopes.

Sankofa Flutter SDK 🚀 #

Pub Version License: MIT Sankofa

The official Flutter SDK for Sankofa — six products in one package: Analytics, Catch, Switch, Config, Pulse, Replay. Plus a standalone native crash bridge that captures iOS NSException + POSIX signals and Android JVM-uncaught + ANR with zero dependency on the iOS / Android SDKs.


✨ Features #

  • Analytics: events, identify, peopleSet, deep-link attribution, offline-first queueing.
  • Catch (Crashlytics + Sentry merged): Dart-level errors via FlutterError.onError / PlatformDispatcher.onError / isolate listeners — plus iOS NSException + POSIX signals + main-queue stalls and Android JVM-uncaught + ANR via the bundled Flutter plugin.
  • Switch: feature flags with bundled defaults + onChange listeners.
  • Config: remote-config with typed get<T> accessors.
  • Pulse: in-app surveys (NPS, CSAT, custom).
  • Session Replay: wireframe + screenshot modes, automatic input masking, SankofaMask widget.

🚀 Quick start #

1. Install #

Add the dependency to your pubspec.yaml:

dependencies:
  sankofa_flutter: ^0.1.0

2. Initialize #

One line — Catch auto-installs with the SDK. Both Dart errors AND iOS/Android native crashes flow through Sankofa.captureException etc.

import 'package:sankofa_flutter/sankofa_flutter.dart';

void main() async {
  WidgetsFlutterBinding.ensureInitialized();

  await Sankofa.instance.init(
    apiKey: 'YOUR_PROJECT_API_KEY',
    endpoint: 'https://api.sankofa.dev',
    debug: true,
    // Catch (defaults shown — enableCatch is true by default).
    enableCatch: true,
    catchEnvironment: 'production',
    release: 'myapp@1.4.0',
    // Optional Sentry-style hook to scrub PII / drop noise.
    beforeSend: (event) {
      if (event.message?.contains('setState called after dispose') ?? false) return null;
      return event;
    },
  );

  runApp(const MyApp());
}

🛠 Usage #

Analytics #

// Events
Sankofa.instance.track('completed_purchase', {
  'item_name': 'Vintage Camera',
  'price': 120.50,
  'currency': 'USD',
});

// Identity
Sankofa.instance.identify('user_99');
Sankofa.instance.setPerson(
  name: 'Jane Doe',
  email: 'jane@example.com',
  properties: {'membership': 'Gold'},
);

Catch — error capture #

Once init() resolves, every helper below works from anywhere. No SankofaCatch.instance to thread through your widget tree.

// Capture a handled exception
try {
  await chargeCard(amount);
} catch (err, stack) {
  Sankofa.captureException(err, stack);
}

// Non-error event
Sankofa.captureMessage('payment retry attempted');

// Crashlytics-style breadcrumb log — rides on next capture, doesn't bill.
Sankofa.log('checkout: applying coupon SUMMER25');

// Ambient context
Sankofa.setUser(CatchUserContext(id: 'u_42', email: 'ada@example.com'));
Sankofa.setTag('flow', 'checkout');
Sankofa.setExtra('cart_id', cart.id);

// Sentry-style temporary scope — tags only on this capture.
Sankofa.withScope((scope) {
  scope.setTag('checkout_step', 'payment');
  scope.setLevel(CatchLevel.warning);
  Sankofa.captureException(err);
});

Session replay #

MaterialApp(
  navigatorObservers: [SankofaNavigatorObserver()],
  home: const SankofaReplayBoundary(
    child: MyHomePage(),
  ),
);

// Hide sensitive UI from replays
SankofaMask(
  child: TextField(controller: _passwordController, obscureText: true),
);

Switch — feature flags #

final flags = SankofaSwitch({'new_checkout': false});

if (flags.getFlag('new_checkout')) showNewCheckout();
final variant = flags.getVariant('checkout_redesign', defaultValue: 'control');

Config — remote config #

final config = SankofaConfig({'max_uploads_per_day': 25});

final maxUploads = config.get<int>('max_uploads_per_day', defaultValue: 25);

Pulse — surveys #

await SankofaPulse.instance.register();
await SankofaPulse.instance.show(context, surveyId: 'nps-2024');

🪤 Native crash bridge (Phase C) #

The Flutter SDK is a federated plugin with a standalone native crash reporter in ios/Classes/ and android/src/main/kotlin/. Zero dependency on the standalone SankofaIOS Pod or dev.sankofa:sankofa Maven artifact.

Layer Captured
Dart FlutterError.onError, PlatformDispatcher.onError, isolate listeners
iOS plugin NSSetUncaughtExceptionHandler, POSIX signals (SIGSEGV/SIGABRT/SIGBUS/SIGILL/SIGFPE/SIGTRAP/SIGSYS), main-queue stalls
Android plugin Chained Thread.UncaughtExceptionHandler, ANR watcher (main thread > 5s)

All three POST to the same /api/catch/events endpoint. Sankofa.setUser / setTag(s) / flushCatch mirror to the native side automatically.


📑 Documentation #

For full API references and integration guides, visit the Sankofa docs.


🛡 License #

Distributed under the MIT License. See LICENSE for more information.

1
likes
0
points
294
downloads

Publisher

unverified uploader

Weekly Downloads

Sankofa Flutter SDK — Deploy (OTA patches via KBC interpreter), Analytics, Replay, Catch, Switch, Config, and Pulse, with offline queueing and Ed25519-signed envelopes.

Homepage
Repository (GitHub)
View/report issues

License

unknown (license)

Dependencies

app_links, carrier_info, connectivity_plus, crypto, cryptography, device_info_plus, flutter, http, package_info_plus, path_provider, shared_preferences, uuid

More

Packages that depend on sankofa_flutter

Packages that implement sankofa_flutter