@@ -28,6 +28,7 @@ import (
2828 "sync/atomic"
2929 "time"
3030
31+ "github.com/Azure/AppConfiguration-GoProvider/azureappconfiguration/internal/afd"
3132 "github.com/Azure/AppConfiguration-GoProvider/azureappconfiguration/internal/jsonc"
3233 "github.com/Azure/AppConfiguration-GoProvider/azureappconfiguration/internal/refresh"
3334 "github.com/Azure/AppConfiguration-GoProvider/azureappconfiguration/internal/tracing"
@@ -51,12 +52,13 @@ type AzureAppConfiguration struct {
5152 trimPrefixes []string
5253 watchedSettings []WatchedSetting
5354 loadBalancingEnabled bool
55+ afdUsed bool
5456
5557 // Settings used for refresh scenarios
5658 sentinelETags map [WatchedSetting ]* azcore.ETag
5759 watchAll bool
58- kvETags map [comparableSelector ][]* azcore. ETag
59- ffETags map [comparableSelector ][]* azcore. ETag
60+ kvWatchers map [comparableSelector ][]settingWatcher
61+ ffWatchers map [comparableSelector ][]settingWatcher
6062 keyVaultRefs map [string ]string // unversioned Key Vault references
6163 kvRefreshTimer refresh.Condition
6264 secretRefreshTimer refresh.Condition
@@ -117,11 +119,18 @@ func Load(ctx context.Context, authentication AuthenticationOptions, options *Op
117119 credential : options .KeyVaultOptions .Credential ,
118120 }
119121
122+ if authentication .Credential != nil {
123+ if _ , ok := authentication .Credential .(* afd.EmptyTokenCredential ); ok {
124+ azappcfg .afdUsed = true
125+ azappcfg .tracingOptions .AfdUsed = true
126+ }
127+ }
128+
120129 if options .RefreshOptions .Enabled {
121130 azappcfg .kvRefreshTimer = refresh .NewTimer (options .RefreshOptions .Interval )
122131 azappcfg .watchedSettings = normalizedWatchedSettings (options .RefreshOptions .WatchedSettings )
123132 azappcfg .sentinelETags = make (map [WatchedSetting ]* azcore.ETag )
124- azappcfg .kvETags = make (map [comparableSelector ][]* azcore. ETag )
133+ azappcfg .kvWatchers = make (map [comparableSelector ][]settingWatcher )
125134 if len (options .RefreshOptions .WatchedSettings ) == 0 {
126135 azappcfg .watchAll = true
127136 }
@@ -137,7 +146,7 @@ func Load(ctx context.Context, authentication AuthenticationOptions, options *Op
137146 azappcfg .ffSelectors = getFeatureFlagSelectors (deduplicateSelectors (options .FeatureFlagOptions .Selectors ))
138147 if options .FeatureFlagOptions .RefreshOptions .Enabled {
139148 azappcfg .ffRefreshTimer = refresh .NewTimer (options .FeatureFlagOptions .RefreshOptions .Interval )
140- azappcfg .ffETags = make (map [comparableSelector ][]* azcore. ETag )
149+ azappcfg .ffWatchers = make (map [comparableSelector ][]settingWatcher )
141150 }
142151 }
143152
@@ -150,6 +159,41 @@ func Load(ctx context.Context, authentication AuthenticationOptions, options *Op
150159 return azappcfg , nil
151160}
152161
162+ func (azappcfg * AzureAppConfiguration ) LoadFromAzureFrontDoor (ctx context.Context , endpoint string , options * Options ) (* AzureAppConfiguration , error ) {
163+ if options == nil {
164+ options = & Options {}
165+ }
166+
167+ if options .ReplicaDiscoveryEnabled != nil && * options .ReplicaDiscoveryEnabled {
168+ return nil , errors .New ("replica discovery is not supported when loading from Azure Front Door. For guidance on how to take advantage of geo-replication when Azure Front Door is used, visit https://aka.ms/appconfig/geo-replication-with-afd" )
169+ }
170+
171+ if options .LoadBalancingEnabled {
172+ return nil , errors .New ("load balancing is not supported when loading from Azure Front Door. For guidance on how to take advantage of geo-replication when Azure Front Door is used, visit https://aka.ms/appconfig/geo-replication-with-afd" )
173+ }
174+
175+ if options .RefreshOptions .Enabled &&
176+ len (options .RefreshOptions .WatchedSettings ) > 0 {
177+ return nil , errors .New ("specifying watched settings is not supported when loading from Azure Front Door. If refresh is enabled, all loaded configuration settings will be watched automatically" )
178+ }
179+
180+ disableReplicaDiscovery := false
181+ options .ReplicaDiscoveryEnabled = & disableReplicaDiscovery
182+
183+ if options .ClientOptions == nil {
184+ options .ClientOptions = & azappconfig.ClientOptions {}
185+ }
186+
187+ options .ClientOptions .PerRetryPolicies = append (options .ClientOptions .PerRetryPolicies , afd .NewAnonymousRequestPipelinePolicy (), afd .NewRemoveSyncTokenPipelinePolicy ())
188+
189+ authOptions := AuthenticationOptions {
190+ Endpoint : endpoint ,
191+ Credential : afd .NewEmptyTokenCredential (),
192+ }
193+
194+ return Load (ctx , authOptions , options )
195+ }
196+
153197// Unmarshal parses the configuration and stores the result in the value pointed to v. It builds a hierarchical configuration structure based on key separators.
154198// It supports converting values to appropriate target types.
155199//
@@ -451,7 +495,7 @@ func (azappcfg *AzureAppConfiguration) loadKeyValues(ctx context.Context, settin
451495 maps .Copy (kvSettings , secrets )
452496 azappcfg .keyValues = kvSettings
453497 azappcfg .keyVaultRefs = getUnversionedKeyVaultRefs (keyVaultRefs )
454- azappcfg .kvETags = settingsResponse .pageETags
498+ azappcfg .kvWatchers = settingsResponse .pageWatchers
455499
456500 return nil
457501}
@@ -600,7 +644,7 @@ func (azappcfg *AzureAppConfiguration) loadFeatureFlags(ctx context.Context, set
600644 },
601645 }
602646
603- azappcfg .ffETags = settingsResponse .pageETags
647+ azappcfg .ffWatchers = settingsResponse .pageWatchers
604648 azappcfg .featureFlags = ffSettings
605649
606650 return nil
@@ -948,10 +992,10 @@ func normalizedWatchedSettings(s []WatchedSetting) []WatchedSetting {
948992func (azappcfg * AzureAppConfiguration ) newKeyValueRefreshClient (client * azappconfig.Client ) refreshClient {
949993 var monitor eTagsClient
950994 if azappcfg .watchAll {
951- monitor = & pageETagsClient {
995+ monitor = & pageWatcherClient {
952996 client : client ,
953997 tracingOptions : azappcfg .tracingOptions ,
954- pageETags : azappcfg .kvETags ,
998+ pageWatchers : azappcfg .kvWatchers ,
955999 }
9561000 } else {
9571001 monitor = & watchedSettingClient {
@@ -983,10 +1027,10 @@ func (azappcfg *AzureAppConfiguration) newFeatureFlagRefreshClient(client *azapp
9831027 client : client ,
9841028 tracingOptions : azappcfg .tracingOptions ,
9851029 },
986- monitor : & pageETagsClient {
1030+ monitor : & pageWatcherClient {
9871031 client : client ,
9881032 tracingOptions : azappcfg .tracingOptions ,
989- pageETags : azappcfg .ffETags ,
1033+ pageWatchers : azappcfg .ffWatchers ,
9901034 },
9911035 }
9921036}
0 commit comments