Skip to content

Commit e7ada4d

Browse files
committed
chore: Add file data source support for FDv2.
1 parent 192a6f2 commit e7ada4d

File tree

10 files changed

+1215
-265
lines changed

10 files changed

+1215
-265
lines changed

lib/sdk/server/src/main/java/com/launchdarkly/sdk/server/integrations/FileData.java

Lines changed: 238 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,13 @@
11
package com.launchdarkly.sdk.server.integrations;
22

33
import com.launchdarkly.sdk.server.LDConfig.Builder;
4+
import com.launchdarkly.sdk.server.datasources.Initializer;
5+
import com.launchdarkly.sdk.server.datasources.Synchronizer;
6+
import com.launchdarkly.sdk.server.subsystems.DataSourceBuildInputs;
7+
import com.launchdarkly.sdk.server.subsystems.DataSourceBuilder;
8+
9+
import java.nio.file.InvalidPathException;
10+
import java.nio.file.Path;
411

512
/**
613
* Integration between the LaunchDarkly SDK and file data.
@@ -137,6 +144,236 @@ public enum DuplicateKeysHandling {
137144
public static FileDataSourceBuilder dataSource() {
138145
return new FileDataSourceBuilder();
139146
}
140-
147+
148+
/**
149+
* Creates a builder for an FDv2 Initializer that loads file data.
150+
* <p>
151+
* An initializer performs a one-shot load of the file data. This is used with the FDv2 data system
152+
* for initial data loading.
153+
* <p>
154+
* This class is not stable, and not subject to any backwards compatibility guarantees or semantic versioning.
155+
* It is in early access. If you want access to this feature please join the EAP.
156+
* <a href="https://launchdarkly.com/docs/sdk/features/data-saving-mode">https://launchdarkly.com/docs/sdk/features/data-saving-mode</a>
157+
*
158+
* @return a builder for configuring the file data initializer
159+
*/
160+
public static FileInitializerBuilder initializer() {
161+
return new FileInitializerBuilder();
162+
}
163+
164+
/**
165+
* Creates a builder for an FDv2 Synchronizer that loads and watches file data.
166+
* <p>
167+
* A synchronizer loads file data and can watch for changes (if autoUpdate is enabled).
168+
* This is used with the FDv2 data system for ongoing data synchronization.
169+
* <p>
170+
* This class is not stable, and not subject to any backwards compatibility guarantees or semantic versioning.
171+
* It is in early access. If you want access to this feature please join the EAP.
172+
* <a href="https://launchdarkly.com/docs/sdk/features/data-saving-mode">https://launchdarkly.com/docs/sdk/features/data-saving-mode</a>
173+
*
174+
* @return a builder for configuring the file data synchronizer
175+
*/
176+
public static FileSynchronizerBuilder synchronizer() {
177+
return new FileSynchronizerBuilder();
178+
}
179+
141180
private FileData() {}
181+
182+
/**
183+
* Builder for creating an FDv2 {@link Initializer} that loads file data.
184+
* <p>
185+
* This class is not stable, and not subject to any backwards compatibility guarantees or semantic versioning.
186+
* It is in early access. If you want access to this feature please join the EAP.
187+
* <a href="https://launchdarkly.com/docs/sdk/features/data-saving-mode">https://launchdarkly.com/docs/sdk/features/data-saving-mode</a>
188+
*/
189+
public static final class FileInitializerBuilder implements DataSourceBuilder<Initializer> {
190+
private final FileDataSourceBuilder delegate = new FileDataSourceBuilder();
191+
192+
FileInitializerBuilder() {
193+
delegate.shouldPersist(false);
194+
}
195+
196+
/**
197+
* Adds any number of source files for loading flag data, specifying each file path as a string.
198+
*
199+
* @param filePaths path(s) to the source file(s); may be absolute or relative to the current working directory
200+
* @return the same builder
201+
* @throws InvalidPathException if one of the parameters is not a valid file path
202+
* @see FileDataSourceBuilder#filePaths(String...)
203+
*/
204+
public FileInitializerBuilder filePaths(String... filePaths) throws InvalidPathException {
205+
delegate.filePaths(filePaths);
206+
return this;
207+
}
208+
209+
/**
210+
* Adds any number of source files for loading flag data, specifying each file path as a Path.
211+
*
212+
* @param filePaths path(s) to the source file(s); may be absolute or relative to the current working directory
213+
* @return the same builder
214+
* @see FileDataSourceBuilder#filePaths(Path...)
215+
*/
216+
public FileInitializerBuilder filePaths(Path... filePaths) {
217+
delegate.filePaths(filePaths);
218+
return this;
219+
}
220+
221+
/**
222+
* Adds any number of classpath resources for loading flag data.
223+
*
224+
* @param resourceLocations resource location(s) in the format used by {@code ClassLoader.getResource()}
225+
* @return the same builder
226+
* @see FileDataSourceBuilder#classpathResources(String...)
227+
*/
228+
public FileInitializerBuilder classpathResources(String... resourceLocations) {
229+
delegate.classpathResources(resourceLocations);
230+
return this;
231+
}
232+
233+
/**
234+
* Specifies how to handle keys that are duplicated across files.
235+
*
236+
* @param duplicateKeysHandling specifies how to handle duplicate keys
237+
* @return the same builder
238+
* @see FileDataSourceBuilder#duplicateKeysHandling(DuplicateKeysHandling)
239+
*/
240+
public FileInitializerBuilder duplicateKeysHandling(DuplicateKeysHandling duplicateKeysHandling) {
241+
delegate.duplicateKeysHandling(duplicateKeysHandling);
242+
return this;
243+
}
244+
245+
/**
246+
* Configures whether file data should be persisted to persistent stores.
247+
* <p>
248+
* By default, file data is not persisted ({@code shouldPersist = false}).
249+
* <p>
250+
* Set this to {@code true} if you want the SDK to persist flag data to persistent stores.
251+
* This isn't the recommended configuration but may be useful for testing scenarios.
252+
* <p>
253+
* Example:
254+
* <pre><code>
255+
* FileData fd = FileData.initializer()
256+
* .filePaths("./testData/flags.json")
257+
* .shouldPersist(true);
258+
* </code></pre>
259+
*
260+
* @param shouldPersist {@code true} if tile data should be persisted to persistent stores, false otherwise
261+
* @return the same {@code TestData} instance
262+
*/
263+
public FileInitializerBuilder shouldPersist(boolean shouldPersist) {
264+
delegate.shouldPersist(shouldPersist);
265+
return this;
266+
}
267+
268+
269+
@Override
270+
public Initializer build(DataSourceBuildInputs context) {
271+
return delegate.buildInitializer(context);
272+
}
273+
}
274+
275+
/**
276+
* Builder for creating an FDv2 {@link Synchronizer} that loads and watches file data.
277+
* <p>
278+
* This class is not stable, and not subject to any backwards compatibility guarantees or semantic versioning.
279+
* It is in early access. If you want access to this feature please join the EAP.
280+
* <a href="https://launchdarkly.com/docs/sdk/features/data-saving-mode">https://launchdarkly.com/docs/sdk/features/data-saving-mode</a>
281+
*/
282+
public static final class FileSynchronizerBuilder implements DataSourceBuilder<Synchronizer> {
283+
private final FileDataSourceBuilder delegate = new FileDataSourceBuilder();
284+
285+
FileSynchronizerBuilder() {
286+
delegate.shouldPersist(false);
287+
}
288+
289+
/**
290+
* Configures whether file data should be persisted to persistent stores.
291+
* <p>
292+
* By default, file data is not persisted ({@code shouldPersist = false}).
293+
* <p>
294+
* Set this to {@code true} if you want the SDK to persist flag data to persistent stores.
295+
* This isn't the recommended configuration but may be useful for testing scenarios.
296+
* <p>
297+
* Example:
298+
* <pre><code>
299+
* FileData fd = FileData.synchronizer()
300+
* .filePaths("./testData/flags.json")
301+
* .shouldPersist(true);
302+
* </code></pre>
303+
*
304+
* @param shouldPersist {@code true} if file data should be persisted to persistent stores, false otherwise
305+
* @return the same {@code TestData} instance
306+
*/
307+
public FileSynchronizerBuilder shouldPersist(boolean shouldPersist) {
308+
delegate.shouldPersist(shouldPersist);
309+
return this;
310+
}
311+
312+
/**
313+
* Adds any number of source files for loading flag data, specifying each file path as a string.
314+
*
315+
* @param filePaths path(s) to the source file(s); may be absolute or relative to the current working directory
316+
* @return the same builder
317+
* @throws InvalidPathException if one of the parameters is not a valid file path
318+
* @see FileDataSourceBuilder#filePaths(String...)
319+
*/
320+
public FileSynchronizerBuilder filePaths(String... filePaths) throws InvalidPathException {
321+
delegate.filePaths(filePaths);
322+
return this;
323+
}
324+
325+
/**
326+
* Adds any number of source files for loading flag data, specifying each file path as a Path.
327+
*
328+
* @param filePaths path(s) to the source file(s); may be absolute or relative to the current working directory
329+
* @return the same builder
330+
* @see FileDataSourceBuilder#filePaths(Path...)
331+
*/
332+
public FileSynchronizerBuilder filePaths(Path... filePaths) {
333+
delegate.filePaths(filePaths);
334+
return this;
335+
}
336+
337+
/**
338+
* Adds any number of classpath resources for loading flag data.
339+
*
340+
* @param resourceLocations resource location(s) in the format used by {@code ClassLoader.getResource()}
341+
* @return the same builder
342+
* @see FileDataSourceBuilder#classpathResources(String...)
343+
*/
344+
public FileSynchronizerBuilder classpathResources(String... resourceLocations) {
345+
delegate.classpathResources(resourceLocations);
346+
return this;
347+
}
348+
349+
/**
350+
* Specifies whether the data source should watch for changes to the source file(s) and reload flags
351+
* whenever there is a change.
352+
*
353+
* @param autoUpdate true if flags should be reloaded whenever a source file changes
354+
* @return the same builder
355+
* @see FileDataSourceBuilder#autoUpdate(boolean)
356+
*/
357+
public FileSynchronizerBuilder autoUpdate(boolean autoUpdate) {
358+
delegate.autoUpdate(autoUpdate);
359+
return this;
360+
}
361+
362+
/**
363+
* Specifies how to handle keys that are duplicated across files.
364+
*
365+
* @param duplicateKeysHandling specifies how to handle duplicate keys
366+
* @return the same builder
367+
* @see FileDataSourceBuilder#duplicateKeysHandling(DuplicateKeysHandling)
368+
*/
369+
public FileSynchronizerBuilder duplicateKeysHandling(DuplicateKeysHandling duplicateKeysHandling) {
370+
delegate.duplicateKeysHandling(duplicateKeysHandling);
371+
return this;
372+
}
373+
374+
@Override
375+
public Synchronizer build(DataSourceBuildInputs context) {
376+
return delegate.buildSynchronizer(context);
377+
}
378+
}
142379
}

0 commit comments

Comments
 (0)