1
1
/*******************************************************************************
2
2
* Copyright 2023 Intel Corporation
3
+ * Copyright 2025 IOTech Ltd
3
4
*
4
5
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
5
6
* in compliance with the License. You may obtain a copy of the License at
@@ -17,25 +18,25 @@ package common_config
17
18
import (
18
19
"context"
19
20
"fmt"
21
+ "gopkg.in/yaml.v3"
20
22
"net/http"
21
23
"os"
22
24
"os/signal"
23
- "sort"
24
25
"sync"
25
26
"syscall"
26
27
27
28
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/config"
28
29
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/container"
29
30
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/environment"
31
+ "github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/file"
30
32
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/flags"
33
+ "github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/interfaces"
31
34
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/secret"
32
35
"github.com/edgexfoundry/go-mod-bootstrap/v4/bootstrap/startup"
33
36
"github.com/edgexfoundry/go-mod-bootstrap/v4/di"
34
- "github.com/edgexfoundry/go-mod-configuration/v4/configuration"
35
37
"github.com/edgexfoundry/go-mod-core-contracts/v4/clients/logger"
36
38
"github.com/edgexfoundry/go-mod-core-contracts/v4/common"
37
39
"github.com/edgexfoundry/go-mod-core-contracts/v4/models"
38
- "gopkg.in/yaml.v3"
39
40
)
40
41
41
42
const (
@@ -96,37 +97,39 @@ func Main(ctx context.Context, cancel context.CancelFunc, args []string) {
96
97
os .Exit (1 )
97
98
}
98
99
99
- hasConfig := false
100
- hasConfigSuccess := false
101
- for startupTimer .HasNotElapsed () {
102
- // check to see if the configuration exists in the config provider
103
- hasConfig , err = configClient .HasConfiguration ()
104
- if err == nil {
105
- hasConfigSuccess = true
106
- break
107
- }
108
-
109
- lc .Warnf ("Unable to determine if common configuration exists in the provider, will try again: %v" , err )
110
- startupTimer .SleepForInterval ()
100
+ // push not done flag to configClient
101
+ err = configClient .PutConfigurationValue (commonConfigDone , []byte (common .ValueFalse ))
102
+ if err != nil {
103
+ lc .Errorf ("failed to push %s on startup: %s" , commonConfigDone , err .Error ())
104
+ os .Exit (1 )
111
105
}
112
106
113
- if ! hasConfigSuccess {
114
- lc .Errorf ("failed to determine if common configuration exists in the provider: %s" , err .Error ())
107
+ yamlFile := config .GetConfigFileLocation (lc , f )
108
+ lc .Infof ("Using common configuration from %s" , yamlFile )
109
+
110
+ configMap , err := loadConfigMapFromYamlFile (yamlFile , secretProvider , lc )
111
+ if err != nil {
112
+ lc .Errorf ("Failed to load %s : %s" , yamlFile , err .Error ())
113
+ os .Exit (1 )
114
+ }
115
+ configMap , err = applyEnvOverrides (configMap , lc )
116
+ if err != nil {
117
+ lc .Errorf ("Failed to apply env overrides to common configuration: %s" , err .Error ())
115
118
os .Exit (1 )
116
119
}
117
120
118
- // load the yaml file and push it using the config client
119
- if ! hasConfig || getOverwriteConfig (f , lc ) {
120
- lc .Info ("Pushing common configuration. It doesn't exists or overwrite flag is set" )
121
+ // PutConfigurationMap func will check each keys and put the config value if not exist or override is set
122
+ err = configClient .PutConfigurationMap (configMap , getOverwriteConfig (f , lc ))
123
+ if err != nil {
124
+ lc .Errorf ("Failed to put configuration: %s" , err .Error ())
125
+ os .Exit (1 )
126
+ }
121
127
122
- yamlFile := config .GetConfigFileLocation (lc , f )
123
- err = pushConfiguration (lc , yamlFile , configClient )
124
- if err != nil {
125
- lc .Error (err .Error ())
126
- os .Exit (1 )
127
- }
128
- } else {
129
- lc .Info ("Skipped pushing common configuration. It already exists and overwrite flag not set" )
128
+ // push done flag to config client
129
+ err = configClient .PutConfigurationValue (commonConfigDone , []byte (common .ValueTrue ))
130
+ if err != nil {
131
+ lc .Errorf ("Failed to push %s on completion: %s" , commonConfigDone , err .Error ())
132
+ os .Exit (1 )
130
133
}
131
134
132
135
lc .Info ("Core Common Config exiting" )
@@ -155,96 +158,30 @@ func translateInterruptToCancel(ctx context.Context, wg *sync.WaitGroup, cancel
155
158
}()
156
159
}
157
160
158
- func pushConfiguration (lc logger.LoggingClient , yamlFile string , configClient configuration.Client ) error {
159
- // push not done flag to configClient
160
- err := configClient .PutConfigurationValue (commonConfigDone , []byte ("false" ))
161
- if err != nil {
162
- return fmt .Errorf ("failed to push %s on startup: %s" , commonConfigDone , err .Error ())
163
- }
164
- lc .Infof ("Using common configuration from %s" , yamlFile )
165
- contents , err := os .ReadFile (yamlFile )
166
- if err != nil {
167
- return fmt .Errorf ("failed to read common configuration file %s: %s" , yamlFile , err .Error ())
168
- }
169
-
170
- data := make (map [string ]interface {})
171
- kv := make (map [string ]interface {})
172
-
173
- err = yaml .Unmarshal (contents , & data )
174
- if err != nil {
175
- return fmt .Errorf ("failed to unmarshall common configuration file %s: %s" , yamlFile , err .Error ())
176
- }
177
-
178
- kv = buildKeyValues (data , kv , "" )
179
-
180
- kv , err = applyEnvOverrides (kv , lc )
181
- if err != nil {
182
- return fmt .Errorf ("failed to apply env overrides to common configuration: %s" , err .Error ())
183
- }
184
-
185
- keys := make ([]string , 0 , len (kv ))
186
-
187
- for k := range kv {
188
- keys = append (keys , k )
189
- }
190
-
191
- sort .Strings (keys )
192
-
193
- for _ , k := range keys {
194
- v := kv [k ]
195
- // Push key/value into Configuration Provider if it is not empty
196
- if v != nil {
197
- err = configClient .PutConfigurationValue (k , []byte (fmt .Sprint (v )))
198
- }
199
- if err != nil {
200
- return fmt .Errorf ("failed to push common configuration key %s with value %v: %s" , k , v , err .Error ())
201
- }
202
- }
161
+ func applyEnvOverrides (keyValues map [string ]any , lc logger.LoggingClient ) (map [string ]any , error ) {
162
+ env := environment .NewVariables (lc )
203
163
204
- // push done flag to config client
205
- err = configClient .PutConfigurationValue (commonConfigDone , []byte ("true" ))
164
+ overrideCount , err := env .OverrideConfigMapValues (keyValues )
206
165
if err != nil {
207
- return fmt . Errorf ( "failed to push %s on completion: %s" , commonConfigDone , err . Error ())
166
+ return nil , err
208
167
}
209
168
210
- lc .Info ("Common configuration has been pushed to into Configuration Provider with overrides applied" )
169
+ lc .Infof ("Common configuration loaded from file with %d overrides applied" , overrideCount )
211
170
212
- return nil
171
+ return keyValues , nil
213
172
}
214
173
215
- // buildKeyValues is a helper function to parse the configuration yaml file contents
216
- func buildKeyValues (data map [string ]interface {}, kv map [string ]interface {}, origKey string ) map [string ]interface {} {
217
- key := origKey
218
- for k , v := range data {
219
- if len (key ) == 0 {
220
- key = fmt .Sprint (k )
221
- } else {
222
- key = fmt .Sprintf ("%s/%s" , key , k )
223
- }
224
-
225
- vdata , ok := v .(map [string ]interface {})
226
- if ! ok {
227
- kv [key ] = v
228
- key = origKey
229
- continue
230
- }
231
-
232
- kv = buildKeyValues (vdata , kv , key )
233
- key = origKey
174
+ func loadConfigMapFromYamlFile (yamlFile string , secretProvider interfaces.SecretProvider , lc logger.LoggingClient ) (map [string ]any , error ) {
175
+ contents , err := file .Load (yamlFile , secretProvider , lc )
176
+ if err != nil {
177
+ return nil , fmt .Errorf ("failed to read configuration file %s: %s" , yamlFile , err .Error ())
234
178
}
235
179
236
- return kv
237
- }
238
-
239
- func applyEnvOverrides (keyValues map [string ]any , lc logger.LoggingClient ) (map [string ]any , error ) {
240
- env := environment .NewVariables (lc )
180
+ data := make (map [string ]any )
241
181
242
- overrideCount , err := env . OverrideConfigMapValues ( keyValues )
182
+ err = yaml . Unmarshal ( contents , & data )
243
183
if err != nil {
244
- return nil , err
184
+ return nil , fmt . Errorf ( "failed to unmarshall yaml configuration: %s" , err . Error ())
245
185
}
246
-
247
- lc .Infof ("Common configuration loaded from file with %d overrides applied" , overrideCount )
248
-
249
- return keyValues , nil
186
+ return data , nil
250
187
}
0 commit comments