Skip to content

feat: Add test harness support for flag change listeners in Client SDKs#320

Draft
aaron-zeisler wants to merge 10 commits intofeat/fdv2from
aaronz/flag-change-listener-tests-for-client-sdks
Draft

feat: Add test harness support for flag change listeners in Client SDKs#320
aaron-zeisler wants to merge 10 commits intofeat/fdv2from
aaronz/flag-change-listener-tests-for-client-sdks

Conversation

@aaron-zeisler
Copy link
Copy Markdown

@aaron-zeisler aaron-zeisler commented Feb 24, 2026

This pull request is part of a larger set of PRs that implement Flag Change Listener tests for both the server SDKs and the client SDKs. Here's the list of pull requests that I currently have open:

Requirements

  • I have added test coverage for new or changed functionality
  • I have followed the repository's pull request submission guidelines
  • I have validated my changes against all supported platform versions

Related issues

Provide links to any issues in this repository or elsewhere relating to this pull request.

Describe the solution you've provided

Provide a clear and concise description of what you expect to happen.

Describe alternatives you've considered

Provide a clear and concise description of any alternative solutions or features you've considered.

Additional context

Add any other context about the pull request here.

aaron-zeisler and others added 10 commits February 23, 2026 15:09
I performed some research to understand the problem better, and to
come up with some ideas for how to implement these types of tests.

This is the research that I performed:
* What are flag change listeners?
* How are they implemented in some of our SDKs?
* How are other features tested using the SDK test harness?
* What would it take to support tests for change listeners?
Added the "flag-change-listeners" capability constant to service_params.go
and documented it in service_spec.md. This capability indicates that an SDK
supports registering listeners for flag changes and can notify the test
harness via callbacks.

The capability supports testing both general flag change listeners
(notified on any flag configuration change) and flag value change
listeners (notified when a specific flag's evaluated value changes for
a given context).
Define the command constants and parameter structs needed for the
test harness to instruct SDK test services to register and unregister
flag change listeners at runtime.

Three new commands are added to servicedef/command_params.go:

- registerFlagChangeListener: registers a general flag change listener
  that notifies when any flag's configuration changes. Params include
  a listener ID, an optional flag key to filter on, and a callback URI
  where the test service will POST notifications.

- registerFlagValueChangeListener: registers a value-specific listener
  that notifies when a flag's evaluated value changes for a given
  context. Params include a listener ID, flag key, evaluation context,
  default value, and callback URI.

- unregisterListener: removes a previously registered listener by ID.

Unlike existing commands (evaluate, migrate, etc.), these commands are
stateful — the test service must maintain a map of active listeners
between commands. This is the first example of dynamic, post-init
registration in the test service protocol.

Co-authored-by: Cursor <cursoragent@cursor.com>
Define the callback infrastructure needed for flag change listener tests:

- servicedef/command_params.go: add ListenerNotification, the JSON payload
  POSTed by the SDK test service to the callback URI when a listener fires.
  OldValue/NewValue are present only for value change notifications.

- mockld/listener_callback_service.go: add ListenerCallbackService, a mock
  HTTP endpoint that receives POSTed notifications and delivers them to a
  Go channel for consumption by tests. Mirrors HookCallbackService.

- sdktests/testapi_listeners.go: add ListenerCallback, the test API layer
  wrapping ListenerCallbackService with three assertion helpers:
  ExpectFlagChangeNotification, ExpectValueChangeNotification, and
  ExpectNoNotification.

Co-authored-by: Cursor <cursoragent@cursor.com>
Add three methods to SDKClient in sdktests/testapi_sdk_client.go:

- RegisterFlagChangeListener: sends a registerFlagChangeListener command
  to the test service, registering a listener for general flag config
  changes on an optional specific flag key.

- RegisterFlagValueChangeListener: sends a registerFlagValueChangeListener
  command, registering a listener for evaluated value changes for a
  specific flag key and context.

- UnregisterListener: sends an unregisterListener command to remove a
  previously registered listener by ID.

All three follow the existing SDKClient command pattern: a single params
struct argument, SendCommandWithParams, and nil response (registration
and unregistration produce no response body).

Co-authored-by: Cursor <cursoragent@cursor.com>
Expand the listener test suite with additional coverage for both listener
types. For general flag change listeners: verify that notifications fire on
any configuration change (not only value changes), and that registering
with an empty flag key subscribes to changes for all flags. For value
change listeners: verify that multiple independent listeners for the same
flag both receive notifications, and that listener notifications are scoped
to the specific evaluation context they were registered with.

Co-authored-by: Cursor <cursoragent@cursor.com>
I performed some research about two scenarios that I'd like to
create test cases for:
* Is the change listener fired when the Identify action is taken?
* Is the change listener fired when a stale version of a flag or
  a stale version of the data is reported?

I've captured my findings in a couple .md files. I don't expect
these will be committed to the main branch: they're just for my
reference.
While researching specific test cases, I found that all of the
code I'd written so far only works on server-side SDKs. I want
these tests to work for client-side SDKs as well. This commit
updates my development plan to include the work for testing client-
side SDKs.
Converts the standalone functions in common_tests_listeners.go to
methods on a new CommonListenerTests struct that embeds commonTestsBase.
No test logic or behavior changes; all eight existing tests pass
unchanged against the Go Server SDK.

The struct pattern (also used by CommonStreamingTests, CommonEventTests,
etc.) gives the listener tests SDK-kind awareness via isClientSide and
sdkKind, and ensures createClient uses baseSDKConfigurationPlus so that
client-side configurers (e.g. WithClientSideInitialContext) are
automatically included. This is the prerequisite for a follow-up commit
that extends the tests to client-side SDKs.
- Make CommonListenerTests SDK-kind-aware: createClient builds
  ClientSDKData for client-side SDKs and pushFlagUpdate serialises
  ClientSDKFlagWithKey instead of a full FeatureFlag model.

- Add setupListenerDataSystems, which always forces a streaming
  synchronizer (so pushFlagUpdate can push SSE updates). For JS-based
  SDKs, the streaming SDKDataSystem is applied first and a polling
  synchronizer is appended with WithPollingSynchronizer rather than via
  a second SDKDataSystem (which would overwrite the streaming URL).

- Gate flagChangeListenerFiresOnConfigChange and
  valueListenerIsContextSpecific with RequireCapability(CapabilityServerSide):
  client-side SDKs receive pre-evaluated values and evaluate for a
  single fixed context, so these tests do not apply.

- Re-enable doCommonListenerTests in doAllClientSideTests now that the
  shared tests are SDK-kind-aware.

- Fix client-side polling to serve FDv1 flat-flag-map format rather
  than the FDv2 PollingPayload envelope; client-side SDKs parse the
  polling response through their streaming put handler which expects the
  simpler format.
@aaron-zeisler aaron-zeisler changed the title feat: Flag Change Listener Tests for Client SDKs feat: Add test harness support for flag change listeners in Server SDKs Feb 24, 2026
@aaron-zeisler aaron-zeisler force-pushed the aaronz/flag-change-listener-tests branch from 35a6b80 to f19469f Compare February 24, 2026 23:32
Base automatically changed from aaronz/flag-change-listener-tests to feat/fdv2 March 2, 2026 18:56
@aaron-zeisler aaron-zeisler changed the title feat: Add test harness support for flag change listeners in Server SDKs feat: Add test harness support for flag change listeners in Client SDKs Mar 5, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant