7bdef6555309fc05c36232d9752559c5c059d5f9
[dcaegen2/collectors/ves.git] / src / main / java / org / onap / dcae / ApplicationSettings.java
1 /*
2  * ============LICENSE_START=======================================================
3  * PROJECT
4  * ================================================================================
5  * Copyright (C) 2017 AT&T Intellectual Property. All rights reserved.
6  * Copyright (C) 2018 - 2020 Nokia. All rights reserved.s
7  * ================================================================================
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *      http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  * ============LICENSE_END=========================================================
20  */
21
22 package org.onap.dcae;
23
24 import static java.lang.String.format;
25
26 import com.google.common.annotations.VisibleForTesting;
27 import com.google.common.reflect.TypeToken;
28 import com.google.gson.Gson;
29 import com.networknt.schema.JsonSchema;
30 import io.vavr.Function1;
31 import io.vavr.collection.HashMap;
32 import io.vavr.collection.Map;
33 import java.io.FileReader;
34 import java.io.IOException;
35 import java.lang.reflect.Type;
36 import java.nio.file.Path;
37 import java.nio.file.Paths;
38 import java.util.List;
39 import javax.annotation.Nullable;
40 import org.apache.commons.configuration.ConfigurationException;
41 import org.apache.commons.configuration.PropertiesConfiguration;
42 import org.onap.dcae.common.EventTransformation;
43 import org.onap.dcae.common.configuration.AuthMethodType;
44 import org.slf4j.Logger;
45 import org.slf4j.LoggerFactory;
46
47 /**
48  * Abstraction over application configuration.
49  * Its job is to provide easily discoverable (by method names lookup) and type safe access to configuration properties.
50  */
51 public class ApplicationSettings {
52
53     private static final String EVENT_TRANSFORM_FILE_PATH = "./etc/eventTransform.json";
54     private static final String COULD_NOT_FIND_FILE = "Couldn't find file " + EVENT_TRANSFORM_FILE_PATH;
55
56     private static final Logger log = LoggerFactory.getLogger(ApplicationSettings.class);
57     private static final String FALLBACK_VES_VERSION = "v5";
58     private static final int DISABLED = -1;
59     private static final int ENABLED = 1;
60     private final String appInvocationDir;
61     private final String configurationFileLocation;
62     private final PropertiesConfiguration properties = new PropertiesConfiguration();
63     private final Map<String, JsonSchema> loadedJsonSchemas;
64     private final List<EventTransformation> eventTransformations;
65
66     public ApplicationSettings(String[] args, Function1<String[], Map<String, String>> argsParser) {
67         this(args, argsParser, System.getProperty("user.dir"));
68     }
69
70     public ApplicationSettings(String[] args, Function1<String[], Map<String, String>> argsParser, String appInvocationDir) {
71         this.appInvocationDir = appInvocationDir;
72         properties.setDelimiterParsingDisabled(true);
73         Map<String, String> parsedArgs = argsParser.apply(args);
74         configurationFileLocation = findOutConfigurationFileLocation(parsedArgs);
75         loadPropertiesFromFile();
76         parsedArgs.filterKeys(k -> !"c".equals(k)).forEach(this::addOrUpdate);
77         String collectorSchemaFile = properties.getString("collector.schema.file",
78                 format("{\"%s\":\"etc/CommonEventFormat_28.4.1.json\"}", FALLBACK_VES_VERSION));
79         loadedJsonSchemas = new JSonSchemasSupplier().loadJsonSchemas(collectorSchemaFile);
80         eventTransformations = loadEventTransformations();
81     }
82
83     /**
84      * Reload application settings.
85      */
86     public void reload() {
87         try {
88             properties.load(configurationFileLocation);
89             properties.refresh();
90         } catch (ConfigurationException ex) {
91             log.error("Cannot load properties cause:", ex);
92             throw new ApplicationException(ex);
93         }
94     }
95
96     public Map<String, String> validAuthorizationCredentials() {
97         return prepareUsersMap(properties.getString("header.authlist", null));
98     }
99     public Path configurationFileLocation() {
100         return Paths.get(configurationFileLocation);
101     }
102
103     public boolean eventSchemaValidationEnabled() {
104         return properties.getInt("collector.schema.checkflag", DISABLED) > 0;
105     }
106
107     public JsonSchema jsonSchema(String version) {
108         return loadedJsonSchemas.get(version)
109             .orElse(loadedJsonSchemas.get(FALLBACK_VES_VERSION))
110             .getOrElseThrow(() -> new IllegalStateException("No fallback schema present in application."));
111     }
112
113     public boolean isVersionSupported(String version){
114        return loadedJsonSchemas.containsKey(version);
115     }
116
117     public int httpPort() {
118         return properties.getInt("collector.service.port", 8080);
119     }
120
121     public int httpsPort() {
122         return properties.getInt("collector.service.secure.port", 8443);
123     }
124
125     public int configurationUpdateFrequency() {
126         return properties.getInt("collector.dynamic.config.update.frequency", 5);
127     }
128
129     public boolean httpsEnabled() {
130         return httpsPort() > 0;
131     }
132
133     public boolean eventTransformingEnabled() {
134         return properties.getInt("event.transform.flag", ENABLED) > 0;
135     }
136
137     public String keystorePasswordFileLocation() {
138         return prependWithUserDirOnRelative(properties.getString("collector.keystore.passwordfile", "etc/passwordfile"));
139     }
140
141     public String keystoreFileLocation() {
142         return prependWithUserDirOnRelative(properties.getString("collector.keystore.file.location", "etc/keystore"));
143     }
144
145     public String truststorePasswordFileLocation() {
146         return prependWithUserDirOnRelative(properties.getString("collector.truststore.passwordfile", "etc/trustpasswordfile"));
147     }
148
149     public String truststoreFileLocation() {
150         return prependWithUserDirOnRelative(properties.getString("collector.truststore.file.location", "etc/truststore"));
151     }
152
153     public String exceptionConfigFileLocation() {
154         return properties.getString("exceptionConfig", null);
155     }
156
157     public String dMaaPConfigurationFileLocation() {
158         return prependWithUserDirOnRelative(properties.getString("collector.dmaapfile", "etc/DmaapConfig.json"));
159     }
160
161     public String certSubjectMatcher(){
162         return prependWithUserDirOnRelative(properties.getString("collector.cert.subject.matcher", "etc/certSubjectMatcher.properties"));
163     }
164
165     public String authMethod(){
166         return properties.getString("auth.method", AuthMethodType.NO_AUTH.value());
167     }
168
169     public Map<String, String[]> getDmaapStreamIds() {
170         String streamIdsProperty = properties.getString("collector.dmaap.streamid", null);
171         if (streamIdsProperty == null) {
172             return HashMap.empty();
173         } else {
174             return convertDMaaPStreamsPropertyToMap(streamIdsProperty);
175         }
176     }
177
178     public boolean getExternalSchemaValidationCheckflag() {
179         return properties.getInt("collector.externalSchema.checkflag", DISABLED) > 0;
180     }
181
182     public String getExternalSchemaSchemasLocation() {
183         return properties.getString("collector.externalSchema.schemasLocation", "./etc/externalRepo");
184     }
185
186     public String getExternalSchemaMappingFileLocation() {
187         return properties.getString("collector.externalSchema.mappingFileLocation", "./etc/externalRepo/schema-map.json");
188     }
189
190     public String getExternalSchemaSchemaRefPath() {
191         return properties.getString("event.externalSchema.schemaRefPath", "/event/stndDefinedFields/schemaReference");
192     }
193
194     public String getExternalSchemaStndDefinedDataPath() {
195         return properties.getString("event.externalSchema.stndDefinedDataPath", "/event/stndDefinedFields/data");
196     }
197
198     public List<EventTransformation> getEventTransformations() {
199         return eventTransformations;
200     }
201
202     public String getApiVersionDescriptionFilepath() {
203         return properties.getString("collector.description.api.version.location", "etc/api_version_description.json");
204     }
205
206     private void loadPropertiesFromFile() {
207         try {
208             properties.load(configurationFileLocation);
209         } catch (ConfigurationException ex) {
210             log.error("Cannot load properties cause:", ex);
211             throw new ApplicationException(ex);
212         }
213     }
214
215     private void addOrUpdate(String key, String value) {
216         if (properties.containsKey(key)) {
217             properties.setProperty(key, value);
218         } else {
219             properties.addProperty(key, value);
220         }
221     }
222
223     private String findOutConfigurationFileLocation(Map<String, String> parsedArgs) {
224         return prependWithUserDirOnRelative(parsedArgs.get("c").getOrElse("etc/collector.properties"));
225     }
226
227     private Map<String, String> prepareUsersMap(@Nullable String allowedUsers) {
228         return allowedUsers == null ? HashMap.empty()
229             : io.vavr.collection.List.of(allowedUsers.split("\\|"))
230                 .map(t->t.split(","))
231                 .toMap(t-> t[0].trim(), t -> t[1].trim());
232     }
233
234     private Map<String, String[]> convertDMaaPStreamsPropertyToMap(String streamIdsProperty) {
235         java.util.HashMap<String, String[]> domainToStreamIdsMapping = new java.util.HashMap<>();
236         String[] topics = streamIdsProperty.split("\\|");
237         for (String t : topics) {
238             String domain = t.split("=")[0];
239             String[] streamIds = t.split("=")[1].split(",");
240             domainToStreamIdsMapping.put(domain, streamIds);
241         }
242         return HashMap.ofAll(domainToStreamIdsMapping);
243     }
244
245     private String prependWithUserDirOnRelative(String filePath) {
246         if (!Paths.get(filePath).isAbsolute()) {
247             filePath = Paths.get(appInvocationDir, filePath).toString();
248         }
249         return filePath;
250     }
251
252     private List<EventTransformation> loadEventTransformations() {
253         Type EVENT_TRANSFORM_LIST_TYPE = new TypeToken<List<EventTransformation>>() {}.getType();
254
255         try (FileReader fr = new FileReader(EVENT_TRANSFORM_FILE_PATH)) {
256             log.info("parse " + EVENT_TRANSFORM_FILE_PATH + " file");
257             return new Gson().fromJson(fr, EVENT_TRANSFORM_LIST_TYPE);
258         } catch (IOException e) {
259             log.error(COULD_NOT_FIND_FILE, e);
260             throw new ApplicationException(COULD_NOT_FIND_FILE, e);
261         }
262     }
263
264     @VisibleForTesting
265     String getStringDirectly(String key) {
266         return properties.getString(key);
267     }
268 }
269