@@ -4,43 +4,45 @@ import * as Sentry from '@sentry/browser';
44import type { Client as SentryClient , Event , EventHint , IntegrationFn } from '@sentry/types' ;
55import type { LDContext , LDEvaluationDetail , LDInspectionFlagUsedHandler } from 'launchdarkly-js-client-sdk' ;
66import type { LaunchDarklyOptions } from '../types' ;
7+ import { insertToFlagBuffer } from '@sentry/utils' ;
78
89/**
910 * Sentry integration for capturing feature flags from LaunchDarkly.
1011 *
1112 * See the [feature flag documentation](TODO:) for more information.
1213 *
1314 * @example
14- *
1515 * ```
16- * TODO:
17- * Sentry.init({
18- * dsn: '__DSN__',
19- * integrations: [Sentry.replayIntegration ()],
20- * } );
16+ * import {SentryInspector, launchDarklyIntegration} from '@sentry/launchdarkly';
17+ * import {LDClient} from 'launchdarkly-js-client-sdk';
18+ *
19+ * Sentry.init(..., integrations: [launchDarklyIntegration ()])
20+ * const ldClient = LDClient.initialize(..., inspectors: [SentryInspector] );
2121 * ```
2222 */
2323export const launchDarklyIntegration = ( ( _options ?: LaunchDarklyOptions ) => {
2424 return {
2525 name : 'launchdarkly' ,
2626
2727 processEvent ( event : Event , _hint : EventHint , _client : SentryClient ) : Event {
28- const scope = Sentry . getCurrentScope ( ) ; // client doesn't have getCurrentScope
29- const flagContext = { values : scope . getFlags ( ) } ;
30- if ( event . contexts ) {
31- event . contexts . flags = flagContext ;
32- } else {
33- event . contexts = { flags : flagContext } ;
28+ const scope = Sentry . getCurrentScope ( ) ;
29+ const flagContext = scope . getScopeData ( ) . contexts . flags ;
30+
31+ if ( event . contexts === undefined ) {
32+ event . contexts = { } ;
3433 }
34+ event . contexts . flags = flagContext ;
3535 return event ;
3636 } ,
3737 } ;
3838} ) satisfies IntegrationFn ;
3939
4040/**
4141 * LaunchDarkly hook that listens for flag evaluations and updates the
42- * flagBuffer in our current scope
43- * TODO: finalize docstring
42+ * flagBuffer in our current scope.
43+ *
44+ * This needs to be registered separately in the LDClient, after initializing
45+ * Sentry.
4446 */
4547export class SentryInspector implements LDInspectionFlagUsedHandler {
4648 public name = 'sentry-flag-auditor' ;
@@ -51,11 +53,16 @@ export class SentryInspector implements LDInspectionFlagUsedHandler {
5153 public synchronous = false ;
5254
5355 /**
54- * TODO: docstring
56+ * Handle a flag evaluation by storing its name and value on the current scope.
5557 */
5658 public method ( flagKey : string , flagDetail : LDEvaluationDetail , _context : LDContext ) : void {
5759 if ( typeof flagDetail . value === 'boolean' ) {
58- Sentry . getCurrentScope ( ) . insertFlag ( flagKey , flagDetail . value ) ;
60+ const scopeContexts = Sentry . getCurrentScope ( ) . getScopeData ( ) . contexts ;
61+ if ( ! scopeContexts . flags ) {
62+ scopeContexts . flags = { values : [ ] }
63+ }
64+ const flagBuffer = scopeContexts . flags . values ;
65+ insertToFlagBuffer ( flagBuffer , flagKey , flagDetail . value ) ;
5966 }
6067 return ;
6168 }
0 commit comments