mobile_proof_plugin 0.2.0
mobile_proof_plugin: ^0.2.0 copied to clipboard
Flutter plugin for TLSN-based mobile proofs with proxy/MPC auto-fallback, WebView capture, and custom provider flows.
mobile_proof_plugin #
mobile_proof_plugin is a Flutter plugin for generating TLSN-backed mobile proofs from provider web sessions.
It gives app developers a one-call API that:
- launches a plugin-managed WebView login flow,
- captures the provider request defined by your rules,
- runs MPC/proof generation through the native core, and
- returns a structured
ProofArtifact.
Features #
- One-call attestation with
MobileProofClient.attestProvider(...) - Custom provider configuration via JSON registry
- Built-in request matching and selective reveal policies
- Progress stream for UX updates
- Android + iOS platform channel bridges
Supported Platforms #
- Android (min SDK 24)
- iOS (13.0+)
Installation #
dependencies:
mobile_proof_plugin: ^0.1.1
Then run:
flutter pub get
Quick Start #
import 'package:flutter/material.dart';
import 'package:mobile_proof_plugin/mobile_proof_plugin.dart';
Future<void> runAttestation(BuildContext context) async {
final client = MobileProofClient(bridge: MethodChannelNativeBridge());
final progress = client.subscribeProgress().listen((event) {
debugPrint('[${event.phase.name}] ${event.message}');
});
try {
final artifact = await client.attestProvider(
context: context,
providerId: 'my_provider.current_user.v1',
providerRegistryAssetPath: 'assets/providers.json',
transportConfig: TransportConfig(
deploymentMode: DeploymentMode.hosted,
verifierUrl: Uri.parse('https://your-verifier.example.com'),
trustedNotaryKeys: const <String>[
'BASE64_NOTARY_PUBLIC_KEY'
],
enforceNativeCore: true,
),
);
debugPrint('Proof ID: ${artifact.proofId}');
debugPrint(client.exportProof(ProofExportFormat.prettyJson, artifact: artifact));
} finally {
await progress.cancel();
await client.dispose();
}
}
Proof Mode Selection (Auto / Proxy / MPC) #
attestProvider(...) defaults to proofMode: ProofMode.auto, which tries
proxy mode first and falls back to MPC on fallback-eligible failures (verifier
rejects proxy, host not allow-listed, TLS cipher mismatch, pre-handshake
errors). Once the HTTP request has reached the origin, fallback is suppressed
to avoid double-sending — the call surfaces the error instead.
// Default: auto-fallback
await client.attestProvider(context: ctx, providerId: 'id', ...);
// Force a specific mode (no fallback in either case):
await client.attestProvider(proofMode: ProofMode.proxy, ...);
await client.attestProvider(proofMode: ProofMode.mpc, ...);
// Auto mode with fallback suppressed (debugging / cost-sensitive):
await client.attestProvider(proofMode: ProofMode.auto, disableFallback: true, ...);
After a successful attestation, inspect artifact.proofMode for the mode
that produced the proof, and (when telemetry is enabled) read
artifact.payload['modeAttempts'] for the per-attempt timeline. Per-provider
proxyCompatible: false in providers.json causes auto mode to skip the
proxy attempt entirely.
Testing fallback locally #
To exercise the fallback path during development, remove the target host from
PROXY_ALLOWED_HOSTS. The verifier rejects the proxy attempt with
proxyDestinationNotAllowed, which is fallback-eligible before request bytes
reach the origin.
Then run attestProvider with proofMode: ProofMode.auto (the default) and
inspect artifact.payload['modeAttempts'] to confirm the proxy attempt
failed and the MPC attempt succeeded.
Custom MPC Through WebView #
This plugin is designed to support custom providers through a registry file (JSON).
You define:
- provider login URL and callback URL,
- request match rules for selecting the captured exchange,
- reveal rules and privacy policy (allowed headers/body paths), and
- proof target constraints (method/url/max sizes).
Include the registry in your app assets and pass it via providerRegistryAssetPath.
Default registry shipped by this package: packages/mobile_proof_plugin/assets/providers.json.
Minimal Provider Entry #
{
"schemaVersion": "1.0.0",
"providers": [
{
"id": "my_provider.current_user.v1",
"displayName": "My Provider",
"webLogin": {
"startUrl": "https://example.com/login",
"callbackUrl": "https://example.com/callback",
"oauthHosts": ["example.com"]
},
"proofTarget": {
"method": "GET",
"url": "https://api.example.com/current_user",
"maxSentData": 4096,
"maxRecvData": 16384
},
"requestMatchRules": [
{ "type": "methodEquals", "pattern": "GET" },
{ "type": "urlContains", "pattern": "/current_user" }
],
"revealRules": [
{
"direction": "RECV",
"part": "BODY",
"action": "REVEAL",
"params": { "type": "json", "path": "$.id" }
}
],
"privacyPolicy": {
"allowedRequestHeaders": ["authorization"],
"allowedResponseBodyJsonPaths": ["$.id"]
}
}
]
}
Security Notes #
- Set
enforceNativeCore: truein production. - Always set
trustedNotaryKeys; the native core requires this for secure proof verification. - Keep reveal rules as narrow as possible to avoid over-disclosure.
Native Rust Core Packaging #
The plugin API depends on native Rust core binaries for real MPC/proof generation. Stub bridges may be used only for local development and integration testing.
For production releases:
- export Android
.solibraries for all supported ABIs and uploadmobile_proof_plugin_android_jniLibs.zipto GitHub Releases tagmobile_proof_plugin-v<plugin version>, - export iOS
.xcframeworkartifacts with exported Rust symbols and uploadMobileProofRustCore.xcframework.zipto GitHub Releases tagmobile_proof_plugin-v<plugin version>, - wire these artifacts into the plugin (
jniLibs/ podspec vendored frameworks), and - validate with
enforceNativeCore: trueon real devices before release.
The published package intentionally excludes android/src/main/jniLibs/** and ios/RustCore/** to stay under pub.dev size limits.
During Android build and iOS pod install, the plugin downloads native artifacts from GitHub Releases automatically.
If the release asset is missing or inaccessible, proof generation falls back to non-production stub behavior and attestation fails.
Release maintainers can prepare and upload native artifacts with:
cd mobile_tlsn_plugin
./scripts/export-native.sh all
./scripts/publish-native-release-assets.sh <version>
The podspec resolves this iOS URL pattern by default:
https://github.com/burnt-labs/mpc-plugin/releases/download/mobile_proof_plugin-v<version>/MobileProofRustCore.xcframework.zip
The Android build resolves this URL pattern by default:
https://github.com/burnt-labs/mpc-plugin/releases/download/mobile_proof_plugin-v<version>/mobile_proof_plugin_android_jniLibs.zip
Set MOBILE_PROOF_PLUGIN_IOS_XCFRAMEWORK_URL or MOBILE_PROOF_PLUGIN_ANDROID_JNILIBS_URL to override these sources in private forks.
Example App #
See example/ in this package for a minimal runnable integration.
Additional Documentation #
License #
MIT (see LICENSE).