Skip to main content

OpenFeature Dart Client SDK

This package is the vendor-neutral OpenFeature SDK for Dart client applications. It uses the static-context paradigm. It has no Flutter or dart:io dependency.

The package is in beta. The first beta defines the public client and provider contracts. It provides synchronous typed evaluation, event handlers, hooks, ordered context changes, and an in-memory provider. Later beta changes will complete the remaining conformance work before the first stable release.

Install

The published beta requires Dart 3.12.2 or later within Dart 3.x. Flutter applications need a Flutter release that includes a compatible Dart SDK.

dependencies:
openfeature_dart_client_sdk: ^0.0.1-beta.1

Run dart pub get, or flutter pub get in a Flutter application.

Use the client

import 'package:openfeature_dart_client_sdk/openfeature_dart_client_sdk.dart';

Future<void> main() async {
final provider = InMemoryProvider({
'new-checkout': true,
'welcome-message': 'Hello',
});

await OpenFeatureAPI.instance.setProviderAndWait(provider);
await OpenFeatureAPI.instance.setEvaluationContextAndWait(
EvaluationContext(targetingKey: 'user-123'),
);

final client = OpenFeatureAPI.instance.getClient('checkout');
final enabled = client.getBooleanValue('new-checkout', false);
final message = client.getStringValue('welcome-message', 'Welcome');

print('$enabled: $message');
await OpenFeatureAPI.instance.shutdown();
}

Implement a provider

Implement FeatureProvider with synchronous resolvers. A resolver must use local state. It must not perform network, file, or platform-channel I/O.

Implement only the optional capabilities that the provider needs:

  • InitializableProvider for asynchronous initialization.
  • ContextReconciliationProvider for static-context changes.
  • ShutdownProvider for resource cleanup.
  • ProviderEventSource for provider lifecycle events.
  • DomainScopedProvider when one provider instance supports one domain.
  • TrackingProvider for non-blocking tracking.

An initializable or reconciling provider must also implement ProviderEventSource. It must emit the terminal lifecycle event before its method terminates. The SDK bounds lifecycle waits to 30 seconds by default so a provider contract violation cannot indefinitely block context changes or shutdown. Tests and isolated integrations may select a shorter timeout through createIsolatedOpenFeatureAPI(lifecycleTimeout: ...).

When initialization or context reconciliation times out, the SDK quarantines and detaches that provider instance. Its underlying asynchronous work cannot be cancelled safely, so applications must register a new provider instance rather than retrying the timed-out one. Subscription cancellation and shutdown cleanup are bounded by the same timeout.

A provider that implements ContextReconciliationProvider can have only one active API/domain binding. Use a separate provider instance for each static context. Providers that resolve entirely from the context passed to each resolver and do not reconcile cached state may be shared across domains.

The server and client packages share the open-feature/dart-sdk repository. The repository rename preserves this package name, Dart imports, and independent client releases.

Scope

This package does not include an HTTP transport, an OFREP provider, a vendor provider, persistent storage, or Flutter APIs.

Validate the package archive

Run the repository staging command to create and validate the same isolated client archive used by the publication workflow:

dart tool/stage_client_package.dart --dry-run

See the beta release procedure for the first-publication bootstrap and later automated prereleases.