npm package: @flagr-dev/sdk
Description: TypeScript/JavaScript SDK for Flagr — feature flags via SSE, evaluated locally
Author: Flagr
Latest version: 0.3.0

# @flagr-dev/sdk

TypeScript/JavaScript SDK for [Flagr](https://flagr.dev) — feature flag client for Node.js with local evaluation and real-time SSE updates.

Connects once at startup, seeds a local in-memory cache from the initial snapshot, and applies real-time updates as flags change. Every flag evaluation is fully local — no network call per check.

## Prerequisites

- Node.js >= 18
- A Flagr account — sign up free at [flagr.dev](https://flagr.dev)

## Get your SDK key

This SDK connects to the hosted Flagr service at [flagr.dev](https://flagr.dev). No self-hosting or infrastructure required — Flagr manages the flag storage, evaluation API, and real-time delivery for you.

To get an SDK key:

1. Sign up at [flagr.dev](https://flagr.dev) — the Hobby plan is free
2. Create a **project** (e.g. `my-app`)
3. Create an **environment** inside the project (e.g. `production`, `staging`)
4. Copy the `sdk_live_...` key shown on the environment page

Each environment has its own SDK key. Use the key for the environment your service is running in. Keep it secret — treat it like an API key.

## Install

```bash
npm install @flagr-dev/sdk
```

## Quickstart

```ts
import { FlagrClient } from "@flagr-dev/sdk";

// Connect once at startup — seeds local cache via SSE
const client = new FlagrClient("sdk_live_...");
client.connect();

// Check instantly — synchronous, no network call
// tenant_id can be a user ID, org ID, account ID, or any entity identifier in your product
// tenant_id is optional — omit it for flags that don't use partial rollout
const enabled = client.isEnabled(
  "new-checkout",                          // flag key
  "a1b2c3d4-e5f6-7890-abcd-ef1234567890", // tenant_id (optional, default "")
  false                                    // default value if flag not found (optional, default false)
);

if (enabled) {
  // show new checkout
}
```

## React to changes (onChange)

Subscribe to real-time updates for a specific flag and tenant. The callback fires immediately with the current value, then again on every SSE update — no new connection is made.

```ts
// tenant_id is optional — omit it for flags that don't use partial rollout
const sub = client.onChange(
  "new-checkout",
  "a1b2c3d4-e5f6-7890-abcd-ef1234567890", // optional
  (enabled) => {
    console.log("new-checkout is now", enabled);
  }
);

// Later — stop receiving updates
sub.unsubscribe();
```

## Low-level connect callbacks

```ts
const disconnect = client.connect(
  (snapshot) => {
    // Called once with all flag values on connect
    console.log("Flags loaded:", Object.keys(snapshot).length);
  },
  (flagKey, value) => {
    // Called on every real-time flag update
    console.log(`Flag updated: ${flagKey} →`, value.state);
  },
  (err) => {
    console.error("Stream error:", err);
  },
);

// Later — disconnect
// disconnect();
```

## Using with OpenFeature

If you need the [OpenFeature](https://openfeature.dev) standard interface (e.g. to stay provider-agnostic), install the peer dependency and use `FlagrProvider`:

```bash
npm install @flagr-dev/sdk @openfeature/server-sdk
```

```ts
import { OpenFeature } from "@openfeature/server-sdk";
import { FlagrProvider } from "@flagr-dev/sdk";

await OpenFeature.setProviderAndWait(
  new FlagrProvider({ sdkKey: "sdk_live_..." })
);

const client = OpenFeature.getClient();
const enabled = await client.getBooleanValue(
  "new-checkout",
  false,
  { targetingKey: "a1b2c3d4-e5f6-7890-abcd-ef1234567890" }
);
```

## Running locally

```bash
npm install
npm run build   # ESM + CJS output via tsup
npm run dev     # watch mode
npm run lint    # type-check
```

## Running tests

```bash
# Unit tests (no server required)
npm test

# Integration tests (requires a running Flagr API + valid SDK key)
FLAGR_ENV_KEY=sdk_live_xxx FLAGR_BASE_URL=http://localhost:8080 npm run test:integration
```

## Releasing a new version

Releases are fully automated via GitLab CI. To publish a new version to npm:

1. Bump the version in `package.json`:
   ```bash
   npm version patch   # or minor / major
   ```

2. Push the tag created by `npm version`:
   ```bash
   git push origin v0.1.1
   ```

   The tag must match the pattern `v*`.

3. GitLab CI runs `.gitlab-ci.yml`, which builds the package and publishes it to npm using the `NPM_TOKEN` variable.

> **Required variable:** `NPM_TOKEN` must be set in GitLab → Settings → CI/CD → Variables with publish access to the `@flagr` npm scope.