> ## Documentation Index
> Fetch the complete documentation index at: https://docs.portalhq.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Feature flags

> Enable or disable specific SDK behaviors using feature flags when initializing Portal.

## Overview

The `PortalFeatureFlags` class is used to configure feature flags when initializing the Portal SDK. Each flag corresponds to a specific feature or behavior that can be toggled on or off. All flags are optional and immutable after initialization — they cannot be changed at runtime.

## Enabling feature flags

Pass `featureFlags` when calling `portal.initialize()`:

```dart theme={null}
import 'package:portal_flutter/portal_flutter.dart';

final portal = Portal();

await portal.initialize(
  apiKey: 'CLIENT_API_KEY_OR_CLIENT_SESSION_TOKEN',
  featureFlags: PortalFeatureFlags(
    useEnclaveMpcApi: true,
  ),
);
```

## Available flags

### `usePreGeneratedWallet`

* **Type:** `bool?`
* **Default:** `null` (disabled)
* **Description:** When enabled, `portal.createWallet()` attempts to claim a pre-generated wallet share instead of running the standard interactive MPC generation. This can make wallet creation faster. You do not need to change how you call `createWallet`.

**How it works**

Normally, `createWallet` runs the interactive MPC key generation protocol in real time. With this flag enabled, the SDK first tries to claim a share from a pre-computed pool. If that fails with an HTTP 5xx response from the enclave, the SDK automatically falls back to the standard generation flow — the fallback is transparent, and `createWallet` resolves or rejects exactly as it would through the standard flow. Failures that aren't a 5xx (for example, a malformed request or a network failure) are not retried and propagate as usual.

**Expected failure cases**

The most common failure to plan for with this flag enabled is a client that **already has a wallet**. The enclave rejects the claim with a `400` — `Not eligible to claim a pre-generated wallet`, or `Wallet already exists` when it's caught while finalizing the claim. Because that isn't a 5xx, the SDK does *not* fall back to standard generation: `createWallet()` throws a `PortalException` carrying the enclave's message.

This applies to any client that already holds a stored signing share — one that created a wallet earlier, recovered a wallet, or had a wallet created on another device — not just a `createWallet()` call that happens twice in the same session. Only call `createWallet()` for clients that don't already have a wallet, and keep a `try`/`catch` around it:

```dart theme={null}
try {
  final addresses = await portal.createWallet();
  print('My Portal EVM address: ${addresses.ethereum}');
} on PortalException catch (e) {
  print('Wallet creation failed: ${e.message}');
}
```

**When to enable**

Enable `usePreGeneratedWallet` when you want faster wallet creation without changing your integration. The resulting wallet is identical to one created through the standard flow. See [Pre-Generated Wallets](../../../resources/pre-generated-wallets) for a deeper explanation.

**Limitations**

* This is a performance optimization only; it doesn't change the API surface, the resulting wallet, or how backup/recovery works.
* Fallback to standard generation happens on an HTTP 5xx response from the enclave only. A 4xx rejection (such as a client that already has a wallet), an unauthorized API key, and network failures propagate normally — so these produce a failed wallet creation rather than a slow one. Keep your existing error handling around `createWallet()`.

**Example**

```dart theme={null}
import 'package:portal_flutter/portal_flutter.dart';

final portal = Portal();

await portal.initialize(
  apiKey: 'CLIENT_API_KEY_OR_CLIENT_SESSION_TOKEN',
  featureFlags: PortalFeatureFlags(
    usePreGeneratedWallet: true,
  ),
);
```

***

### `useEnclaveMpcApi`

* **Type:** `bool?`
* **Default:** `null` (disabled)
* **Description:** Enables the use of the **Enclave MPC API** for signing transactions. When enabled, MPC operations are executed server-side in a secure AWS Nitro Enclave, ensuring consistent and faster signing times.

**How it works**

Executing MPC operations on client devices can lead to inconsistent signing times due to variations in device CPU performance. By enabling the `useEnclaveMpcApi` flag, the client key share is transmitted to a **Trusted Execution Environment (TEE)** hosted in an AWS Nitro Enclave. This ensures:

1. **Encrypted memory**: All data processed in the enclave is encrypted and inaccessible to anyone, including Portal employees.
2. **Verified execution**: Users can cryptographically verify that their request was handled in a secure enclave using signed measurements.

**Example**

```dart theme={null}
import 'package:portal_flutter/portal_flutter.dart';

final portal = Portal();

await portal.initialize(
  apiKey: 'CLIENT_API_KEY_OR_CLIENT_SESSION_TOKEN',
  featureFlags: PortalFeatureFlags(
    useEnclaveMpcApi: true,
  ),
);
```

***

### `usePresignatures`

* **Type:** `bool?`
* **Default:** `null` (disabled)
* **Description:** Enables the automatic use of presignatures to improve signing latency for EVM transactions.

**How it works**

When `usePresignatures` is enabled, the SDK automatically generates and uses presignatures in the background. This reduces the time required for transactions to be signed, as the SDK pre-computes part of the MPC signing flow. Users do not need to take any additional actions — the SDK handles presignature generation and consumption automatically.

<Note>
  Presignatures currently only support the `SECP256K1` curve (EVM, Bitcoin). ED25519 (Solana) signing is unaffected by this flag — support is coming soon.
</Note>

**Example**

```dart theme={null}
import 'package:portal_flutter/portal_flutter.dart';

final portal = Portal();

await portal.initialize(
  apiKey: 'CLIENT_API_KEY_OR_CLIENT_SESSION_TOKEN',
  featureFlags: PortalFeatureFlags(
    usePresignatures: true,
  ),
);
```

***

## Important notes

* All feature flags are **set at initialization time** and cannot be changed at runtime.
* Each flag is optional (`bool?`) — you only need to set the flags you want to enable.
* Flags not specified will use their default behavior (disabled).
