Experiment JVM SDK

Official documentation for Amplitude Experiment's server-side JVM SDK implementation. This SDK may be used in either Java or Kotlin server-side implementations.

This documentation has separate sections for remote and local evaluation:

Remote evaluation

Implements fetching variants for a user via remote evaluation.

Install

Install the JVM Server SDK using Gradle.

1implementation "com.amplitude:experiment-jvm-server:<VERSION>"

1implementation("com.amplitude:experiment-jvm-server:<VERSION>")

Quick start

  1. Initialize the experiment client
  2. Fetch variants for the user
  3. Access a flag's variant

1// (1) Initialize the remote evaluation client with a server deployment key.
2val experiment = Experiment.initializeRemote("<DEPLOYMENT_KEY>")
3 
4// (2) Fetch variants for a user
5val user = ExperimentUser.builder()
6 .userId("user@company.com")
7 .deviceId("abcdefg")
8 .userProperty("premium", true)
9 .build()
10val variants = try {
11 experiment.fetch(user).get()
12} catch (e: Exception) {
13 e.printStackTrace()
14 return
15}
16 
17// (3) Access a flag's variant
18val variant = variants["<FLAG_KEY>"]
19if (variant?.value == "on") {
20 // Flag is on
21} else {
22 // Flag is off
23}

1// (1) Initialize the remote evaluation client with a server deployment key.
2RemoteEvaluationClient experiment =
3 Experiment.initializeRemote("<DEPLOYMENT_KEY>");
4 
5// (2) Fetch variants for a user
6ExperimentUser user = ExperimentUser.builder()
7 .userId("user@company.com")
8 .deviceId("abcdefg")
9 .userProperty("premium", true)
10 .build();
11Map<String, Variant> variants;
12try {
13 variants = experiment.fetch(user).get();
14} catch (Exception e) {
15 e.printStackTrace();
16 return;
17}
18 
19// (3) Access a flag's variant
20Variant variant = variants.get("<FLAG_KEY>");
21if (Variant.valueEquals(variant, "on")) {
22 // Flag is on
23} else {
24 // Flag is off
25}

Initialize remote

The SDK client should be initialized in your server on startup. The deployment key argument passed into the apiKey parameter must live within the same project that you are sending analytics events to.

1fun initializeRemote(
2 apiKey: String,
3 config: RemoteEvaluationConfig = RemoteEvaluationConfig()
4): RemoteEvaluationClient

1@Nonnull
2public RemoteEvaluationClient initializeRemote(
3 @Nonnull String apiKey,
4 @Nonnull RemoteEvaluationConfig config
5);

Parameter Requirement Description
apiKey required The deployment key which authorizes fetch requests and determines which flags should be evaluated for the user.
config optional The client configuration used to customize SDK client behavior.

1val experiment = Experiment.initializeRemote("<DEPLOYMENT_KEY>")

1RemoteEvaluationClient experiment = Experiment.initializeRemote("<DEPLOYMENT_KEY>");

Configuration

The SDK client can be configured on initialization.

Name
Description Default Value
debug Set to true to enable debug logging. false
serverUrl The host to fetch flag configurations from. https://api.lab.amplitude.com
fetchTimeoutMillis The timeout for fetching variants in milliseconds. This timeout only applies to the initial request, not subsequent retries 500
fetchRetries The number of retries to attempt if a request to fetch variants fails. 1
fetchRetryBackoffMinMillis The minimum (initial) backoff after a request to fetch variants fails. This delay is scaled by the fetchRetryBackoffScalar 0
fetchRetryBackoffMaxMillis The maximum backoff between retries. If the scaled backoff becomes greater than the max, the max is used for all subsequent requests 10000
fetchRetryBackoffScalar Scales the minimum backoff exponentially. 1
assignmentConfiguration Configuration for automatically tracking assignment events after an evaluation. null

EU data center

If you're using Amplitude's EU data center, configure the serverUrl option on initialization to https://api.lab.eu.amplitude.com

Fetch

Fetches variants for a user and returns the results. This function remote evaluates the user for flags associated with the deployment used to initialize the SDK client.

1fun fetch(user: ExperimentUser): CompletableFuture<Map<String, Variant>>

1@Nonnull
2public CompletableFuture<Map<String, Variant>> fetch(@Nonnull ExperimentUser user);

Parameter Requirement Description
user required The user to remote fetch variants for.

1val user = ExperimentUser.builder()
2 .userId("user@company.com")
3 .deviceId("abcdefg")
4 .userProperty("premium", true)
5 .build()
6val variants = try {
7 experiment.fetch(user).get()
8} catch (e: Exception) {
9 e.printStackTrace()
10 return
11}

1ExperimentUser user = ExperimentUser.builder()
2 .userId("user@company.com")
3 .deviceId("abcdefg")
4 .userProperty("premium", true)
5 .build();
6Map<String, Variant> variants;
7try {
8 variants = experiment.fetch(user).get();
9} catch (Exception e) {
10 e.printStackTrace();
11 return;
12}

After fetching variants for a user, you may to access the variant for a specific flag.

1val variant = variants["<FLAG_KEY>"]
2if (variant?.value == "on") {
3 // Flag is on
4} else {
5 // Flag is off
6}

1Variant variant = variants.get("<FLAG_KEY>");
2if (Variant.valueEquals(variant, "on")) {
3 // Flag is on
4} else {
5 // Flag is off
6}

Local evaluation

Implements evaluating variants for a user via local evaluation. If you plan on using local evaluation, you should understand the tradeoffs.

Install

Install the JVM Server SDK using Gradle.

1implementation "com.amplitude:experiment-jvm-server:<VERSION>"

1implementation("com.amplitude:experiment-jvm-server:<VERSION>")

Quick start

  1. Initialize the local evaluation client.
  2. Start the local evaluation client.
  3. Evaluate a user.

1// (1) Initialize the local evaluation client with a server deployment key.
2val experiment = Experiment.initializeLocal("<DEPLOYMENT_KEY>")
3 
4// (2) Start the local evaluation client.
5experiment.start()
6 
7// (3) Evaluate a user.
8val user = ExperimentUser.builder()
9 .userId("user@company.com")
10 .deviceId("abcdefg")
11 .userProperty("premium", true)
12 .build()
13val variants = experiment.evaluate(user)

1// (1) Initialize the local evaluation client with a server deployment key.
2LocalEvaluationClient experiment = Experiment.initializeLocal("<DEPLOYMENT_KEY>");
3 
4// (2) Start the local evaluation client.
5experiment.start();
6 
7// (3) Evaluate a user.
8ExperimentUser user = ExperimentUser.builder()
9 .userId("user@company.com")
10 .deviceId("abcdefg")
11 .userProperty("premium", true)
12 .build();
13Map<String, Variant> variants = experiment.evaluate(user);

Initialize local

Initializes a local evaluation client.

!!!warning "Server Deployment Key"

Server deployment key

You must initialize the local evaluation client with a server deployment key to get access to local evaluation flag configs.

1fun initializeLocal(
2 apiKey: String,
3 config: LocalEvaluationConfig = LocalEvaluationConfig(),
4): LocalEvaluationClient

1@Nonnull
2public LocalEvaluationClient initializeLocal(
3 @Nonnull String apiKey,
4 @Nonnull LocalEvaluationConfig config
5);

Parameter Requirement Description
apiKey required The server deployment key which authorizes fetch requests and determines which flags should be evaluated for the user.
config optional The client configuration used to customize SDK client behavior.

Flag polling interval

Use the flagConfigPollingIntervalMillis configuration to determine the time flag configs take to update once modified (default 30s).

Configuration

You can configure the SDK client on initialization.

LocalEvaluationConfig

Name
Description Default Value
debug Set to true to enable debug logging. false
serverUrl The host to fetch flag configurations from. https://api.lab.amplitude.com
flagConfigPollingIntervalMillis The interval to poll for updated flag configs after calling Start() 30000
flagConfigPollerRequestTimeoutMillis The timeout for the request made by the flag config poller 10000

AssignmentConfiguration

Name
Description Default Value
api_key The analytics API key and NOT the experiment deployment key required
cache_capacity The maximum number of assignments stored in the assignment cache 65536
eventUploadThreshold setEventUploadThreshold() in the underlying Analytics SDK 10
eventUploadPeriodMillis setEventUploadPeriodMillis() in the underlying Analytics SDK 10000
useBatchMode useBatchMode() in the underlying Analytics SDK true

EU data center

If you're using Amplitude's EU data center, configure the serverUrl option on initialization to https://api.lab.eu.amplitude.com

Start

Start the local evaluation client, pre-fetching local evaluation mode flag configs for evaluation and starting the flag config poller at the configured interval.

1fun start()

1public void start();

You should wait for start() to return before calling evaluate() to ensure that flag configs are available for use in evaluation.

Evaluate

Executes the evaluation logic using the flags pre-fetched on start(). Evaluate must be given a user object argument and can optionally be passed an array of flag keys if only a specific subset of required flag variants are required.

!!!tip "Automatic Assignment Tracking"

Automatic assignment tracking

Set assignmentConfiguration to automatically track an assignment event to Amplitude when evaluate() is called.

1fun evaluate(user: ExperimentUser, flagKeys: List<String> = listOf()): Map<String, Variant>

1@Nonnull
2public Map<String, Variant> evaluate(@Nonnull experimentUser, @Nonnull List<String> flagKeys);

Parameter Requirement Description
user required The user to evaluate.
flagKeys optional Specific flags or experiments to evaluate. If empty, all flags and experiments are evaluated.

1// The user to evaluate
2val user = ExperimentUser.builder()
3 .userId("user@company.com")
4 .deviceId("abcdefg")
5 .userProperty("premium", true)
6 .build()
7 
8// Evaluate all flag variants
9val allVariants = experiment.evaluate(user)
10 
11// Evaluate a specific subset of flag variants
12val specificVariants = experiment.evaluate(user, listOf(
13 "<FLAG_KEY_1>",
14 "<FLAG_KEY_2>",
15))
16 
17// Access a variant
18val variant = allVariants["<FLAG_KEY>"]
19if (variant?.value == "on") {
20 // Flag is on
21} else {
22 // Flag is off
23}

1// The user to evaluate
2ExperimentUser user = ExperimentUser.builder()
3 .userId("user@company.com")
4 .deviceId("abcdefg")
5 .userProperty("premium", true)
6 .build();
7 
8// Evaluate all flag variants
9Map<String, Variant> allVariants = experiment.evaluate(user);
10 
11// Evaluate a specific subset of flag variants
12Map<String, Variant> specificVariants = experiment.evaluate(user,
13 List.of("<FLAG_KEY_1>", "<FLAG_KEY_2>"));
14 
15// Access a variant
16Variant variant = allVariants.get("<FLAG_KEY>");
17if (Variant.valueEquals(variant, "on")) {
18 // Flag is on
19} else {
20 // Flag is off
21}

Was this page helpful?

Thanks for your feedback!

June 4th, 2024

Need help? Contact Support

Visit Amplitude.com

Have a look at the Amplitude Blog

Learn more at Amplitude Academy

© 2024 Amplitude, Inc. All rights reserved. Amplitude is a registered trademark of Amplitude, Inc.