50c6d49c70e3a032f856aeeba38fa3d00c5f464d
[appc.git] / appc-oam / appc-oam-bundle / src / main / java / org / onap / appc / oam / AppcOam.java
1 /*-
2  * ============LICENSE_START=======================================================
3  * ONAP : APPC
4  * ================================================================================
5  * Copyright (C) 2017-2019 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Copyright (C) 2017 Amdocs
8  * ================================================================================
9  * Modifications (C) 2018 Ericsson
10  * =============================================================================
11  * Licensed under the Apache License, Version 2.0 (the "License");
12  * you may not use this file except in compliance with the License.
13  * You may obtain a copy of the License at
14  * 
15  *      http://www.apache.org/licenses/LICENSE-2.0
16  * 
17  * Unless required by applicable law or agreed to in writing, software
18  * distributed under the License is distributed on an "AS IS" BASIS,
19  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20  * See the License for the specific language governing permissions and
21  * limitations under the License.
22  * 
23  * ============LICENSE_END=========================================================
24  */
25
26 package org.onap.appc.oam;
27
28 import com.att.eelf.configuration.EELFLogger;
29 import com.att.eelf.configuration.EELFManager;
30 import com.google.common.util.concurrent.Futures;
31 import com.google.common.util.concurrent.ListenableFuture;
32 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
33 import org.opendaylight.controller.sal.binding.api.BindingAwareBroker;
34 import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
35 import org.opendaylight.controller.sal.binding.api.RpcProviderRegistry;
36 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.AppcOamService;
37 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.AppcState;
38 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetAppcStateInput;
39 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetAppcStateOutput;
40 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetAppcStateOutputBuilder;
41 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetMetricsInput;
42 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetMetricsOutput;
43 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.GetMetricsOutputBuilder;
44 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.MaintenanceModeInput;
45 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.MaintenanceModeOutput;
46 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.MaintenanceModeOutputBuilder;
47 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.RestartInput;
48 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.RestartOutput;
49 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.RestartOutputBuilder;
50 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StartInput;
51 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StartOutput;
52 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StartOutputBuilder;
53 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StopInput;
54 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StopOutput;
55 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.StopOutputBuilder;
56 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.common.header.CommonHeader;
57 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.get.metrics.output.Metrics;
58 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.get.metrics.output.MetricsBuilder;
59 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.get.metrics.output.metrics.KpiValues;
60 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.get.metrics.output.metrics.KpiValuesBuilder;
61 import org.opendaylight.yang.gen.v1.org.onap.appc.oam.rev170303.status.Status;
62 import org.opendaylight.yangtools.yang.common.RpcError;
63 import org.opendaylight.yangtools.yang.common.RpcResult;
64 import org.opendaylight.yangtools.yang.common.RpcResultBuilder;
65 import org.onap.appc.exceptions.APPCException;
66 import org.onap.appc.i18n.Msg;
67 import org.onap.appc.metricservice.MetricRegistry;
68 import org.onap.appc.metricservice.MetricService;
69 import org.onap.appc.metricservice.metric.Metric;
70 import org.onap.appc.oam.processor.OamMmodeProcessor;
71 import org.onap.appc.oam.processor.OamRestartProcessor;
72 import org.onap.appc.oam.processor.OamStartProcessor;
73 import org.onap.appc.oam.processor.OamStopProcessor;
74 import org.onap.appc.oam.util.AsyncTaskHelper;
75 import org.onap.appc.oam.util.ConfigurationHelper;
76 import org.onap.appc.oam.util.OperationHelper;
77 import org.onap.appc.oam.util.StateHelper;
78 import org.onap.appc.statemachine.impl.readers.AppcOamMetaDataReader.AppcOperation;
79
80 import java.util.ArrayList;
81 import java.util.List;
82 import java.util.Map;
83 import java.util.concurrent.Future;
84
85 /**
86  * RPC class of APP-C OAM API.
87  * <p>Implement all the RPCs defined in AppcOamService through yang model definition.
88  * <p>All RPC methods' JAVADOC are using "inheritDoc" to use the description from the yang model file.
89  */
90 public class AppcOam implements AutoCloseable, AppcOamService {
91     /**
92      * Invalid state message format with fliexible operation, appc name and state values
93      */
94     public static final String INVALID_STATE_MESSAGE_FORMAT = "%s API is not allowed when %s is in the %s state.";
95
96     private final EELFLogger logger = EELFManager.getInstance().getLogger(AppcOam.class);
97
98     private boolean isMetricEnabled = false;
99
100     /**
101      * Represents our RPC implementation registration
102      */
103     private BindingAwareBroker.RpcRegistration<AppcOamService> rpcRegistration;
104
105
106     /**
107      * The yang rpc names with value mapping to AppcOperation
108      */
109     public enum RPC {
110         maintenance_mode(AppcOperation.MaintenanceMode),
111         start(AppcOperation.Start),
112         stop(AppcOperation.Stop),
113         restart(AppcOperation.Restart);
114
115         AppcOperation appcOperation;
116
117         RPC(AppcOperation appcOperation) {
118             this.appcOperation = appcOperation;
119         }
120
121         public AppcOperation getAppcOperation() {
122             return appcOperation;
123         }
124     }
125
126     private AsyncTaskHelper asyncTaskHelper;
127     private ConfigurationHelper configurationHelper;
128     private OperationHelper operationHelper;
129     private StateHelper stateHelper;
130
131     /**
132      * APP-C OAM contructor
133      *
134      * @param dataBroker                  object of The ODL data store broker. Provides access to a conceptual data
135      *                                    tree store
136      *                                    and also provides the ability to subscribe for changes to data under a
137      *                                    given branch
138      *                                    of the tree. Not used in this class.
139      * @param notificationPublishService object of ODL Notification Service that provides publish/subscribe
140      *                                    capabilities for YANG modeled notifications. Not used in this class.
141      * @param rpcProviderRegistry         object of RpcProviderResigstry. Used to register our RPCs.
142      */
143     @SuppressWarnings({"unused", "nls"})
144     public AppcOam(DataBroker dataBroker,
145                    NotificationPublishService notificationPublishService,
146                    RpcProviderRegistry rpcProviderRegistry) {
147
148         configurationHelper = new ConfigurationHelper(logger);
149         String appName = configurationHelper.getAppcName();
150         logger.info(Msg.COMPONENT_INITIALIZING, appName, "oam");
151
152         if (rpcProviderRegistry != null) {
153             rpcRegistration = rpcProviderRegistry.addRpcImplementation(AppcOamService.class, this);
154         }
155
156         isMetricEnabled = configurationHelper.isMetricEnabled();
157
158         initHelpers();
159
160         logger.info(Msg.COMPONENT_INITIALIZED, appName, "oam");
161     }
162
163     /**
164      * Initialize helper classes.
165      * <p>Note: ConfigurationHelper initializetion is in included here
166      * because it is needed for extracting the AppName used in the debug logs within the constructor.
167      */
168     private void initHelpers() {
169         operationHelper = new OperationHelper();
170         asyncTaskHelper = new AsyncTaskHelper(logger);
171         stateHelper = new StateHelper(logger, configurationHelper);
172     }
173
174     /**
175      * Implements the close of the service
176      *
177      * @see AutoCloseable#close()
178      */
179     @SuppressWarnings("nls")
180     @Override
181     public void close() throws Exception {
182         String appName = configurationHelper.getAppcName();
183         logger.info(Msg.COMPONENT_TERMINATING, appName, "oam");
184
185         asyncTaskHelper.close();
186
187         if (rpcRegistration != null) {
188             rpcRegistration.close();
189         }
190         logger.info(Msg.COMPONENT_TERMINATED, appName, "oam");
191     }
192
193     /**
194      * {@inheritDoc}
195      */
196     @Override
197     public ListenableFuture<RpcResult<GetMetricsOutput>> getMetrics(GetMetricsInput getMetricsInput) {
198
199         if (!isMetricEnabled) {
200             logger.error("Metric Service not enabled returning failure");
201             RpcResult<GetMetricsOutput> result = RpcResultBuilder.<GetMetricsOutput>
202                     status(false).withError(RpcError.ErrorType.APPLICATION, "Metric Service not enabled").build();
203             return Futures.immediateFuture(result);
204         }
205
206         MetricService metricService;
207         try {
208             metricService = operationHelper.getService(MetricService.class);
209         } catch (APPCException e) {
210             logger.error("MetricService not found", e);
211             RpcResult<GetMetricsOutput> result = RpcResultBuilder.<GetMetricsOutput>
212                     status(false).withError(RpcError.ErrorType.APPLICATION, "Metric Service not found").build();
213             return Futures.immediateFuture(result);
214         }
215
216         Map<String, MetricRegistry> allMetricRegitry = metricService.getAllRegistry();
217         if (allMetricRegitry == null || allMetricRegitry.isEmpty()) {
218             logger.error("No metrics registered returning failure");
219             RpcResult<GetMetricsOutput> result = RpcResultBuilder.<GetMetricsOutput>
220                     status(false).withError(RpcError.ErrorType.APPLICATION, "No metrics Registered").build();
221             return Futures.immediateFuture(result);
222         }
223
224         List<Metrics> metricsList = new ArrayList<>();
225
226         logger.debug("Iterating metric registry list");
227         for (MetricRegistry metricRegistry : allMetricRegitry.values()) {
228             logger.debug("Iterating metric registry :" + metricRegistry.toString());
229             Metric[] metrics = metricRegistry.metrics();
230             if (metrics != null && metrics.length > 0) {
231                 logger.debug("Iterating though metrics in registry");
232                 for (Metric metric : metrics) {
233                     logger.debug("Iterating though metrics: " + metric.name());
234                     MetricsBuilder metricsBuilder = new MetricsBuilder();
235                     metricsBuilder.setKpiName(metric.name());
236                     metricsBuilder.setLastResetTime(metric.getLastModified());
237                     List<KpiValues> kpiList = new ArrayList<>();
238                     Map<String, String> metricsOutput = metric.getMetricsOutput();
239                     for (Map.Entry<String, String> kpi : metricsOutput.entrySet()) {
240                         KpiValuesBuilder kpiValuesBuilder = new KpiValuesBuilder();
241                         kpiValuesBuilder.setName(kpi.getKey());
242                         kpiValuesBuilder.setValue(kpi.getValue());
243                         kpiList.add(kpiValuesBuilder.build());
244                     }
245                     metricsBuilder.setKpiValues(kpiList);
246                     metricsList.add(metricsBuilder.build());
247                 }
248             }
249         }
250
251         GetMetricsOutputBuilder outputBuilder = new GetMetricsOutputBuilder();
252         outputBuilder.setMetrics(metricsList);
253         RpcResult<GetMetricsOutput> result = RpcResultBuilder.<GetMetricsOutput>
254                 status(true).withResult(outputBuilder.build()).build();
255         return Futures.immediateFuture(result);
256     }
257
258     /**
259      * {@inheritDoc}
260      */
261     @Override
262     public ListenableFuture<RpcResult<StopOutput>> stop(StopInput stopInput) {
263         logger.debug("Entering Stop with Input : " + stopInput);
264         final CommonHeader commonHeader = stopInput.getCommonHeader();
265
266         OamStopProcessor oamStopProcessor =
267                 getOamStopProcessor(logger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
268         Status status = oamStopProcessor.processRequest(stopInput);
269
270         StopOutputBuilder stopOutputBuilder = new StopOutputBuilder();
271         stopOutputBuilder.setStatus(status);
272         stopOutputBuilder.setCommonHeader(commonHeader);
273         return RpcResultBuilder.success(stopOutputBuilder.build()).buildFuture();
274     }
275
276     /**
277      * {@inheritDoc}
278      */
279     @Override
280     public ListenableFuture<RpcResult<RestartOutput>> restart(RestartInput input) {
281         logger.debug("Entering restart with Input : " + input);
282         final CommonHeader commonHeader = input.getCommonHeader();
283
284         OamRestartProcessor oamRestartProcessor =
285                 getOamRestartProcessor(logger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
286         Status status = oamRestartProcessor.processRequest(input);
287
288         RestartOutputBuilder restartOutputBuilder = new RestartOutputBuilder();
289         restartOutputBuilder.setStatus(status);
290         restartOutputBuilder.setCommonHeader(commonHeader);
291
292         return RpcResultBuilder.success(restartOutputBuilder.build()).buildFuture();
293     }
294
295     /**
296      * {@inheritDoc}
297      */
298     @Override
299     public ListenableFuture<RpcResult<MaintenanceModeOutput>> maintenanceMode(MaintenanceModeInput maintenanceModeInput) {
300         logger.debug("Entering MaintenanceMode with Input : " + maintenanceModeInput);
301         final CommonHeader commonHeader = maintenanceModeInput.getCommonHeader();
302
303         OamMmodeProcessor oamMmodeProcessor =
304                 getOamMmodeProcessor(logger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
305         Status status = oamMmodeProcessor.processRequest(maintenanceModeInput);
306
307         MaintenanceModeOutputBuilder maintenanceModeOutputBuilder = new MaintenanceModeOutputBuilder();
308         maintenanceModeOutputBuilder.setStatus(status);
309         maintenanceModeOutputBuilder.setCommonHeader(commonHeader);
310         return RpcResultBuilder.success(maintenanceModeOutputBuilder.build()).buildFuture();
311     }
312
313     /**
314      * {@inheritDoc}
315      */
316     @Override
317     public ListenableFuture<RpcResult<GetAppcStateOutput>> getAppcState(GetAppcStateInput getAppcStateInput) {
318         AppcState appcState = stateHelper.getCurrentOamYangState();
319
320         GetAppcStateOutputBuilder builder = new GetAppcStateOutputBuilder();
321         builder.setState(appcState);
322         return RpcResultBuilder.success(builder.build()).buildFuture();
323     }
324
325     /**
326      * {@inheritDoc}
327      */
328     @Override
329     public ListenableFuture<RpcResult<StartOutput>> start(StartInput startInput) {
330         logger.debug("Input received : " + startInput);
331         final CommonHeader commonHeader = startInput.getCommonHeader();
332
333         OamStartProcessor oamStartProcessor =
334                 getOamStartProcessor(logger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
335         Status status = oamStartProcessor.processRequest(startInput);
336
337         StartOutputBuilder startOutputBuilder = new StartOutputBuilder();
338         startOutputBuilder.setStatus(status);
339         startOutputBuilder.setCommonHeader(commonHeader);
340         StartOutput startOutput = startOutputBuilder.build();
341         return RpcResultBuilder.success(startOutput).buildFuture();
342     }
343
344     protected OamStartProcessor getOamStartProcessor(EELFLogger eelfLogger,
345             ConfigurationHelper configurationHelper,
346             StateHelper stateHelper,
347             AsyncTaskHelper asyncTaskHelper,
348             OperationHelper operationHelper) {
349         return new OamStartProcessor(eelfLogger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
350     }
351
352     protected OamStopProcessor getOamStopProcessor(EELFLogger eelfLogger,
353             ConfigurationHelper configurationHelper,
354             StateHelper stateHelper,
355             AsyncTaskHelper asyncTaskHelper,
356             OperationHelper operationHelper) {
357         return new OamStopProcessor(eelfLogger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
358     }
359
360     protected OamRestartProcessor getOamRestartProcessor(EELFLogger eelfLogger,
361             ConfigurationHelper configurationHelper,
362             StateHelper stateHelper,
363             AsyncTaskHelper asyncTaskHelper,
364             OperationHelper operationHelper) {
365         return new OamRestartProcessor(eelfLogger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
366     }
367
368     protected OamMmodeProcessor getOamMmodeProcessor(EELFLogger eelfLogger,
369             ConfigurationHelper configurationHelper,
370             StateHelper stateHelper,
371             AsyncTaskHelper asyncTaskHelper,
372             OperationHelper operationHelper) {
373         return new OamMmodeProcessor(eelfLogger, configurationHelper, stateHelper, asyncTaskHelper, operationHelper);
374     }
375 }