From d3bd373d305a5ca19045b6ada3e5b537bf3819a6 Mon Sep 17 00:00:00 2001 From: Daniele Margutti Date: Thu, 31 Aug 2023 11:39:07 +0200 Subject: [PATCH] Added support for dynamic source of providers for a FlagsLoader --- .../Classes/FlagsLoader/FlagsLoader.swift | 47 +++++++++++++++++-- 1 file changed, 42 insertions(+), 5 deletions(-) diff --git a/RealFlags/Sources/RealFlags/Classes/FlagsLoader/FlagsLoader.swift b/RealFlags/Sources/RealFlags/Classes/FlagsLoader/FlagsLoader.swift index 0d10b18..bfe8ea5 100644 --- a/RealFlags/Sources/RealFlags/Classes/FlagsLoader/FlagsLoader.swift +++ b/RealFlags/Sources/RealFlags/Classes/FlagsLoader/FlagsLoader.swift @@ -19,13 +19,22 @@ import Foundation @dynamicMemberLookup public class FlagsLoader: FlagsLoaderProtocol, CustomDebugStringConvertible { + /// A function which allows to provide a dynamic list of providers for a flag loader. + public typealias FlagsProviderDynamicCallback = (() -> [FlagsProvider]) + // MARK: - Public Properties /// Collection of feature flag loaded. public private(set) var loadedCollection: Collection /// Providers where we'll get the data. - public var providers: [FlagsProvider]? + public var providers: [FlagsProvider]? { + if let dynamicProvider = self.dynamicProvidersCallback { + return dynamicProvider() + } + + return staticProviders + } /// How to build automatically keys for each property of the group. public let keyConfiguration: KeyConfiguration @@ -33,25 +42,53 @@ public class FlagsLoader: FlagsLoaderProtoco /// Metadata associated with loaded flag collection. public var metadata: FlagMetadata? + // MARK: - Private Properties + + /// Static list of providers if specified. + /// When a `FlagsProviderDynamicCallback` is passed it will empty. + private var staticProviders: [FlagsProvider]? + + /// Specify a callback function to provide list of dynamic providers. + private var dynamicProvidersCallback: FlagsProviderDynamicCallback? + // MARK: - Initialization - /// Initiali + /// Initialize a new flags loader collection with static list of providers. + /// /// - Parameters: /// - collection: type of collection to load. a new instance is made. /// - metadata: optional metadata associated with the flag loader. /// - providers: providers to use to fetch values. Providers are fetched in order. - /// - keysConfiguration: configuration + /// - keysConfiguration: configuration. public init (_ collectionType: Collection.Type, description: FlagMetadata? = nil, - providers: [FlagsProvider]? = nil, + providers: [FlagsProvider], keyConfiguration: KeyConfiguration = .init()) { self.loadedCollection = collectionType.init() - self.providers = providers + self.staticProviders = providers self.keyConfiguration = keyConfiguration self.metadata = description initializeCollectionObjects() } + /// Initialize a new flags loader collection with a function which provide providers dynamically. + /// + /// - Parameters: + /// - collectionType: type of collection to load. a new instance is made. + /// - description: optional metadata associated with the flag loader. + /// - dynamicProviders: a function which provide a list of providers to use when querying properties from this loader. + /// - keyConfiguration: configuratior. + public init(_ collectionType: Collection.Type, + description: FlagMetadata? = nil, + dynamicProviders: FlagsProviderDynamicCallback? = nil, + keyConfiguration: KeyConfiguration = .init()) { + self.loadedCollection = collectionType.init() + self.dynamicProvidersCallback = dynamicProviders + self.keyConfiguration = keyConfiguration + self.metadata = description + initializeCollectionObjects() + } + // MARK: - Public Functions public var debugDescription: String {