2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017 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.switchover.detector;
23 import org.apache.commons.codec.binary.Base64;
24 import org.apache.http.entity.ContentType;
25 import org.apache.http.entity.StringEntity;
26 import org.openecomp.sdc.be.config.BeEcompErrorManager;
27 import org.openecomp.sdc.be.config.Configuration.SwitchoverDetectorConfig;
28 import org.openecomp.sdc.be.config.ConfigurationManager;
29 import org.openecomp.sdc.common.http.client.api.HttpRequest;
30 import org.openecomp.sdc.common.log.wrappers.Logger;
31 import org.springframework.stereotype.Component;
33 import javax.annotation.PostConstruct;
34 import javax.annotation.PreDestroy;
35 import java.net.InetAddress;
36 import java.util.Properties;
37 import java.util.concurrent.*;
39 @Component("switchover-detector")
40 public class SwitchoverDetector {
42 protected static String SWITCHOVER_DETECTOR_LOG_CONTEXT = "switchover.detector";
44 private SwitchoverDetectorConfig switchoverDetectorConfig;
46 private Properties authHeader = null;
48 private long detectorInterval = 60;
50 private int maxBeQueryAttempts = 3;
52 private int maxFeQueryAttempts = 3;
54 private Boolean beMatch = null;
56 private Boolean feMatch = null;
58 private static final Logger logger = Logger.getLogger(SwitchoverDetector.class);
60 private volatile String siteMode = SwitchoverDetectorState.UNKNOWN.getState();
62 private ScheduledFuture<?> scheduledFuture = null;
64 ScheduledExecutorService switchoverDetectorScheduler = Executors.newSingleThreadScheduledExecutor(new ThreadFactory() {
66 public Thread newThread(Runnable r) {
67 return new Thread(r, "Switchover-Detector-Task");
71 SwitchoverDetectorScheduledTask switchoverDetectorScheduledTask = null;
73 public enum SwitchoverDetectorState {
75 UNKNOWN("unknown"), ACTIVE("active"), STANDBY("standby");
79 SwitchoverDetectorState(String state) {
83 public String getState() {
88 public enum SwitchoverDetectorGroup {
90 BE_SET("beSet"), FE_SET("feSet");
94 SwitchoverDetectorGroup(String group) {
98 public String getGroup() {
103 public String getSiteMode() {
107 public void setSiteMode(String mode) {
108 this.siteMode = mode;
111 private Boolean queryBe() {
112 return queryGss(switchoverDetectorConfig.getgBeFqdn(), switchoverDetectorConfig.getBeVip(), maxBeQueryAttempts);
115 private Boolean queryFe() {
116 return queryGss(switchoverDetectorConfig.getgFeFqdn(), switchoverDetectorConfig.getFeVip(), maxFeQueryAttempts);
119 private void setAuthorizationProperties() {
120 String userInfo = switchoverDetectorConfig.getChangePriorityUser() + ":" + switchoverDetectorConfig.getChangePriorityPassword();
121 String auth = "Basic " + new String(new Base64().encode(userInfo.getBytes()));
122 authHeader = new Properties();
123 authHeader.put("Authorization", auth);
126 private void initializeSiteMode() {
127 while (siteMode.equals(SwitchoverDetectorState.UNKNOWN.getState())) {
132 if (beMatch == feMatch && beMatch != null) {
134 setSiteMode(SwitchoverDetectorState.ACTIVE.getState());
136 setSiteMode(SwitchoverDetectorState.STANDBY.getState());
142 private Boolean queryGss(String fqdn, String vip, int maxAttempts) {
144 Boolean result = null;
147 while (result == null && (++attempts < maxAttempts)) {
149 InetAddress inetAddress = InetAddress.getByName(fqdn);
150 result = inetAddress.getHostAddress().equals(vip);
152 } catch (Exception e) {
153 String message = e.getMessage();
154 if (message == null) {
155 message = e.getClass().getName();
157 logger.debug("Error occured during switchover detector query, Result is {}", message, e);
160 if (null == result) {
161 BeEcompErrorManager.getInstance().logFqdnResolveError(SWITCHOVER_DETECTOR_LOG_CONTEXT, "host " + fqdn + " not resolved after " + attempts + " attempts");
166 public class SwitchoverDetectorScheduledTask implements Runnable {
168 public SwitchoverDetectorScheduledTask() {
174 logger.trace("Executing Switchover Detector Task - Start");
176 initializeSiteMode();
178 Boolean beRes = queryBe();
179 Boolean feRes = queryFe();
181 if (null == beRes || null == feRes) {
185 Boolean updateRequired = siteMode == SwitchoverDetectorState.STANDBY.getState() && (beRes || feRes) && (beMatch != beRes || feMatch != feRes);
187 updateSiteModeAndPriority(beRes && feRes, siteMode == SwitchoverDetectorState.STANDBY.getState(), updateRequired);
193 ExecutorService switchoverDetectorExecutor = Executors.newSingleThreadExecutor(new ThreadFactory() {
195 public Thread newThread(Runnable r) {
196 return new Thread(r, "Switchover-Detector-Thread");
200 private void updateSiteModeAndPriority(Boolean bothMatch, Boolean previousModeStandby, Boolean updateRequired) {
201 if (bothMatch && previousModeStandby) {
202 logger.trace("Site switch over was done. Site is now in active mode");
203 setSiteMode(SwitchoverDetectorState.ACTIVE.getState());
204 BeEcompErrorManager.getInstance().logSiteSwitchoverInfo(SWITCHOVER_DETECTOR_LOG_CONTEXT, siteMode);
205 } else if (!bothMatch && !previousModeStandby) {
206 logger.trace("Site switch over was done. Site is now in stand-by mode");
207 setSiteMode(SwitchoverDetectorState.STANDBY.getState());
208 BeEcompErrorManager.getInstance().logSiteSwitchoverInfo(SWITCHOVER_DETECTOR_LOG_CONTEXT, siteMode);
210 if (updateRequired) {
211 changeSitePriority(SwitchoverDetectorGroup.BE_SET.getGroup());
212 changeSitePriority(SwitchoverDetectorGroup.FE_SET.getGroup());
217 private void changeSitePriority(String groupToSet) {
219 String url = switchoverDetectorConfig.getGroups().get(groupToSet).getChangePriorityUrl();
220 String body = switchoverDetectorConfig.getGroups().get(groupToSet).getChangePriorityBody();
223 HttpRequest.put(url, authHeader, new StringEntity(body, ContentType.APPLICATION_JSON));
224 } catch (Exception e) {
225 String message = e.getMessage();
226 if (message == null) {
227 message = e.getClass().getName();
229 logger.debug("Error occured during change site priority request, Result is {}", message, e);
234 private void publishNetwork() {
236 String url = switchoverDetectorConfig.getPublishNetworkUrl();
237 String body = switchoverDetectorConfig.getPublishNetworkBody();
239 HttpRequest.post(url, authHeader, new StringEntity(body, ContentType.APPLICATION_JSON));
240 } catch (Exception e) {
241 String message = e.getMessage();
242 if (message == null) {
243 message = e.getClass().getName();
245 logger.debug("Error occured during publish network request, Result is {}", message, e);
252 private void init() {
253 logger.info("Enter init method of SwitchoverDetector");
255 switchoverDetectorConfig = ConfigurationManager.getConfigurationManager().getConfiguration().getSwitchoverDetector();
257 if (!switchoverDetectorConfig.getEnabled()) {
258 logger.info("switchover detector service is disabled");
262 Long detectorIntervalConfig = switchoverDetectorConfig.getInterval();
263 if (detectorIntervalConfig != null) {
264 detectorInterval = detectorIntervalConfig.longValue();
267 Integer maxAttempts = switchoverDetectorConfig.getBeResolveAttempts();
268 if (maxAttempts != null) {
269 maxBeQueryAttempts = maxAttempts.intValue();
271 maxAttempts = switchoverDetectorConfig.getFeResolveAttempts();
272 if (maxAttempts != null) {
273 maxFeQueryAttempts = maxAttempts.intValue();
276 setAuthorizationProperties();
277 logger.info("switchover detector service is enabled, interval is {} seconds", detectorInterval);
279 this.switchoverDetectorScheduledTask = new SwitchoverDetectorScheduledTask();
280 startSwitchoverDetectorTask();
281 logger.trace("Exit init method of SwitchoverDetector");
286 private void destroy() {
288 if (scheduledFuture != null) {
289 scheduledFuture.cancel(true);
290 scheduledFuture = null;
293 if (switchoverDetectorScheduler != null) {
294 switchoverDetectorScheduler.shutdown();
299 public void startSwitchoverDetectorTask() {
300 if (this.scheduledFuture == null) {
301 this.scheduledFuture = this.switchoverDetectorScheduler.scheduleAtFixedRate(switchoverDetectorScheduledTask, 0, detectorInterval, TimeUnit.SECONDS);