mini_program_sdk

Flutter runtime SDK for rendering mini-program UI from static Mp JSON artifacts.

Host applications should use the supported package barrel:

import 'package:mini_program_sdk/mini_program_sdk.dart';

The 0.6.x line uses feature-oriented runtime internals while preserving public APIs, historical public import paths, and wire formats.

New screens can use a root Mp.page plus Mp.topBar to opt into explicit safe-area ownership and stable fixed headers. Existing artifacts retain the legacy outer padding and scrolling behavior.

Mp.page may also provide logical-pixel responsive breakpoints inherited by Mp.responsive descendants. Selection uses each node's available layout width, while Mp.constrainedContent and adaptive Mp.grid keep tablet, foldable, landscape, and resizable-window layouts bounded without exposing viewport dimensions through live state.

The SDK stays provider-neutral:

  • artifact opening uses MiniProgramEndpoint.public(apiBaseUri: artifactBaseUrl)
  • optional runtime data uses the artifact-owned publisher_backend.json
  • provider SDKs, database clients, payment clients, secrets, and business rules stay outside the host app

Static Opening

final config = MiniProgramConfig(
  source: EndpointRoutingMiniProgramSource(
    endpoints: {
      'coupon_demo': MiniProgramEndpoint.public(
        apiBaseUri: Uri.parse('https://static.example.com/coupon_demo/'),
      ),
    },
  ),
);

The host fetches manifest and screen/static artifact JSON from the artifact base URL. No runtime API URL is required to open the mini-program.

Artifact-local JSON resources are loaded through the optional MiniProgramJsonAssetSource capability. HttpMiniProgramSource and EndpointRoutingMiniProgramSource implement it for immutable files at artifacts/<appId>/<version>/assets/<path>. Resources are constrained by the host-accepted data cache policy and are never copied wholesale into live state.

Optional Runtime API

{
  "schemaVersion": 1,
  "type": "mini_program_publisher_backend_contract",
  "contractVersion": "1",
  "appId": "coupon_demo",
  "backendBaseUrl": "https://publisher.example.com/api/coupon_demo/",
  "permissionReason": "Load current coupon offers.",
  "healthEndpoint": "health",
  "smokeTests": [
    {
      "id": "health",
      "method": "GET",
      "endpoint": "health",
      "expectedStatus": 200,
      "expectJsonObject": true
    }
  ]
}

Artifact tooling validates and packages this file. The generated endpoint sets publisherApiPolicy from host-owned accepted policy. During loading, the SDK reads the contract, checks that policy, and creates an app-scoped connector. Denied calls fail with publisher_api_disabled.

Runtime APIs are used only by actions such as Mp.backend.call, Mp.backend.query, Mp.lazy.chunk, search/load-more, and form submit.

Host Rule

Opening a mini-program requires only appId + artifactBaseUrl. The publisher owns the optional runtime API declaration; the host owns only permission to use it.

Optional Current Location

location.getCurrent is provider-neutral. A host opts in by accepting a per-app MiniProgramLocationPolicy, installing a MiniProgramLocationProvider, and advertising CapabilityIds.locationCurrent. The SDK validates the host result and exposes only one approximate, foreground, user-initiated snapshot to the requesting mini-program.

final config = MiniProgramConfig(
  source: source,
  locationProvider: appLocationProvider,
  capabilityRegistry: CapabilityRegistry(
    const <CapabilityId>{CapabilityIds.locationCurrent},
  ),
);

Missing providers and denied policy fail with stable location error codes; they do not fall through to host bridge actions.

Optional Camera And Flashlight

camera.capturePhoto delegates still-photo capture to a host MiniProgramCameraProvider. The SDK enforces accepted camera policy, one host-wide capture at a time, logical cancellation, opaque media references, and temporary-media cleanup when the mini-program closes.

Captured media can be registered with MiniProgramMediaManager, rendered by hostMedia images through a bounded trusted preview, supplied to file uploads as opaque references, and released explicitly with media.release. Ownership is checked again in both the SDK and native provider. Native paths, content URIs, and raw bytes never enter live state.

Flashlight actions use MiniProgramFlashlightProvider under a separate MiniProgramFlashlightPolicy. The manager prevents cross-app control and turns the torch off when its owning mini-program closes. Neither capability exposes camera identifiers, native paths, content URIs, or bytes to live state.

Optional QR Scanning

qrCode nodes render locally on every supported Flutter platform. qr.scan uses a host-installed MiniProgramQrScannerProvider and an accepted MiniProgramQrPolicy; it is rejected unless dispatched from an explicit user gesture. The manager permits one scanner session at a time and cancels it when the mini-program closes.

Providers return MiniProgramQrScanResult as inert structured data. The SDK validates its size, type, format, and UTC timestamp, but deliberately does not open URLs, join Wi-Fi, add contacts, or execute any scanned content. Scanner torch controls belong to the scanner session and are separate from MiniProgramFlashlightProvider.

Optional System Sharing

share.open invokes a host MiniProgramShareProvider only after an explicit user gesture and accepted MiniProgramSharePolicy. The SDK validates bounded text, one absolute HTTPS URL, and up to the accepted number of opaque media references. Media ownership is revalidated against MiniProgramMediaManager before the provider is called.

Providers return MiniProgramShareResult(chooserOpened: true) when platform sharing UI opens. The SDK intentionally does not report share completion, because Android's chooser does not provide a reliable completion result. Native paths, content URIs, authorization data, and media bytes remain inside the trusted host integration.

Optional Publisher File Transfers

file.upload, file.download, and file.cancel use a separate streaming host provider because the normal Publisher API connector is intentionally bounded to JSON responses. The SDK still resolves only relative routes against the validated artifact Publisher API and applies delivery and auth headers.

Hosts accept a per-app MiniProgramFilePolicy and install one MiniProgramFileTransferProvider. Transfers are app-isolated, cancellable, and constrained by accepted MIME types, destinations, concurrency, free-space reserve, and an optional maximum file size. Live state contains only bounded progress and sanitized result metadata; providers must never return native paths or content URIs.

Optional Media Playback

MiniProgramMediaPlaybackProvider supplies app-scoped foreground audio and inline video sessions. The SDK resolves only artifact assets or relative Publisher API routes, keeps URLs and authorization headers outside live state, and releases every session when its mini-program closes.

Hosts decide audio and video independently through MiniProgramMediaPlaybackPolicy. A temporary cache request also requires the matching accepted audio/video cache policy. Providers receive app- and kind-scoped byte and TTL limits. The generated Android Media3 adapter enforces them with LRU range/HLS-segment cache directories, clears expired entries when opening a cache, participates in audio focus, pauses when audio becomes noisy or the host leaves the foreground, and supports native fullscreen video. Permanent offline downloads and background playback are not part of this release.

Libraries

actions/host_action_dispatcher
auth/mini_program_auth
cache/asset_cache
cache/delivery/asset/entry
cache/delivery/asset/file_store
cache/delivery/asset/no_op_store
cache/delivery/asset/store
cache/delivery/manifest/entry
cache/delivery/manifest/file_store
cache/delivery/manifest/memory_store
cache/delivery/manifest/store
cache/delivery/screen/entry
cache/delivery/screen/file_store
cache/delivery/screen/keys
cache/delivery/screen/memory_store
cache/delivery/screen/store
cache/delivery/storage_key_codec
cache/manifest_cache
cache/mini_program_cache_bundle
cache/persistence/file_runtime_store
cache/persistence/preferences_runtime_store
cache/persistence/runtime_entry_codec
cache/persistence/storage_key_codec
cache/runtime_cache
cache/runtime_file_cache
cache/runtime_shared_preferences_cache
cache/screen_cache
camera/mini_program_camera
capability_registry
data/mini_program_data_resource
display/mini_program_display
feature_flag_evaluator
file/mini_program_file
flashlight/mini_program_flashlight
host_bridge
location/mini_program_location
manifest_loader
media/mini_program_media
media_playback/mini_program_media_playback
mini_program_config
mini_program_controller
mini_program_discovery
mini_program_failure
mini_program_host
mini_program_launch_options
mini_program_launcher
mini_program_page
mini_program_runtime
mini_program_scope
mini_program_sdk
network/asset_resolver
network/http_mini_program_source
network/local_backend_defaults
network/mini_program_backend_connector
network/mini_program_backend_store
network/mini_program_delivery_context
network/mini_program_endpoint
network/mini_program_source
network/mini_program_source_exception
network/published_mini_program_catalog_client
observability/sdk_logger
qr/mini_program_qr
rendering/mini_program_backend_binding_resolver
rendering/mini_program_screen_renderer
rendering/mp_screen_renderer
sdk_context
share/mini_program_share
state/mp_state
version_validator
widgets/sdk_email_auth_sheet
widgets/sdk_error_view
widgets/sdk_loading_view
widgets/sdk_offline_notice