2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2020 AT&T Intellectual Property. All rights reserved.
6 * ================================================================================
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 * ============LICENSE_END=========================================================
21 package org.openecomp.sdc.be.components.health;
23 import com.google.common.annotations.VisibleForTesting;
24 import org.apache.commons.lang.StringUtils;
25 import org.onap.portalsdk.core.onboarding.exception.CipherUtilException;
26 import org.onap.portalsdk.core.onboarding.util.PortalApiProperties;
27 import org.openecomp.sdc.be.config.Configuration;
28 import org.openecomp.sdc.be.config.Configuration.EcompPortalConfig;
29 import org.openecomp.sdc.be.config.ConfigurationManager;
30 import org.openecomp.sdc.be.ecomp.PortalPropertiesEnum;
31 import org.openecomp.sdc.common.api.Constants;
32 import org.openecomp.sdc.common.api.HealthCheckInfo;
33 import org.openecomp.sdc.common.api.HealthCheckInfo.HealthCheckStatus;
34 import org.openecomp.sdc.common.http.client.api.HttpExecuteException;
35 import org.openecomp.sdc.common.http.client.api.HttpRequest;
36 import org.openecomp.sdc.common.http.client.api.HttpResponse;
37 import org.openecomp.sdc.common.http.config.HttpClientConfig;
38 import org.openecomp.sdc.common.http.config.Timeouts;
39 import org.openecomp.sdc.common.log.wrappers.Logger;
40 import org.springframework.stereotype.Component;
42 import javax.annotation.PostConstruct;
43 import javax.annotation.PreDestroy;
44 import javax.ws.rs.core.HttpHeaders;
45 import javax.ws.rs.core.MediaType;
46 import java.security.InvalidParameterException;
47 import java.util.Base64;
48 import java.util.Properties;
49 import java.util.UUID;
50 import java.util.concurrent.Executors;
51 import java.util.concurrent.ScheduledExecutorService;
52 import java.util.concurrent.ScheduledFuture;
53 import java.util.concurrent.TimeUnit;
55 import static org.apache.http.HttpStatus.SC_OK;
56 import static org.onap.portalsdk.core.onboarding.util.CipherUtil.decryptPKC;
57 import static org.openecomp.sdc.common.api.Constants.HC_COMPONENT_ECOMP_PORTAL;
58 import static org.openecomp.sdc.common.api.HealthCheckInfo.HealthCheckStatus.DOWN;
59 import static org.openecomp.sdc.common.api.HealthCheckInfo.HealthCheckStatus.UP;
61 @Component("portalHealthCheckBusinessLogic")
62 public class PortalHealthCheckBuilder {
64 private static final Logger log = Logger.getLogger(HealthCheckBusinessLogic.class.getName());
65 private static final String PORTAL_NOT_AVAILABLE = HC_COMPONENT_ECOMP_PORTAL + " is not available";
66 private static final String PROPERTY_NOT_SET = "Property is not found %s";
67 private static final String CONFIG_IS_MISSING = HC_COMPONENT_ECOMP_PORTAL + " health check configuration is missing";
68 private static final String PORTAL_ERROR = HC_COMPONENT_ECOMP_PORTAL + " responded with %s status code";
69 private String decryptedPortalUser;
70 private String decryptedPortalPass;
71 private EcompPortalConfig configuration = null ;
72 private long healthCheckReadTimeout = 20;
73 private long reconnectInterval = 5;
74 private HealthCheckScheduledTask healthCheckScheduledTask = null ;
75 private final ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
76 private ScheduledFuture<?> scheduledFuture = null;
77 private HealthCheckInfo healthCheckInfo = new HealthCheckInfo
78 (HC_COMPONENT_ECOMP_PORTAL, HealthCheckStatus.DOWN, null, CONFIG_IS_MISSING, null);
81 PortalHealthCheckBuilder init(EcompPortalConfig configuration) throws CipherUtilException {
82 log.trace("Enter init method of Portal healthcheck");
83 decryptedPortalUser = decryptPKC
84 (getPortalProperty(PortalPropertiesEnum.USER.value()));
85 decryptedPortalPass = decryptPKC
86 (getPortalProperty(PortalPropertiesEnum.PASSWORD.value()));
87 synchronized (PortalHealthCheckBuilder.class){
88 if (configuration != null) {
89 Integer pollingInterval = configuration.getPollingInterval();
90 if (pollingInterval != null && pollingInterval != 0) {
91 reconnectInterval = pollingInterval;
93 Integer healthCheckReadTimeoutConfig = configuration.getTimeoutMs();
94 if (healthCheckReadTimeoutConfig != null) {
95 this.healthCheckReadTimeout = healthCheckReadTimeoutConfig;
97 this.healthCheckScheduledTask = new HealthCheckScheduledTask(configuration);
98 startHealthCheckTask(true);
101 log.error("ECOMP Portal health check configuration is missing.");
104 log.trace("Exit init method of Portal healthcheck");
109 public PortalHealthCheckBuilder init() throws CipherUtilException {
110 return init(ConfigurationManager.getConfigurationManager().getConfiguration().getEcompPortal());
115 protected void destroy() {
116 if (scheduledFuture != null) {
117 scheduledFuture.cancel(true);
118 scheduledFuture = null;
120 if (scheduler != null) {
121 scheduler.shutdown();
126 * Start health check task.
130 private void startHealthCheckTask(boolean startTask) {
131 synchronized (PortalHealthCheckBuilder.class){
132 if (startTask && this.scheduledFuture == null) {
133 this.scheduledFuture = this.scheduler.scheduleAtFixedRate(this.healthCheckScheduledTask , 0, reconnectInterval, TimeUnit.SECONDS);
140 healthCheckScheduledTask.run();
143 public HealthCheckInfo getHealthCheckInfo() {
144 return healthCheckInfo;
148 * Health Check Task Scheduler - infinite check.
150 public class HealthCheckScheduledTask implements Runnable {
151 private final EcompPortalConfig config;
152 String healthCheckUrl = buildPortalHealthCheckUrl();
153 HealthCheckStatus healthCheckStatus = DOWN;
154 String componentName = HC_COMPONENT_ECOMP_PORTAL;
156 final int timeout = 3000;
158 HealthCheckScheduledTask(final EcompPortalConfig config){
159 this.config = config;
163 if (healthCheckUrl != null) {
165 int statusCode = getStatusCode(healthCheckUrl, timeout);
166 log.trace("{} Health Check response code: {}", componentName, statusCode);
167 if (statusCode != SC_OK) {
168 description = String.format(PORTAL_ERROR, statusCode);
170 healthCheckStatus = UP;
173 } catch (Exception e) {
174 log.error("{} is not available: ", componentName, e.getMessage());
175 description = PORTAL_NOT_AVAILABLE;
178 description = CONFIG_IS_MISSING;
181 healthCheckInfo.setHealthCheckStatus(healthCheckStatus);
182 healthCheckInfo.setDescription(description);
186 private static String getPortalProperty(String key) {
187 String value = PortalApiProperties.getProperty(key);
188 if (StringUtils.isEmpty(value)) {
189 throw new InvalidParameterException(String.format(PROPERTY_NOT_SET, key));
194 String buildPortalHealthCheckUrl() {
195 final String hcUrl = "%s://%s:%s%s";
196 Configuration.EcompPortalConfig configuration = ConfigurationManager.getConfigurationManager().getConfiguration().getEcompPortal();
197 if (configuration != null) {
198 return String.format(hcUrl, configuration.getProtocol(), configuration.getHost(),
199 configuration.getPort(), configuration.getHealthCheckUri());
201 log.error("ECOMP Portal health check configuration is missing.");
205 private Properties createHeaders(){
206 Properties headers = new Properties();
207 String encodedBasicAuthCred = Base64.getEncoder()
208 .encodeToString((decryptedPortalUser + ":" +
211 headers.put(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON);
212 headers.put(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON);
213 headers.put(Constants.X_TRANSACTION_ID_HEADER, UUID.randomUUID().toString());
214 headers.put("Authorization", "Basic " + encodedBasicAuthCred);
215 headers.put("cache-control", "no-cache");
216 headers.put("uebkey", PortalApiProperties.getProperty("ueb_app_key"));
220 int getStatusCode(String healthCheckUrl, int timeout) throws HttpExecuteException {
221 HttpResponse<String> httpResponse = HttpRequest.get(healthCheckUrl, createHeaders(), new HttpClientConfig(new Timeouts(timeout, timeout)));
222 return httpResponse.getStatusCode();
226 public EcompPortalConfig getConfiguration() {
227 return ConfigurationManager.getConfigurationManager().getConfiguration().getEcompPortal();