SDKs
React
@nanoflags/sdk/react, built on useSyncExternalStore: components re-render when a new revision arrives or the client status changes. Evaluation stays local.On this page
Set up the provider
Create the client once, outside components, and pass it with the evaluation context to NanoFlagsProvider.
import { createClient } from "@nanoflags/sdk";
import { NanoFlagsProvider } from "@nanoflags/sdk/react";
const client = createClient({ sdkKey: "nf_pub_…", baseUrl: "https://edge.nanoflags.io", service: "web" });
export function App({ user }: { user: { id: string; plan: string } }) {
return (
<NanoFlagsProvider client={client} context={{ key: user.id, plan: user.plan }}>
<Search />
</NanoFlagsProvider>
);
}| Prop | Description |
|---|---|
client | A client from createClient. |
context | Evaluation context shared by every useFlag below the provider. Compared by value (serialized), so a new object with the same content does not re-evaluate. |
nf_pub_…) in browser code. Client keys receive only client-exposed flags, and their rules are readable by anyone with the page.useFlag
import { useFlag } from "@nanoflags/sdk/react";
function Search() {
const ranking = useFlag("search-ranking", "relevance-v2"); // string
const compact = useFlag("compact-results", false, { device: "mobile" }); // boolean, context override
const limits = useFlag("result-limits", { page: 20 }); // json
…
}- The accessor is chosen from the type of the fallback: boolean, string, number, otherwise JSON.
- The optional third argument is shallow-merged over the provider context for this call.
- A missing flag, no bundle yet, or a type mismatch returns the fallback.
useFlaganduseFlagsStatusthrow if used outsideNanoFlagsProvider.
useFlagsStatus
const { status, revision, hasBundle } = useFlagsStatus();
// status: "not-ready" | "ready" | "stale"; hasBundle: status !== "not-ready"Use it to show a neutral state while nothing is loaded, or to surface that the configuration in use is not known to be current. See Status.
Server rendering
Until a bundle is loaded the hooks return fallbacks. To make the first client render match the server, evaluate on the server with a server client and pass the client view of the bundle to the browser client as bootstrap. Never send a server key's full bundle to the browser if it contains flags that are not client-exposed: fetch the bootstrap bundle with a client key, or embed one fetched at build time.
// browser
const client = createClient({ sdkKey: "nf_pub_…", baseUrl: "https://edge.nanoflags.io", bootstrap: bundleFromServer });A bootstrap bundle is trusted as given (it is not signature-checked); the client then revalidates with the edge as usual.
Test sessions in the browser
client.useSession(token) routes the client's own accessors, and therefore every hook, through a test session for this tab. The token is kept in sessionStorage; useSession(null) leaves the session.
await client.useSession(tokenFromYourTestTooling); // nf_ts_…
fetch("/api/cart", { headers: { ...client.sessionHeaders() } }); // your backend joins the session