@coframe/sdk 1.1.22 → 1.1.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +163 -0
- package/dist/pkg/cf.cjs.js +336 -53
- package/dist/pkg/cf.esm.mjs +336 -53
- package/dist/pkg/feature-flags.cjs.js +623 -0
- package/dist/pkg/feature-flags.esm.mjs +609 -0
- package/dist/pkg/react.cjs.js +36 -1
- package/dist/pkg/react.esm.mjs +32 -2
- package/dist/pkg/server.cjs.js +75 -0
- package/dist/pkg/server.esm.mjs +70 -1
- package/dist/pkg/types/feature-flags.d.ts +75 -0
- package/dist/pkg/types/index.d.ts +2 -0
- package/dist/pkg/types/react.d.ts +24 -1
- package/dist/pkg/types/server.d.ts +53 -2
- package/package.json +6 -1
package/README.md
CHANGED
|
@@ -65,6 +65,12 @@ only has to forward `<ingestUrl>/*` to `https://ingest.app.coframe.com/ingest/v2
|
|
|
65
65
|
with the path unchanged. Both overrides are optional and retain the compiled
|
|
66
66
|
Coframe endpoints when omitted.
|
|
67
67
|
|
|
68
|
+
Configuring either `projectUrl` or `ingestUrl` makes CMAB experiments use
|
|
69
|
+
deterministic local assignment without calling the Edge assignment API.
|
|
70
|
+
Configure both overrides when the browser must avoid the SDK-compiled Coframe
|
|
71
|
+
project and ingest endpoints entirely. Debug tools remain controlled by
|
|
72
|
+
`enableDebug`.
|
|
73
|
+
|
|
68
74
|
### URL controls
|
|
69
75
|
|
|
70
76
|
The npm entry uses the same browser URL controls as the script-tag and Edge
|
|
@@ -130,6 +136,148 @@ const projectData = serverData?.project
|
|
|
130
136
|
|
|
131
137
|
Pass `projectData` into `<CoframeProvider>` to avoid the extra client-side project fetch and personalize on first paint.
|
|
132
138
|
|
|
139
|
+
## Feature flags and remote config
|
|
140
|
+
|
|
141
|
+
Browser Feature Flags use the existing public `projectId` and receive only
|
|
142
|
+
flags marked **Public**. `selector` is optional; use `names` for
|
|
143
|
+
individual flag keys and `groups` to evaluate every flag assigned to a page or
|
|
144
|
+
business area.
|
|
145
|
+
|
|
146
|
+
```ts
|
|
147
|
+
import { setUserToken } from '@coframe/sdk'
|
|
148
|
+
import {
|
|
149
|
+
featureFlags,
|
|
150
|
+
getFeatureFlag,
|
|
151
|
+
getFeatureFlagPayload,
|
|
152
|
+
isFeatureEnabled,
|
|
153
|
+
onFeatureFlags,
|
|
154
|
+
} from '@coframe/sdk/feature-flags'
|
|
155
|
+
|
|
156
|
+
setUserToken('customer-123')
|
|
157
|
+
|
|
158
|
+
await featureFlags.init({
|
|
159
|
+
projectId: 'your-project-id',
|
|
160
|
+
selector: {
|
|
161
|
+
names: ['checkout-redesign'],
|
|
162
|
+
groups: ['homepage_campaigns'],
|
|
163
|
+
},
|
|
164
|
+
})
|
|
165
|
+
|
|
166
|
+
onFeatureFlags(() => {
|
|
167
|
+
if (isFeatureEnabled('checkout-redesign')) {
|
|
168
|
+
showNewCheckout()
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const content = getFeatureFlagPayload('homepage-content')
|
|
172
|
+
const checkoutVariant = getFeatureFlag('checkout-layout')
|
|
173
|
+
})
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
Feature Flags are a separate browser entry point and do not increase or initialize
|
|
177
|
+
the main SDK bundle. When both clients are used, Feature Flags reuse the latest
|
|
178
|
+
`setUserToken()` command from Coframe's shared command queue and follow later
|
|
179
|
+
identity changes automatically.
|
|
180
|
+
|
|
181
|
+
Loading does not delay Coframe page modification. Synchronous getters return
|
|
182
|
+
`undefined` until a cached or fresh evaluation is available. The browser client
|
|
183
|
+
always keeps the latest successful response in memory. Before consent, no
|
|
184
|
+
Feature Flag result or evaluation context is persisted. After consent, the
|
|
185
|
+
client also caches the response in `localStorage` for five minutes and keys it
|
|
186
|
+
with an opaque SHA-256 fingerprint derived from the user token and evaluation
|
|
187
|
+
context. It can fall back to that persistent cache if Edge is temporarily
|
|
188
|
+
unavailable. Call `reloadFeatureFlags()` to request fresh evaluations
|
|
189
|
+
explicitly.
|
|
190
|
+
|
|
191
|
+
Payloads support any JSON value up to 32 KB. A payload is returned only when its
|
|
192
|
+
flag is enabled. Remote Config uses the same transport and payload API and
|
|
193
|
+
returns the same payload to all users while active:
|
|
194
|
+
|
|
195
|
+
```ts
|
|
196
|
+
import { getRemoteConfig } from '@coframe/sdk/feature-flags'
|
|
197
|
+
|
|
198
|
+
const navigation = getRemoteConfig('navigation-config')
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
Multivariate flags return a stable variant key from `getFeatureFlag()`. Their
|
|
202
|
+
weights divide users into deterministic buckets, and each variant can carry an
|
|
203
|
+
independent optional payload. `isFeatureEnabled()` remains a boolean
|
|
204
|
+
convenience and returns `true` whenever a variant is assigned:
|
|
205
|
+
|
|
206
|
+
```ts
|
|
207
|
+
import {
|
|
208
|
+
getFeatureFlag,
|
|
209
|
+
getFeatureFlagPayload,
|
|
210
|
+
isFeatureEnabled,
|
|
211
|
+
} from '@coframe/sdk/feature-flags'
|
|
212
|
+
|
|
213
|
+
const variant = getFeatureFlag('checkout-layout')
|
|
214
|
+
const config = getFeatureFlagPayload('checkout-layout')
|
|
215
|
+
const enabled = isFeatureEnabled('checkout-layout')
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
React apps can read evaluated values from the existing provider:
|
|
219
|
+
|
|
220
|
+
```tsx
|
|
221
|
+
import {
|
|
222
|
+
useFeatureFlag,
|
|
223
|
+
useFeatureFlagEnabled,
|
|
224
|
+
useFeatureFlagPayload,
|
|
225
|
+
useFeatureFlagVariantKey,
|
|
226
|
+
} from '@coframe/sdk/react'
|
|
227
|
+
|
|
228
|
+
function Checkout() {
|
|
229
|
+
const enabled = useFeatureFlag('checkout-redesign')
|
|
230
|
+
const payload = useFeatureFlagPayload('checkout-redesign')
|
|
231
|
+
|
|
232
|
+
if (enabled === undefined) return <CheckoutSkeleton />
|
|
233
|
+
return enabled ? <NewCheckout config={payload} /> : <OldCheckout />
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
function CheckoutLayout() {
|
|
237
|
+
const variant = useFeatureFlagVariantKey('checkout-layout')
|
|
238
|
+
const enabled = useFeatureFlagEnabled('checkout-layout')
|
|
239
|
+
const payload = useFeatureFlagPayload('checkout-layout')
|
|
240
|
+
return <Checkout variant={variant} enabled={enabled} config={payload} />
|
|
241
|
+
}
|
|
242
|
+
```
|
|
243
|
+
|
|
244
|
+
For server and edge runtimes, use a secret Feature Flags Server API key. It is
|
|
245
|
+
project-scoped, can read **Private** flags, and must never be included in a
|
|
246
|
+
browser bundle or a `NEXT_PUBLIC_*` environment variable. Each single-key
|
|
247
|
+
helper sends a key-filtered request and fails closed unless a `defaultValue` is
|
|
248
|
+
supplied. Browser and server helpers both call `/api/v1/flags`; server helpers
|
|
249
|
+
include the API key as a Bearer credential so the response may include both
|
|
250
|
+
**Public** and **Private** flags:
|
|
251
|
+
|
|
252
|
+
```ts
|
|
253
|
+
import {
|
|
254
|
+
evaluateFlags,
|
|
255
|
+
getFeatureFlag,
|
|
256
|
+
getRemoteConfig,
|
|
257
|
+
isFeatureEnabled,
|
|
258
|
+
} from '@coframe/sdk/server'
|
|
259
|
+
|
|
260
|
+
const options = {
|
|
261
|
+
projectId: 'your-project-id',
|
|
262
|
+
apiKey: process.env.COFRAME_FEATURE_FLAGS_SERVER_KEY!,
|
|
263
|
+
userToken: user.id,
|
|
264
|
+
currentUrl: request.url,
|
|
265
|
+
userContext: { plan: user.plan },
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
const checkoutFlags = await evaluateFlags({
|
|
269
|
+
...options,
|
|
270
|
+
selector: { groups: ['cart_checkout'] },
|
|
271
|
+
})
|
|
272
|
+
|
|
273
|
+
const enabled = await isFeatureEnabled('checkout-redesign', {
|
|
274
|
+
...options,
|
|
275
|
+
defaultValue: false,
|
|
276
|
+
})
|
|
277
|
+
const variant = await getFeatureFlag('checkout-layout', options)
|
|
278
|
+
const content = await getRemoteConfig('homepage-content', options)
|
|
279
|
+
```
|
|
280
|
+
|
|
133
281
|
## Common React usage
|
|
134
282
|
|
|
135
283
|
### Read variants in components
|
|
@@ -253,9 +401,21 @@ Modern resolution modes handle package subpath exports more reliably.
|
|
|
253
401
|
- `onTreatmentApplied(...)`
|
|
254
402
|
- `onLog(...)`
|
|
255
403
|
|
|
404
|
+
### `@coframe/sdk/feature-flags`
|
|
405
|
+
|
|
406
|
+
- `featureFlags.init(options)`
|
|
407
|
+
- `featureFlags.setUserToken(userToken)` / `featureFlags.reset()`
|
|
408
|
+
- `featureFlags.getUserToken()`
|
|
409
|
+
- `getFeatureFlag(key)` / `isFeatureEnabled(key)`
|
|
410
|
+
- `getFeatureFlagPayload(key)` / `getRemoteConfig(key)`
|
|
411
|
+
- `onFeatureFlags(callback)` / `reloadFeatureFlags()`
|
|
412
|
+
|
|
256
413
|
### `@coframe/sdk/server`
|
|
257
414
|
|
|
258
415
|
- `getProjectData(options)`
|
|
416
|
+
- `evaluateFlags(options)`
|
|
417
|
+
- `getFeatureFlag(key, options)` / `isFeatureEnabled(key, options)`
|
|
418
|
+
- `getFeatureFlagPayload(key, options)` / `getRemoteConfig(key, options)`
|
|
259
419
|
|
|
260
420
|
Returns a payload that may include:
|
|
261
421
|
|
|
@@ -269,3 +429,6 @@ Returns a payload that may include:
|
|
|
269
429
|
- `useCoframeTreatments()`
|
|
270
430
|
- `useCoframeTreatment(experimentId)`
|
|
271
431
|
- `useCoframeVariant(experimentId)`
|
|
432
|
+
- `useFeatureFlag(key)` / `useFeatureFlagVariantKey(key)`
|
|
433
|
+
- `useFeatureFlagEnabled(key)`
|
|
434
|
+
- `useFeatureFlagResult(key)` / `useFeatureFlagPayload(key)`
|