Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@harnessio/ff-react-client-sdk

Package Overview
Dependencies
Maintainers
0
Versions
43
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@harnessio/ff-react-client-sdk - npm Package Compare versions

Comparing version 1.13.0 to 1.14.0-rc.0

dist/cjs/context/FFContext.test.d.ts

3

dist/cjs/context/FFContext.d.ts
import { FC, PropsWithChildren, ReactNode } from 'react';
import { Evaluation, Event as FFEvent, Options, Result as InitializeResult, Target } from '@harnessio/ff-javascript-client-sdk';
import { Evaluation, Event as FFEvent, Options, Result as InitializeResult, Target, DefaultVariationEventPayload } from '@harnessio/ff-javascript-client-sdk';
export interface FFContextValue {

@@ -18,3 +18,4 @@ loading: boolean;

onError?: (event: NetworkError | 'PropsError', error?: unknown) => void;
onFlagNotFound?: (flagNotFound: DefaultVariationEventPayload, loading: boolean) => void;
}
export declare const FFContextProvider: FC<FFContextProviderProps>;

@@ -12,6 +12,8 @@ "use strict";

exports.FFContext = (0, react_1.createContext)({});
const FFContextProvider = ({ children, apiKey, target, options = {}, fallback = (0, jsx_runtime_1.jsx)("p", { children: "Loading..." }), async = false, initialEvaluations, onError = () => void 0 }) => {
const FFContextProvider = ({ children, apiKey, target, options = {}, fallback = (0, jsx_runtime_1.jsx)("p", { children: "Loading..." }), async = false, initialEvaluations, onError = () => void 0, onFlagNotFound = () => void 0 }) => {
const [loading, setLoading] = (0, react_1.useState)(true);
const [flags, setFlags] = (0, react_1.useState)({});
const [clientInstance, setClientInstance] = (0, react_1.useState)();
// Use a reference to keep track of the latest loading state so we can use it with event callbacks.
const loadingRef = (0, react_1.useRef)(true);
(0, react_1.useEffect)(() => {

@@ -33,5 +35,7 @@ if (!apiKey) {

setLoading(true);
loadingRef.current = true;
setClientInstance(client);
const onInitialLoad = (newFlags) => {
setLoading(false);
loadingRef.current = false;
setFlags(newFlags);

@@ -54,2 +58,5 @@ client.on(ff_javascript_client_sdk_1.Event.CHANGED, onFlagChange);

};
const onFlagNotFoundListener = ({ flag, defaultVariation }) => {
onFlagNotFound({ flag, defaultVariation }, loadingRef.current);
};
const onAuthError = onNetworkError(ff_javascript_client_sdk_1.Event.ERROR_AUTH);

@@ -66,2 +73,3 @@ const onStreamError = onNetworkError(ff_javascript_client_sdk_1.Event.ERROR_STREAM);

client.on(ff_javascript_client_sdk_1.Event.ERROR_METRICS, onMetricsError);
client.on(ff_javascript_client_sdk_1.Event.ERROR_DEFAULT_VARIATION_RETURNED, onFlagNotFoundListener);
if (initialEvaluations) {

@@ -78,2 +86,3 @@ client.setEvaluations(initialEvaluations);

client.off(ff_javascript_client_sdk_1.Event.ERROR_METRICS, onMetricsError);
client.off(ff_javascript_client_sdk_1.Event.ERROR_DEFAULT_VARIATION_RETURNED, onFlagNotFoundListener);
client.close();

@@ -80,0 +89,0 @@ };

import { FC, PropsWithChildren, ReactNode } from 'react';
import { Evaluation, Event as FFEvent, Options, Result as InitializeResult, Target } from '@harnessio/ff-javascript-client-sdk';
import { Evaluation, Event as FFEvent, Options, Result as InitializeResult, Target, DefaultVariationEventPayload } from '@harnessio/ff-javascript-client-sdk';
export interface FFContextValue {

@@ -18,3 +18,4 @@ loading: boolean;

onError?: (event: NetworkError | 'PropsError', error?: unknown) => void;
onFlagNotFound?: (flagNotFound: DefaultVariationEventPayload, loading: boolean) => void;
}
export declare const FFContextProvider: FC<FFContextProviderProps>;
import { jsx as _jsx } from "react/jsx-runtime";
import { createContext, useEffect, useState } from 'react';
import { createContext, useEffect, useRef, useState } from 'react';
import { Event as FFEvent, initialize } from '@harnessio/ff-javascript-client-sdk';
import omit from 'lodash.omit';
export const FFContext = createContext({});
export const FFContextProvider = ({ children, apiKey, target, options = {}, fallback = _jsx("p", { children: "Loading..." }), async = false, initialEvaluations, onError = () => void 0 }) => {
export const FFContextProvider = ({ children, apiKey, target, options = {}, fallback = _jsx("p", { children: "Loading..." }), async = false, initialEvaluations, onError = () => void 0, onFlagNotFound = () => void 0 }) => {
const [loading, setLoading] = useState(true);
const [flags, setFlags] = useState({});
const [clientInstance, setClientInstance] = useState();
// Use a reference to keep track of the latest loading state so we can use it with event callbacks.
const loadingRef = useRef(true);
useEffect(() => {

@@ -26,5 +28,7 @@ if (!apiKey) {

setLoading(true);
loadingRef.current = true;
setClientInstance(client);
const onInitialLoad = (newFlags) => {
setLoading(false);
loadingRef.current = false;
setFlags(newFlags);

@@ -47,2 +51,5 @@ client.on(FFEvent.CHANGED, onFlagChange);

};
const onFlagNotFoundListener = ({ flag, defaultVariation }) => {
onFlagNotFound({ flag, defaultVariation }, loadingRef.current);
};
const onAuthError = onNetworkError(FFEvent.ERROR_AUTH);

@@ -59,2 +66,3 @@ const onStreamError = onNetworkError(FFEvent.ERROR_STREAM);

client.on(FFEvent.ERROR_METRICS, onMetricsError);
client.on(FFEvent.ERROR_DEFAULT_VARIATION_RETURNED, onFlagNotFoundListener);
if (initialEvaluations) {

@@ -71,2 +79,3 @@ client.setEvaluations(initialEvaluations);

client.off(FFEvent.ERROR_METRICS, onMetricsError);
client.off(FFEvent.ERROR_DEFAULT_VARIATION_RETURNED, onFlagNotFoundListener);
client.close();

@@ -73,0 +82,0 @@ };

{
"name": "@harnessio/ff-react-client-sdk",
"version": "1.13.0",
"version": "1.14.0-rc.0",
"author": "Harness",

@@ -24,3 +24,3 @@ "license": "Apache-2.0",

"dependencies": {
"@harnessio/ff-javascript-client-sdk": "^1.28.0",
"@harnessio/ff-javascript-client-sdk": "^1.29.0",
"lodash.omit": "^4.5.0"

@@ -27,0 +27,0 @@ },

@@ -108,2 +108,35 @@ # React.js Client SDK For Harness Feature Flags

## On Flag Not Found
The `onFlagNotFound` option allows you to handle situations where a default variation is returned.
It includes the flag, variation, and whether the SDK was still initializing (`loading)` when the default was served.
This can happen when:
1. Using `async` mode without `cache` or `initialEvaluations` and where the SDK is still initializing.
2. The flag identifier is incorrect (e.g., due to a typo).
3. The wrong API key is being used, and the expected flags are not available for that project.
```typescript jsx
<FFContextProvider
apiKey="YOUR_API_KEY"
target={{
identifier: 'reactclientsdk',
name: 'ReactClientSDK'
}}
onFlagNotFound={(flagNotFoundPayload, loading) => {
if (loading) {
console.debug(`Flag "${flagNotFound.flag}" not found because the SDK is still initializing. Returned default: ${flagNotFound.defaultVariation}`);
} else {
console.warn(`Flag "${flagNotFound.flag}" not found. Returned default: ${flagNotFound.defaultVariation}`);
}
}}
>
<MyApp />
</FFContextProvider>
```
By using the `onFlagNotFound` prop, your application can be notified whenever a flag is missing and the default variation has been returned.
## Caching evaluations

@@ -110,0 +143,0 @@

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc