Skip to content
This repository was archived by the owner on May 30, 2024. It is now read-only.

Commit cc1cccd

Browse files
LaunchDarklyReleaseBoteli-darklyLaunchDarklyReleaseBotaengelbergantonmos
authored
prepare 7.1.0 release (#318)
## [7.1.0] - 2023-11-02 ### Added: - Added an improved way of setting wrapper information for wrapper SDKs. This functionality is primarily intended for use by LaunchDarkly while developing wrapper SDKs. --------- Co-authored-by: Eli Bishop <[email protected]> Co-authored-by: LaunchDarklyReleaseBot <[email protected]> Co-authored-by: Alex Engelberg <[email protected]> Co-authored-by: Anton Mostovoy <[email protected]> Co-authored-by: LaunchDarklyCI <[email protected]> Co-authored-by: LaunchDarklyCI <[email protected]> Co-authored-by: Gavin Whelan <[email protected]> Co-authored-by: ssrm <[email protected]> Co-authored-by: Harpo Roeder <[email protected]> Co-authored-by: Ben Woskow <[email protected]> Co-authored-by: Elliot <[email protected]> Co-authored-by: Robert J. Neal <[email protected]> Co-authored-by: Robert J. Neal <[email protected]> Co-authored-by: Sam Stokes <[email protected]> Co-authored-by: Ember Stevens <[email protected]> Co-authored-by: ember-stevens <[email protected]> Co-authored-by: Alex Engelberg <[email protected]> Co-authored-by: Louis Chan <[email protected]> Co-authored-by: Louis Chan <[email protected]> Co-authored-by: Todd Anderson <[email protected]> Co-authored-by: tanderson-ld <[email protected]> Co-authored-by: Matthew M. Keeler <[email protected]> Co-authored-by: ld-repository-standards[bot] <113625520+ld-repository-standards[bot]@users.noreply.github.com> Co-authored-by: Kane Parkinson <[email protected]> Co-authored-by: Ryan Lamb <[email protected]>
1 parent 325c82e commit cc1cccd

File tree

12 files changed

+403
-33
lines changed

12 files changed

+403
-33
lines changed

Diff for: src/main/java/com/launchdarkly/sdk/server/ClientContextImpl.java

+4-4
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ private ClientContextImpl(
3737
) {
3838
super(baseContext.getSdkKey(), baseContext.getApplicationInfo(), baseContext.getHttp(),
3939
baseContext.getLogging(), baseContext.isOffline(), baseContext.getServiceEndpoints(),
40-
baseContext.getThreadPriority());
40+
baseContext.getThreadPriority(), baseContext.getWrapperInfo());
4141
this.sharedExecutor = sharedExecutor;
4242
this.diagnosticStore = diagnosticStore;
4343
this.dataSourceUpdateSink = null;
@@ -80,11 +80,11 @@ static ClientContextImpl fromConfig(
8080
ScheduledExecutorService sharedExecutor
8181
) {
8282
ClientContext minimalContext = new ClientContext(sdkKey, config.applicationInfo, null,
83-
null, config.offline, config.serviceEndpoints, config.threadPriority);
83+
null, config.offline, config.serviceEndpoints, config.threadPriority, config.wrapperInfo);
8484
LoggingConfiguration loggingConfig = config.logging.build(minimalContext);
8585

8686
ClientContext contextWithLogging = new ClientContext(sdkKey, config.applicationInfo, null,
87-
loggingConfig, config.offline, config.serviceEndpoints, config.threadPriority);
87+
loggingConfig, config.offline, config.serviceEndpoints, config.threadPriority, config.wrapperInfo);
8888
HttpConfiguration httpConfig = config.http.build(contextWithLogging);
8989

9090
if (httpConfig.getProxy() != null) {
@@ -94,7 +94,7 @@ static ClientContextImpl fromConfig(
9494
}
9595

9696
ClientContext contextWithHttpAndLogging = new ClientContext(sdkKey, config.applicationInfo, httpConfig,
97-
loggingConfig, config.offline, config.serviceEndpoints, config.threadPriority);
97+
loggingConfig, config.offline, config.serviceEndpoints, config.threadPriority, config.wrapperInfo);
9898

9999
// Create a diagnostic store only if diagnostics are enabled. Diagnostics are enabled as long as 1. the
100100
// opt-out property was not set in the config, and 2. we are using the standard event processor.

Diff for: src/main/java/com/launchdarkly/sdk/server/Components.java

+12
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
import com.launchdarkly.sdk.server.ComponentsImpl.PollingDataSourceBuilderImpl;
1313
import com.launchdarkly.sdk.server.ComponentsImpl.ServiceEndpointsBuilderImpl;
1414
import com.launchdarkly.sdk.server.ComponentsImpl.StreamingDataSourceBuilderImpl;
15+
import com.launchdarkly.sdk.server.ComponentsImpl.WrapperInfoBuilderImpl;
1516
import com.launchdarkly.sdk.server.integrations.ApplicationInfoBuilder;
1617
import com.launchdarkly.sdk.server.integrations.BigSegmentsConfigurationBuilder;
1718
import com.launchdarkly.sdk.server.integrations.EventProcessorBuilder;
@@ -21,6 +22,7 @@
2122
import com.launchdarkly.sdk.server.integrations.PollingDataSourceBuilder;
2223
import com.launchdarkly.sdk.server.integrations.ServiceEndpointsBuilder;
2324
import com.launchdarkly.sdk.server.integrations.StreamingDataSourceBuilder;
25+
import com.launchdarkly.sdk.server.integrations.WrapperInfoBuilder;
2426
import com.launchdarkly.sdk.server.interfaces.HttpAuthentication;
2527
import com.launchdarkly.sdk.server.subsystems.BigSegmentStore;
2628
import com.launchdarkly.sdk.server.subsystems.ComponentConfigurer;
@@ -420,4 +422,14 @@ public static ApplicationInfoBuilder applicationInfo() {
420422
public static ServiceEndpointsBuilder serviceEndpoints() {
421423
return new ServiceEndpointsBuilderImpl();
422424
}
425+
426+
/**
427+
* Returns a wrapper information builder.
428+
* <p>
429+
* This is intended for use by LaunchDarkly in the development of wrapper SDKs.
430+
*
431+
* @return a builder object
432+
* @since 7.1.0
433+
*/
434+
public static WrapperInfoBuilder wrapperInfo() { return new WrapperInfoBuilderImpl(); }
423435
}

Diff for: src/main/java/com/launchdarkly/sdk/server/ComponentsImpl.java

+46-2
Original file line numberDiff line numberDiff line change
@@ -21,9 +21,11 @@
2121
import com.launchdarkly.sdk.server.integrations.PollingDataSourceBuilder;
2222
import com.launchdarkly.sdk.server.integrations.ServiceEndpointsBuilder;
2323
import com.launchdarkly.sdk.server.integrations.StreamingDataSourceBuilder;
24+
import com.launchdarkly.sdk.server.integrations.WrapperInfoBuilder;
2425
import com.launchdarkly.sdk.server.interfaces.DataSourceStatusProvider;
2526
import com.launchdarkly.sdk.server.interfaces.HttpAuthentication;
2627
import com.launchdarkly.sdk.server.interfaces.ServiceEndpoints;
28+
import com.launchdarkly.sdk.server.interfaces.WrapperInfo;
2729
import com.launchdarkly.sdk.server.subsystems.ClientContext;
2830
import com.launchdarkly.sdk.server.subsystems.ComponentConfigurer;
2931
import com.launchdarkly.sdk.server.subsystems.DataSource;
@@ -342,8 +344,24 @@ public HttpConfiguration build(ClientContext clientContext) {
342344
headers.put("X-LaunchDarkly-Tags", tagHeader);
343345
}
344346
}
345-
if (wrapperName != null) {
346-
String wrapperId = wrapperVersion == null ? wrapperName : (wrapperName + "/" + wrapperVersion);
347+
348+
String wrapperNameToUse = null;
349+
String wrapperVersionToUse = null;
350+
351+
WrapperInfo wrapperInfo = clientContext.getWrapperInfo();
352+
// If information from wrapperInfo is available, then it overwrites that from the http properties
353+
// builder.
354+
if(wrapperInfo != null) {
355+
wrapperNameToUse = wrapperInfo.getWrapperName();
356+
wrapperVersionToUse = wrapperInfo.getWrapperVersion();
357+
}
358+
else if (wrapperName != null) {
359+
wrapperNameToUse = wrapperName;
360+
wrapperVersionToUse = wrapperVersion;
361+
}
362+
363+
if(wrapperNameToUse != null) {
364+
String wrapperId = wrapperVersionToUse == null ? wrapperNameToUse : (wrapperNameToUse + "/" + wrapperVersionToUse);
347365
headers.put("X-LaunchDarkly-Wrapper", wrapperId);
348366
}
349367

@@ -447,6 +465,14 @@ public ServiceEndpoints createServiceEndpoints() {
447465
}
448466
return new ServiceEndpoints(streamingBaseUri, pollingBaseUri, eventsBaseUri);
449467
}
468+
469+
public static ServiceEndpointsBuilderImpl fromServiceEndpoints(ServiceEndpoints endpoints) {
470+
ServiceEndpointsBuilderImpl newBuilder = new ServiceEndpointsBuilderImpl();
471+
newBuilder.eventsBaseUri = endpoints.getEventsBaseUri();
472+
newBuilder.pollingBaseUri = endpoints.getPollingBaseUri();
473+
newBuilder.streamingBaseUri = endpoints.getStreamingBaseUri();
474+
return newBuilder;
475+
}
450476
}
451477

452478
static HttpProperties toHttpProperties(HttpConfiguration httpConfig) {
@@ -465,4 +491,22 @@ static HttpProperties toHttpProperties(HttpConfiguration httpConfig) {
465491
httpConfig.getSslSocketFactory(),
466492
httpConfig.getTrustManager());
467493
}
494+
495+
static final class WrapperInfoBuilderImpl extends WrapperInfoBuilder {
496+
public WrapperInfoBuilderImpl() {
497+
this(null, null);
498+
}
499+
public WrapperInfoBuilderImpl(String wrapperName, String wrapperVersion) {
500+
this.wrapperName = wrapperName;
501+
this.wrapperVersion = wrapperVersion;
502+
}
503+
504+
public WrapperInfo build() {
505+
return new WrapperInfo(wrapperName, wrapperVersion);
506+
}
507+
508+
public static WrapperInfoBuilderImpl fromInfo(WrapperInfo info) {
509+
return new WrapperInfoBuilderImpl(info.getWrapperName(), info.getWrapperVersion());
510+
}
511+
}
468512
}

Diff for: src/main/java/com/launchdarkly/sdk/server/LDConfig.java

+55-12
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,11 @@
44
import com.launchdarkly.sdk.EvaluationReason.BigSegmentsStatus;
55
import com.launchdarkly.sdk.server.integrations.ApplicationInfoBuilder;
66
import com.launchdarkly.sdk.server.integrations.ServiceEndpointsBuilder;
7+
import com.launchdarkly.sdk.server.integrations.WrapperInfoBuilder;
78
import com.launchdarkly.sdk.server.interfaces.ApplicationInfo;
89
import com.launchdarkly.sdk.server.interfaces.BigSegmentsConfiguration;
910
import com.launchdarkly.sdk.server.interfaces.ServiceEndpoints;
11+
import com.launchdarkly.sdk.server.interfaces.WrapperInfo;
1012
import com.launchdarkly.sdk.server.subsystems.ComponentConfigurer;
1113
import com.launchdarkly.sdk.server.subsystems.DataSource;
1214
import com.launchdarkly.sdk.server.subsystems.DataStore;
@@ -24,7 +26,7 @@ public final class LDConfig {
2426
* The default value for {@link Builder#startWait(Duration)}: 5 seconds.
2527
*/
2628
public static final Duration DEFAULT_START_WAIT = Duration.ofSeconds(5);
27-
29+
2830
protected static final LDConfig DEFAULT = new Builder().build();
2931

3032
final ApplicationInfo applicationInfo;
@@ -39,6 +41,7 @@ public final class LDConfig {
3941
final boolean offline;
4042
final Duration startWait;
4143
final int threadPriority;
44+
final WrapperInfo wrapperInfo;
4245

4346
protected LDConfig(Builder builder) {
4447
if (builder.offline) {
@@ -62,8 +65,9 @@ protected LDConfig(Builder builder) {
6265
.createServiceEndpoints();
6366
this.startWait = builder.startWait;
6467
this.threadPriority = builder.threadPriority;
68+
this.wrapperInfo = builder.wrapperBuilder != null ? builder.wrapperBuilder.build() : null;
6569
}
66-
70+
6771
/**
6872
* A <a href="http://en.wikipedia.org/wiki/Builder_pattern">builder</a> that helps construct
6973
* {@link com.launchdarkly.sdk.server.LDConfig} objects. Builder calls can be chained, enabling the
@@ -88,13 +92,35 @@ public static class Builder {
8892
private boolean offline = false;
8993
private Duration startWait = DEFAULT_START_WAIT;
9094
private int threadPriority = Thread.MIN_PRIORITY;
95+
private WrapperInfoBuilder wrapperBuilder = null;
9196

9297
/**
9398
* Creates a builder with all configuration parameters set to the default
9499
*/
95100
public Builder() {
96101
}
97102

103+
public static Builder fromConfig(LDConfig config) {
104+
Builder newBuilder = new Builder();
105+
newBuilder.applicationInfoBuilder = ApplicationInfoBuilder.fromApplicationInfo(config.applicationInfo);
106+
newBuilder.bigSegments = config.bigSegments;
107+
newBuilder.dataSource = config.dataSource;
108+
newBuilder.dataStore = config.dataStore;
109+
newBuilder.diagnosticOptOut = config.diagnosticOptOut;
110+
newBuilder.events = config.events;
111+
newBuilder.http = config.http;
112+
newBuilder.logging = config.logging;
113+
114+
newBuilder.serviceEndpointsBuilder = ComponentsImpl.ServiceEndpointsBuilderImpl
115+
.fromServiceEndpoints(config.serviceEndpoints);
116+
newBuilder.offline = config.offline;
117+
newBuilder.startWait = config.startWait;
118+
newBuilder.threadPriority = config.threadPriority;
119+
newBuilder.wrapperBuilder = config.wrapperInfo != null ?
120+
ComponentsImpl.WrapperInfoBuilderImpl.fromInfo(config.wrapperInfo) : null;
121+
return newBuilder;
122+
}
123+
98124
/**
99125
* Sets the SDK's application metadata, which may be used in LaunchDarkly analytics or other product features,
100126
* but does not affect feature flag evaluations.
@@ -144,7 +170,7 @@ public Builder bigSegments(ComponentConfigurer<BigSegmentsConfiguration> bigSegm
144170
this.bigSegments = bigSegmentsConfigurer;
145171
return this;
146172
}
147-
173+
148174
/**
149175
* Sets the implementation of the component that receives feature flag data from LaunchDarkly,
150176
* using a factory object. Depending on the implementation, the factory may be a builder that
@@ -154,7 +180,7 @@ public Builder bigSegments(ComponentConfigurer<BigSegmentsConfiguration> bigSegm
154180
* {@link Components#pollingDataSource()}, or a test fixture such as
155181
* {@link com.launchdarkly.sdk.server.integrations.FileData#dataSource()}. See those methods
156182
* for details on how to configure them.
157-
*
183+
*
158184
* @param dataSourceConfigurer the data source configuration builder
159185
* @return the main configuration builder
160186
* @since 4.12.0
@@ -169,7 +195,7 @@ public Builder dataSource(ComponentConfigurer<DataSource> dataSourceConfigurer)
169195
* related data received from LaunchDarkly, using a factory object. The default is
170196
* {@link Components#inMemoryDataStore()}; for database integrations, use
171197
* {@link Components#persistentDataStore(ComponentConfigurer)}.
172-
*
198+
*
173199
* @param dataStoreConfigurer the data store configuration builder
174200
* @return the main configuration builder
175201
* @since 4.12.0
@@ -206,7 +232,7 @@ public Builder diagnosticOptOut(boolean diagnosticOptOut) {
206232
* {@link Components#sendEvents()} and then set custom options for event processing; or, disable
207233
* events with {@link Components#noEvents()}; or, choose to use a custom implementation (for
208234
* instance, a test fixture).
209-
*
235+
*
210236
* @param eventsConfigurer the events configuration builder
211237
* @return the main configuration builder
212238
* @since 4.12.0
@@ -222,7 +248,7 @@ public Builder events(ComponentConfigurer<EventProcessor> eventsConfigurer) {
222248
* Sets the SDK's networking configuration, using a configuration builder. This builder is
223249
* obtained from {@link Components#httpConfiguration()}, and has methods for setting individual
224250
* HTTP-related properties.
225-
*
251+
*
226252
* @param httpConfigurer the HTTP configuration builder
227253
* @return the main configuration builder
228254
* @since 4.13.0
@@ -237,7 +263,7 @@ public Builder http(ComponentConfigurer<HttpConfiguration> httpConfigurer) {
237263
* Sets the SDK's logging configuration, using a factory object. This object is normally a
238264
* configuration builder obtained from {@link Components#logging()}, which has methods
239265
* for setting individual logging-related properties.
240-
*
266+
*
241267
* @param loggingConfigurer the logging configuration builder
242268
* @return the main configuration builder
243269
* @since 5.0.0
@@ -258,7 +284,7 @@ public Builder logging(ComponentConfigurer<LoggingConfiguration> loggingConfigur
258284
* This is equivalent to calling {@code dataSource(Components.externalUpdatesOnly())} and
259285
* {@code events(Components.noEvents())}. It overrides any other values you may have set for
260286
* {@link #dataSource(ComponentConfigurer)} or {@link #events(ComponentConfigurer)}.
261-
*
287+
*
262288
* @param offline when set to true no calls to LaunchDarkly will be made
263289
* @return the builder
264290
*/
@@ -267,7 +293,7 @@ public Builder offline(boolean offline) {
267293
return this;
268294
}
269295

270-
/**
296+
/**
271297
* Sets the base service URIs used by SDK components.
272298
* <p>
273299
* This object is normally a configuration builder obtained from {@link Components#serviceEndpoints()},
@@ -305,7 +331,7 @@ public Builder startWait(Duration startWait) {
305331
* <p>
306332
* Values outside the range of [{@code Thread.MIN_PRIORITY}, {@code Thread.MAX_PRIORITY}] will be set
307333
* to the minimum or maximum.
308-
*
334+
*
309335
* @param threadPriority the priority for SDK threads
310336
* @return the builder
311337
* @since 5.0.0
@@ -314,7 +340,24 @@ public Builder threadPriority(int threadPriority) {
314340
this.threadPriority = Math.max(Thread.MIN_PRIORITY, Math.min(Thread.MAX_PRIORITY, threadPriority));
315341
return this;
316342
}
317-
343+
344+
/**
345+
* Set the wrapper information.
346+
* <p>
347+
* This is intended for use with wrapper SDKs from LaunchDarkly.
348+
* <p>
349+
* If the WrapperBuilder is set, then it will replace the wrapper information from the HttpPropertiesBuilder.
350+
* Additionally, any wrapper SDK may overwrite any application developer provided wrapper information.
351+
*
352+
* @param wrapperBuilder the wrapper builder
353+
* @return the builder
354+
* @since 7.1.0
355+
*/
356+
public Builder wrapper(WrapperInfoBuilder wrapperBuilder) {
357+
this.wrapperBuilder = wrapperBuilder;
358+
return this;
359+
}
360+
318361
/**
319362
* Builds the configured {@link com.launchdarkly.sdk.server.LDConfig} object.
320363
*

Diff for: src/main/java/com/launchdarkly/sdk/server/integrations/ApplicationInfoBuilder.java

+7
Original file line numberDiff line numberDiff line change
@@ -74,4 +74,11 @@ public ApplicationInfoBuilder applicationVersion(String applicationVersion) {
7474
public ApplicationInfo createApplicationInfo() {
7575
return new ApplicationInfo(applicationId, applicationVersion);
7676
}
77+
78+
public static ApplicationInfoBuilder fromApplicationInfo(ApplicationInfo info) {
79+
ApplicationInfoBuilder newBuilder = new ApplicationInfoBuilder();
80+
newBuilder.applicationId = info.getApplicationId();
81+
newBuilder.applicationVersion = info.getApplicationVersion();
82+
return newBuilder;
83+
}
7784
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package com.launchdarkly.sdk.server.integrations;
2+
3+
import com.launchdarkly.sdk.server.interfaces.WrapperInfo;
4+
5+
/**
6+
* Contains methods for configuring wrapper information.
7+
* <p>
8+
* This builder is primarily intended for use by LaunchDarkly in developing wrapper SDKs.
9+
* <p>
10+
* If the WrapperBuilder is used, then it will replace the wrapper information from the HttpPropertiesBuilder.
11+
* Additionally, any wrapper SDK may overwrite any application developer provided wrapper information.
12+
*/
13+
public abstract class WrapperInfoBuilder {
14+
protected String wrapperName;
15+
protected String wrapperVersion;
16+
17+
/**
18+
* Set the name of the wrapper.
19+
*
20+
* @param wrapperName the name of the wrapper
21+
* @return the builder
22+
*/
23+
public WrapperInfoBuilder wrapperName(String wrapperName) {
24+
this.wrapperName = wrapperName;
25+
return this;
26+
}
27+
28+
/**
29+
* Set the version of the wrapper.
30+
* <p>
31+
* This information will not be used unless the wrapperName is also set.
32+
*
33+
* @param wrapperVersion the version of the wrapper
34+
* @return the builder
35+
*/
36+
public WrapperInfoBuilder wrapperVersion(String wrapperVersion) {
37+
this.wrapperVersion = wrapperVersion;
38+
return this;
39+
}
40+
41+
public abstract WrapperInfo build();
42+
}

0 commit comments

Comments
 (0)