2 * ============LICENSE_START=======================================================
4 * ================================================================================
5 * Copyright (C) 2017 AT&T Intellectual Property. All rights
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
12 * http://www.apache.org/licenses/LICENSE-2.0
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 * ECOMP is a trademark and service mark of AT&T Intellectual Property.
24 package org.onap.clamp.clds.service;
26 import java.io.IOException;
27 import java.io.InputStream;
28 import java.sql.SQLException;
29 import java.util.Date;
30 import java.util.HashMap;
31 import java.util.List;
33 import java.util.Properties;
34 import java.util.UUID;
35 import java.util.concurrent.TimeUnit;
37 import javax.annotation.PostConstruct;
38 import javax.ws.rs.Consumes;
39 import javax.ws.rs.DefaultValue;
40 import javax.ws.rs.GET;
41 import javax.ws.rs.NotAuthorizedException;
42 import javax.ws.rs.POST;
43 import javax.ws.rs.PUT;
44 import javax.ws.rs.Path;
45 import javax.ws.rs.PathParam;
46 import javax.ws.rs.Produces;
47 import javax.ws.rs.QueryParam;
48 import javax.ws.rs.core.MediaType;
49 import javax.xml.transform.TransformerConfigurationException;
50 import javax.xml.transform.TransformerException;
52 import org.apache.commons.lang3.StringUtils;
53 import org.camunda.bpm.engine.RuntimeService;
54 import org.camunda.bpm.engine.runtime.ProcessInstance;
55 import org.jboss.resteasy.spi.BadRequestException;
56 import org.onap.clamp.clds.client.DcaeDispatcherServices;
57 import org.onap.clamp.clds.client.DcaeInventoryServices;
58 import org.onap.clamp.clds.client.SdcCatalogServices;
59 import org.onap.clamp.clds.dao.CldsDao;
60 import org.onap.clamp.clds.model.CldsDBServiceCache;
61 import org.onap.clamp.clds.model.CldsEvent;
62 import org.onap.clamp.clds.model.CldsHealthCheck;
63 import org.onap.clamp.clds.model.CldsInfo;
64 import org.onap.clamp.clds.model.CldsModel;
65 import org.onap.clamp.clds.model.CldsSdcResource;
66 import org.onap.clamp.clds.model.CldsSdcServiceDetail;
67 import org.onap.clamp.clds.model.CldsSdcServiceInfo;
68 import org.onap.clamp.clds.model.CldsServiceData;
69 import org.onap.clamp.clds.model.CldsTemplate;
70 import org.onap.clamp.clds.model.DcaeEvent;
71 import org.onap.clamp.clds.model.ValueItem;
72 import org.onap.clamp.clds.model.prop.ModelProperties;
73 import org.onap.clamp.clds.model.refprop.RefProp;
74 import org.onap.clamp.clds.transform.XslTransformer;
75 import org.onap.clamp.clds.util.LoggingUtils;
76 import org.springframework.beans.factory.annotation.Autowired;
77 import org.springframework.beans.factory.annotation.Value;
78 import org.springframework.context.ApplicationContext;
80 import com.att.ajsc.common.AjscService;
81 import com.att.eelf.configuration.EELFLogger;
82 import com.att.eelf.configuration.EELFManager;
83 import com.fasterxml.jackson.core.JsonProcessingException;
84 import com.fasterxml.jackson.databind.JsonNode;
85 import com.fasterxml.jackson.databind.ObjectMapper;
86 import com.fasterxml.jackson.databind.node.ObjectNode;
88 import io.swagger.annotations.Api;
89 import io.swagger.annotations.ApiOperation;
92 * Service to save and retrieve the CLDS model attributes.
95 @Api(value = "/clds", description = "Clds operations")
97 public class CldsService extends SecureServiceBase {
100 private ApplicationContext appContext;
102 private static final String RESOURCE_NAME = "clds-version.properties";
104 protected static final EELFLogger logger = EELFManager.getInstance().getLogger(CldsService.class);
105 protected static final EELFLogger auditLogger = EELFManager.getInstance().getAuditLogger();
107 @Value("${CLDS_PERMISSION_TYPE_CL:permission-type-cl}")
108 private String cldsPersmissionTypeCl;
110 @Value("${CLDS_PERMISSION_TYPE_CL_MANAGE:permission-type-cl-manage}")
111 private String cldsPermissionTypeClManage;
113 @Value("${CLDS_PERMISSION_TYPE_CL_EVENT:permission-type-cl-event}")
114 private String cldsPermissionTypeClEvent;
116 @Value("${CLDS_PERMISSION_TYPE_FILTER_VF:permission-type-filter-vf}")
117 private String cldsPermissionTypeFilterVf;
119 @Value("${CLDS_PERMISSION_TYPE_TEMPLATE:permission-type-template}")
120 private String cldsPermissionTypeTemplate;
122 @Value("${CLDS_PERMISSION_INSTANCE:dev}")
123 private String cldsPermissionInstance;
125 private SecureServicePermission permissionReadCl;
127 private SecureServicePermission permissionUpdateCl;
129 private SecureServicePermission permissionReadTemplate;
131 private SecureServicePermission permissionUpdateTemplate;
134 private final void afterConstruction() {
135 permissionReadCl = SecureServicePermission.create(cldsPersmissionTypeCl, cldsPermissionInstance, "read");
136 permissionUpdateCl = SecureServicePermission.create(cldsPersmissionTypeCl, cldsPermissionInstance, "update");
137 permissionReadTemplate = SecureServicePermission.create(cldsPermissionTypeTemplate, cldsPermissionInstance,
139 permissionUpdateTemplate = SecureServicePermission.create(cldsPermissionTypeTemplate, cldsPermissionInstance,
143 @Value("${org.onap.clamp.config.files.globalClds:'classpath:/clds/globalClds.properties'}")
144 private String globalClds;
146 private Properties globalCldsProperties;
149 private CldsDao cldsDao;
151 private RuntimeService runtimeService;
153 private XslTransformer cldsBpmnTransformer;
156 private RefProp refProp;
159 private SdcCatalogServices sdcCatalogServices;
162 private DcaeDispatcherServices dcaeDispatcherServices;
165 private DcaeInventoryServices dcaeInventoryServices;
167 public CldsService() {
170 public CldsService(RefProp refProp) {
171 this.refProp = refProp;
176 * CLDS IFO service will return 3 things 1. User Name 2. CLDS code version
177 * that is currently installed from pom.xml file 3. User permissions
183 @Produces(MediaType.APPLICATION_JSON)
184 public CldsInfo getCldsInfo() {
186 CldsInfo cldsInfo = new CldsInfo();
189 cldsInfo.setUserName(getUserName());
191 // Get CLDS application version
192 String cldsVersion = "";
193 Properties props = new Properties();
194 InputStream resourceStream = null;
197 ClassLoader loader = Thread.currentThread().getContextClassLoader();
198 resourceStream = loader.getResourceAsStream(RESOURCE_NAME);
199 props.load(resourceStream);
200 cldsVersion = props.getProperty("clds.version");
201 } catch (Exception ex) {
202 ex.printStackTrace();
204 if (resourceStream != null) {
206 resourceStream.close();
207 } catch (IOException e) {
212 cldsInfo.setCldsVersion(cldsVersion);
214 // Get the user list of permissions
215 cldsInfo.setPermissionReadCl(isAuthorized(permissionReadCl));
216 cldsInfo.setPermissionUpdateCl(isAuthorized(permissionUpdateCl));
217 cldsInfo.setPermissionReadTemplate(isAuthorized(permissionReadTemplate));
218 cldsInfo.setPermissionUpdateTemplate(isAuthorized(permissionUpdateTemplate));
223 @Path("/healthcheck")
224 @Produces(MediaType.APPLICATION_JSON)
225 public CldsHealthCheck gethealthcheck() {
227 CldsHealthCheck cldsHealthCheck = new CldsHealthCheck();
230 cldsDao.doHealthCheck();
231 cldsHealthCheck.setHealthCheckComponent("CLDS-APP");
232 cldsHealthCheck.setHealthCheckStatus("UP");
233 cldsHealthCheck.setDescription("OK");
234 } catch (SQLException e) {
235 logger.error("CLAMP application DB Error" + e);
236 cldsHealthCheck.setHealthCheckComponent("CLDS-APP");
237 cldsHealthCheck.setHealthCheckStatus("DOWN");
238 cldsHealthCheck.setDescription("NOT-OK");
239 // return Response.status(500).entity("Database down for CLDS
240 // application").build();
241 } catch (Exception e) {
242 logger.error("CLAMP application DB Error" + e);
243 cldsHealthCheck.setHealthCheckComponent("CLDS-APP");
244 cldsHealthCheck.setHealthCheckStatus("DOWN");
245 cldsHealthCheck.setDescription("NOT-OK");
246 // return Response.status(500).entity("Database down for CLDS
247 // application").build();
250 return cldsHealthCheck;
255 * REST service that retrieves BPMN for a CLDS model name from the database.
256 * This is subset of the json getModel. This is only expected to be used for
257 * testing purposes, not by the UI.
260 * @return bpmn xml text - content of bpmn given name
262 @ApiOperation(value = "Retrieves BPMN for a CLDS model name from the database", notes = "This is only expected to be used for testing purposes, not by the UI", response = String.class)
264 @Path("/model/bpmn/{modelName}")
265 @Produces(MediaType.TEXT_XML)
266 public String getBpmnXml(@PathParam("modelName") String modelName) {
267 Date startTime = new Date();
268 LoggingUtils.setRequestContext("CldsService: GET model bpmn", getPrincipalName());
269 isAuthorized(permissionReadCl);
270 logger.info("GET bpmnText for modelName={}", modelName);
271 CldsModel model = CldsModel.retrieve(cldsDao, modelName, false);
273 LoggingUtils.setTimeContext(startTime, new Date());
274 LoggingUtils.setResponseContext("0", "Get model bpmn success", this.getClass().getName());
275 auditLogger.info("GET model bpmn completed");
276 return model.getBpmnText();
280 * REST service that saves BPMN for a CLDS model by name in the database.
281 * This is subset of the json putModel. This is only expected to be used for
282 * testing purposes, not by the UI.
286 @ApiOperation(value = "Saves BPMN for a CLDS model by name in the database", notes = "This is only expected to be used for testing purposes, not by the UI", response = String.class)
288 @Path("/model/bpmn/{modelName}")
289 @Consumes(MediaType.TEXT_XML)
290 public String putBpmnXml(@PathParam("modelName") String modelName, String bpmnText) {
291 LoggingUtils.setRequestContext("CldsService: PUT model bpmn", getPrincipalName());
292 isAuthorized(permissionUpdateCl);
293 logger.info("PUT bpmnText for modelName={}", modelName);
294 logger.info("PUT bpmnText={}", bpmnText);
295 CldsModel cldsModel = CldsModel.retrieve(cldsDao, modelName, true);
296 cldsModel.setBpmnText(bpmnText);
297 cldsModel.save(cldsDao, getUserId());
299 LoggingUtils.setTimeContext(new Date(), new Date());
300 LoggingUtils.setResponseContext("0", "Put model bpmn success", this.getClass().getName());
301 auditLogger.info("PUT model bpmn completed");
302 return "wrote bpmnText for modelName=" + modelName;
306 * REST service that retrieves image for a CLDS model name from the
307 * database. This is subset of the json getModel. This is only expected to
308 * be used for testing purposes, not by the UI.
311 * @return image xml text - content of image given name
313 @ApiOperation(value = "Retrieves image for a CLDS model name from the database", notes = "This is only expected to be used for testing purposes, not by the UI", response = String.class)
315 @Path("/model/image/{modelName}")
316 @Produces(MediaType.TEXT_XML)
317 public String getImageXml(@PathParam("modelName") String modelName) {
318 Date startTime = new Date();
319 LoggingUtils.setRequestContext("CldsService: GET model image", getPrincipalName());
320 isAuthorized(permissionReadCl);
321 logger.info("GET imageText for modelName={}", modelName);
322 CldsModel model = CldsModel.retrieve(cldsDao, modelName, false);
324 LoggingUtils.setTimeContext(startTime, new Date());
325 LoggingUtils.setResponseContext("0", "Get model image success", this.getClass().getName());
326 auditLogger.info("GET model image completed");
327 return model.getImageText();
331 * REST service that saves image for a CLDS model by name in the database.
332 * This is subset of the json putModel. This is only expected to be used for
333 * testing purposes, not by the UI.
337 @ApiOperation(value = "Saves image for a CLDS model by name in the database", notes = "This is only expected to be used for testing purposes, not by the UI", response = String.class)
339 @Path("/model/image/{modelName}")
340 @Consumes(MediaType.TEXT_XML)
341 public String putImageXml(@PathParam("modelName") String modelName, String imageText) {
342 Date startTime = new Date();
343 LoggingUtils.setRequestContext("CldsService: PUT model image", getPrincipalName());
344 isAuthorized(permissionUpdateCl);
345 logger.info("PUT iamgeText for modelName={}", modelName);
346 logger.info("PUT imageText={}", imageText);
347 CldsModel cldsModel = CldsModel.retrieve(cldsDao, modelName, true);
348 cldsModel.setImageText(imageText);
349 cldsModel.save(cldsDao, getUserId());
351 LoggingUtils.setTimeContext(startTime, new Date());
352 LoggingUtils.setResponseContext("0", "Put model image success", this.getClass().getName());
353 auditLogger.info("PUT model image completed");
354 return "wrote imageText for modelName=" + modelName;
358 * REST service that retrieves a CLDS model by name from the database.
361 * @return clds model - clds model for the given model name
362 * @throws NotAuthorizedException
364 @ApiOperation(value = "Retrieves a CLDS model by name from the database", notes = "", response = String.class)
366 @Path("/model/{modelName}")
367 @Produces(MediaType.APPLICATION_JSON)
368 public CldsModel getModel(@PathParam("modelName") String modelName) throws NotAuthorizedException {
369 Date startTime = new Date();
370 LoggingUtils.setRequestContext("CldsService: GET model", getPrincipalName());
371 isAuthorized(permissionReadCl);
372 logger.debug("GET model for modelName={}", modelName);
373 CldsModel cldsModel = CldsModel.retrieve(cldsDao, modelName, false);
374 isAuthorizedForVf(cldsModel);
375 cldsModel.setUserAuthorizedToUpdate(isAuthorizedNoException(permissionUpdateCl));
378 * Checking condtion whether our CLDS model can call INventory Method
380 if (cldsModel.canInventoryCall()) {
383 * Below is the method to for inventory call and DB insert for
386 dcaeInventoryServices.setEventInventory(cldsModel, getUserId());
387 } catch (Exception e) {
388 LoggingUtils.setErrorContext("900", "Set event inventory error");
389 logger.error("getModel set event Inventory error:" + e);
393 LoggingUtils.setTimeContext(startTime, new Date());
394 LoggingUtils.setResponseContext("0", "Get model success", this.getClass().getName());
395 auditLogger.info("GET model completed");
400 * REST service that saves a CLDS model by name in the database.
403 * @throws TransformerException
404 * @throws TransformerConfigurationException
406 @ApiOperation(value = "Saves a CLDS model by name in the database", notes = "", response = String.class)
408 @Path("/model/{modelName}")
409 @Consumes(MediaType.APPLICATION_JSON)
410 @Produces(MediaType.APPLICATION_JSON)
411 public CldsModel putModel(@PathParam("modelName") String modelName, CldsModel cldsModel)
412 throws TransformerException {
413 Date startTime = new Date();
414 LoggingUtils.setRequestContext("CldsService: PUT model", getPrincipalName());
415 isAuthorized(permissionUpdateCl);
416 isAuthorizedForVf(cldsModel);
417 logger.info("PUT model for modelName={}", modelName);
418 logger.info("PUT bpmnText={}", cldsModel.getBpmnText());
419 logger.info("PUT propText={}", cldsModel.getPropText());
420 logger.info("PUT imageText={}", cldsModel.getImageText());
421 cldsModel.setName(modelName);
423 if (cldsModel.getTemplateName() != null) {
424 CldsTemplate template = cldsDao.getTemplate(cldsModel.getTemplateName());
425 if (template != null) {
426 cldsModel.setTemplateId(template.getId());
427 cldsModel.setDocText(template.getPropText());
428 cldsModel.setDocId(template.getPropId());
431 cldsModel.save(cldsDao, getUserId());
432 cldsModel.save(cldsDao, getUserId());
434 LoggingUtils.setTimeContext(startTime, new Date());
435 LoggingUtils.setResponseContext("0", "Put model success", this.getClass().getName());
436 auditLogger.info("PUT model completed");
441 * REST service that retrieves a list of CLDS model names.
443 * @return model names in JSON
445 @ApiOperation(value = "Retrieves a list of CLDS model names", notes = "", response = String.class)
447 @Path("/model-names")
448 @Produces(MediaType.APPLICATION_JSON)
449 public List<ValueItem> getModelNames() {
450 // isAuthorized(permissionReadCl);
451 Date startTime = new Date();
452 LoggingUtils.setRequestContext("CldsService: GET model names", getPrincipalName());
453 logger.info("GET list of model names");
454 List<ValueItem> names = cldsDao.getBpmnNames();
456 LoggingUtils.setTimeContext(startTime, new Date());
457 LoggingUtils.setResponseContext("0", "Get model names success", this.getClass().getName());
458 auditLogger.info("GET model names completed");
463 * REST service that saves and processes an action for a CLDS model by name.
471 * @throws JsonProcessingException
472 * @throws NotAuthorizedException
474 @ApiOperation(value = "Saves and processes an action for a CLDS model by name", notes = "", response = String.class)
476 @Path("/action/{action}/{modelName}")
477 @Consumes(MediaType.APPLICATION_JSON)
478 @Produces(MediaType.APPLICATION_JSON)
479 public CldsModel putModelAndProcessAction(@PathParam("action") String action,
480 @PathParam("modelName") String modelName, @QueryParam("test") String test, CldsModel model)
482 Date startTime = new Date();
483 LoggingUtils.setRequestContext("CldsService: Process model action", getPrincipalName());
484 String actionCd = action.toUpperCase();
485 SecureServicePermission permisionManage = SecureServicePermission.create(cldsPermissionTypeClManage,
486 cldsPermissionInstance, actionCd);
487 isAuthorized(permisionManage);
488 isAuthorizedForVf(model);
489 String userid = getUserId();
490 String actionStateCd = CldsEvent.ACTION_STATE_INITIATED;
491 String processDefinitionKey = "clds-process-action-wf";
493 logger.info("PUT actionCd={}", actionCd);
494 logger.info("PUT actionStateCd={}", actionStateCd);
495 logger.info("PUT processDefinitionKey={}", processDefinitionKey);
496 logger.info("PUT modelName={}", modelName);
497 logger.info("PUT test={}", test);
498 logger.info("PUT bpmnText={}", model.getBpmnText());
499 logger.info("PUT propText={}", model.getPropText());
500 logger.info("PUT userid={}", userid);
501 logger.info("PUT getTypeId={}", model.getTypeId());
502 logger.info("PUT deploymentId={}", model.getDeploymentId());
504 if (model.getTemplateName() != null) {
505 CldsTemplate template = cldsDao.getTemplate(model.getTemplateName());
506 if (template != null) {
507 model.setTemplateId(template.getId());
508 model.setDocText(template.getPropText());
509 model.setDocId(template.getPropId());
513 model.setName(modelName);
514 model.save(cldsDao, getUserId());
516 // get vars and format if necessary
517 String prop = model.getPropText();
518 String bpmn = model.getBpmnText();
519 String docText = model.getDocText();
520 String controlName = model.getControlName();
522 String bpmnJson = cldsBpmnTransformer.doXslTransformToString(bpmn);
523 logger.info("PUT bpmnJson={}", bpmnJson);
525 // Flag indicates whether it is triggered by Validation Test button from UI
526 boolean isTest = false;
527 if (test != null && test.equalsIgnoreCase("true")) {
530 // if action.test.override is true, then any action will be marked
531 // as test=true (even if incoming action request had test=false);
532 // otherwise, test flag will be unchanged on the action request
533 String actionTestOverride = refProp.getStringValue("action.test.override");
534 if (actionTestOverride != null && actionTestOverride.equalsIgnoreCase("true")) {
535 logger.info("PUT actionTestOverride={}", actionTestOverride);
536 logger.info("PUT override test indicator and setting it to true");
540 logger.info("PUT isTest={}", isTest);
542 boolean isInsertTestEvent = false;
543 String insertTestEvent = refProp.getStringValue("action.insert.test.event");
544 if (insertTestEvent != null && insertTestEvent.equalsIgnoreCase("true")) {
545 isInsertTestEvent = true;
547 logger.info("PUT isInsertTestEvent={}", isInsertTestEvent);
549 // determine if requested action is permitted
550 model.validateAction(actionCd);
552 // input variables to camunda process
553 Map<String, Object> variables = new HashMap<>();
554 variables.put("actionCd", actionCd);
555 variables.put("modelProp", prop.getBytes());
556 variables.put("modelBpmnProp", bpmnJson);
557 variables.put("modelName", modelName);
558 variables.put("controlName", controlName);
559 variables.put("docText", docText.getBytes());
560 variables.put("isTest", isTest);
561 variables.put("userid", userid);
562 variables.put("isInsertTestEvent", isInsertTestEvent);
563 logger.info("modelProp - " + prop);
564 logger.info("docText - " + docText);
566 // start camunda process
567 ProcessInstance pi = runtimeService.startProcessInstanceByKey(processDefinitionKey, variables);
570 logger.info("Started processDefinitionId={}, processInstanceId={}", pi.getProcessDefinitionId(),
571 pi.getProcessInstanceId());
573 // refresh model info from db (get fresh event info)
574 CldsModel retreivedModel = CldsModel.retrieve(cldsDao, modelName, false);
576 if (actionCd.equalsIgnoreCase(CldsEvent.ACTION_SUBMIT)
577 || actionCd.equalsIgnoreCase(CldsEvent.ACTION_RESUBMIT)) {
578 // To verify inventory status and modify model status to distribute
579 dcaeInventoryServices.setEventInventory(retreivedModel, getUserId());
580 retreivedModel.save(cldsDao, getUserId());
583 LoggingUtils.setTimeContext(startTime, new Date());
584 LoggingUtils.setResponseContext("0", "Process model action success", this.getClass().getName());
585 auditLogger.info("Process model action completed");
587 return retreivedModel;
591 * REST service that accepts events for a model.
595 * @throws BadRequestException
597 @ApiOperation(value = "Accepts events for a model", notes = "", response = String.class)
600 @Consumes(MediaType.APPLICATION_JSON)
601 @Produces(MediaType.APPLICATION_JSON)
602 public String postDcaeEvent(@QueryParam("test") String test, DcaeEvent dcaeEvent) throws BadRequestException {
603 Date startTime = new Date();
604 LoggingUtils.setRequestContext("CldsService: Post dcae event", getPrincipalName());
605 String userid = null;
606 // TODO: allow auth checking to be turned off by removing the permission
608 if (cldsPermissionTypeClEvent != null && cldsPermissionTypeClEvent.length() > 0) {
609 SecureServicePermission permissionEvent = SecureServicePermission.create(cldsPermissionTypeClEvent,
610 cldsPermissionInstance, dcaeEvent.getEvent());
611 isAuthorized(permissionEvent);
612 userid = getUserId();
615 // Flag indicates whether it is triggered by Validation Test button from UI
616 boolean isTest = false;
617 if (test != null && test.equalsIgnoreCase("true")) {
621 int instanceCount = 0;
622 if (dcaeEvent.getInstances() != null) {
623 instanceCount = dcaeEvent.getInstances().size();
625 String msgInfo = "event=" + dcaeEvent.getEvent() + " serviceUUID=" + dcaeEvent.getServiceUUID()
626 + " resourceUUID=" + dcaeEvent.getResourceUUID() + " artifactName=" + dcaeEvent.getArtifactName()
627 + " instance count=" + instanceCount + " isTest=" + isTest;
628 logger.info("POST dcae event {}", msgInfo);
631 logger.warn("Ignorning test event from DCAE");
633 if (DcaeEvent.EVENT_DEPLOYMENT.equalsIgnoreCase(dcaeEvent.getEvent())) {
634 CldsModel.insertModelInstance(cldsDao, dcaeEvent, userid);
636 CldsEvent.insEvent(cldsDao, dcaeEvent.getControlName(), userid, dcaeEvent.getCldsActionCd(),
637 CldsEvent.ACTION_STATE_RECEIVED, null);
641 LoggingUtils.setTimeContext(startTime, new Date());
642 LoggingUtils.setResponseContext("0", "Post dcae event success", this.getClass().getName());
643 auditLogger.info("Post dcae event completed");
649 * REST service that retrieves sdc services
653 @ApiOperation(value = "Retrieves sdc services", notes = "", response = String.class)
655 @Path("/sdc/services")
656 @Produces(MediaType.APPLICATION_JSON)
657 public String getSdcServices() throws Exception {
658 Date startTime = new Date();
659 LoggingUtils.setRequestContext("CldsService: GET sdc services", getPrincipalName());
662 String responseStr = sdcCatalogServices.getSdcServicesInformation(null);
663 retStr = createUiServiceFormatJson(responseStr);
664 } catch (Exception e) {
665 logger.info("{} {}", e.getClass().getName(), e.getMessage());
668 logger.info("value of sdcServices : {}", retStr);
670 LoggingUtils.setTimeContext(startTime, new Date());
671 LoggingUtils.setResponseContext("0", "Get sdc services success", this.getClass().getName());
672 auditLogger.info("GET sdc services completed");
677 * REST service that retrieves total properties required by UI
681 @ApiOperation(value = "Retrieves total properties required by UI", notes = "", response = String.class)
684 @Produces(MediaType.APPLICATION_JSON)
685 public String getSdcProperties() throws Exception {
686 return createPropertiesObjectByUUID(getGlobalCldsString(), "{}");
690 * REST service that retrieves total properties by using invariantUUID based
691 * on refresh and non refresh
695 @ApiOperation(value = "Retrieves total properties by using invariantUUID based on refresh and non refresh", notes = "", response = String.class)
697 @Path("/properties/{serviceInvariantUUID}")
698 @Produces(MediaType.APPLICATION_JSON)
699 public String getSdcPropertiesByServiceUUIDForRefresh(
700 @PathParam("serviceInvariantUUID") String serviceInvariantUUID,
701 @DefaultValue("false") @QueryParam("refresh") String refresh) throws Exception {
702 Date startTime = new Date();
703 LoggingUtils.setRequestContext("CldsService: GET sdc properties by uuid", getPrincipalName());
704 CldsServiceData cldsServiceData = new CldsServiceData();
705 cldsServiceData.setServiceInvariantUUID(serviceInvariantUUID);
707 boolean isCldsSdcDataExpired = true;
708 // To getcldsService information from database cache using invariantUUID
709 // only when refresh = false
710 if (refresh != null && refresh.equalsIgnoreCase("false")) {
711 cldsServiceData = cldsServiceData.getCldsServiceCache(cldsDao, serviceInvariantUUID);
712 // If cldsService is available in database Cache , verify is data
714 if (cldsServiceData != null) {
715 isCldsSdcDataExpired = sdcCatalogServices.isCldsSdcCacheDataExpired(cldsServiceData);
718 // If user Requested for refresh or database cache expired , get all
719 // data from sdc api.
720 if ((refresh != null && refresh.equalsIgnoreCase("true")) || isCldsSdcDataExpired) {
721 cldsServiceData = sdcCatalogServices.getCldsServiceDataWithAlarmConditions(serviceInvariantUUID);
722 CldsDBServiceCache cldsDBServiceCache = sdcCatalogServices
723 .getCldsDbServiceCacheUsingCldsServiceData(cldsServiceData);
724 if (cldsDBServiceCache != null && cldsDBServiceCache.getInvariantId() != null
725 && cldsDBServiceCache.getServiceId() != null) {
726 cldsServiceData.setCldsServiceCache(cldsDao, cldsDBServiceCache);
730 // filter out VFs the user is not authorized for
731 cldsServiceData.filterVfs(this);
734 LoggingUtils.setTimeContext(startTime, new Date());
735 LoggingUtils.setResponseContext("0", "Get sdc properties by uuid success", this.getClass().getName());
736 auditLogger.info("GET sdc properties by uuid completed");
738 // format retrieved data into properties json
739 return sdcCatalogServices.createPropertiesObjectByUUID(getGlobalCldsString(), cldsServiceData);
743 * Determine if the user is authorized for a particular VF by its invariant
746 * @param vfInvariantUuid
747 * @throws NotAuthorizedException
750 public boolean isAuthorizedForVf(String vfInvariantUuid) throws NotAuthorizedException {
751 if (cldsPermissionTypeFilterVf != null && cldsPermissionTypeFilterVf.length() > 0) {
752 SecureServicePermission permission = SecureServicePermission.create(cldsPermissionTypeFilterVf,
753 cldsPermissionInstance, vfInvariantUuid);
754 return isAuthorized(permission);
756 // if CLDS_PERMISSION_TYPE_FILTER_VF property is not provided, then
757 // VF filtering is turned off
758 logger.warn("VF filtering turned off");
764 * Determine if the user is authorized for a particular VF by its invariant
765 * UUID. If not authorized, then NotAuthorizedException is thrown.
770 private boolean isAuthorizedForVf(CldsModel model) throws NotAuthorizedException {
771 String vf = ModelProperties.getVf(model);
772 if (vf == null || vf.length() == 0) {
773 logger.info("VF not found in model");
776 return isAuthorizedForVf(vf);
780 private String createUiServiceFormatJson(String responseStr) throws IOException {
781 if (StringUtils.isBlank(responseStr)) {
784 ObjectMapper objectMapper = new ObjectMapper();
785 List<CldsSdcServiceInfo> rawList = objectMapper.readValue(responseStr,
786 objectMapper.getTypeFactory().constructCollectionType(List.class, CldsSdcServiceInfo.class));
787 ObjectNode invariantIdServiceNode = objectMapper.createObjectNode();
788 ObjectNode serviceNode = objectMapper.createObjectNode();
789 logger.info("value of cldsserviceiNfolist: {}", rawList);
790 if (rawList != null && rawList.size() > 0) {
791 List<CldsSdcServiceInfo> cldsSdcServiceInfoList = sdcCatalogServices.removeDuplicateServices(rawList);
793 for (CldsSdcServiceInfo currCldsSdcServiceInfo : cldsSdcServiceInfoList) {
794 if (currCldsSdcServiceInfo != null) {
795 invariantIdServiceNode.put(currCldsSdcServiceInfo.getInvariantUUID(),
796 currCldsSdcServiceInfo.getName());
799 serviceNode.putPOJO("service", invariantIdServiceNode);
801 return serviceNode.toString();
804 private String createPropertiesObjectByUUID(String globalProps, String cldsResponseStr) throws IOException {
805 ObjectMapper mapper = new ObjectMapper();
806 CldsSdcServiceDetail cldsSdcServiceDetail = mapper.readValue(cldsResponseStr, CldsSdcServiceDetail.class);
807 ObjectNode globalPropsJson = null;
808 if (cldsSdcServiceDetail != null && cldsSdcServiceDetail.getUuid() != null) {
810 * to create json with vf, alarm and locations
812 ObjectNode serviceObjectNode = createEmptyVfAlarmObject(mapper);
813 ObjectNode vfObjectNode = mapper.createObjectNode();
816 * to create json with vf and vfresourceId
818 createVfObjectNode(vfObjectNode, mapper, cldsSdcServiceDetail.getResources());
819 serviceObjectNode.putPOJO(cldsSdcServiceDetail.getInvariantUUID(), vfObjectNode);
820 ObjectNode byServiceBasicObjetNode = mapper.createObjectNode();
821 byServiceBasicObjetNode.putPOJO("byService", serviceObjectNode);
824 * to create json with VFC Node
826 ObjectNode emptyvfcobjectNode = createByVFCObjectNode(mapper, cldsSdcServiceDetail.getResources());
827 byServiceBasicObjetNode.putPOJO("byVf", emptyvfcobjectNode);
828 globalPropsJson = (ObjectNode) mapper.readValue(globalProps, JsonNode.class);
829 globalPropsJson.putPOJO("shared", byServiceBasicObjetNode);
830 logger.info("valuie of objNode: {}", globalPropsJson);
833 * to create json with total properties when no serviceUUID passed
835 globalPropsJson = (ObjectNode) mapper.readValue(globalProps, JsonNode.class);
837 return globalPropsJson.toString();
840 private ObjectNode createEmptyVfAlarmObject(ObjectMapper mapper) {
841 ObjectNode emptyObjectNode = mapper.createObjectNode();
842 emptyObjectNode.put("", "");
843 ObjectNode vfObjectNode = mapper.createObjectNode();
844 vfObjectNode.putPOJO("vf", emptyObjectNode);
845 vfObjectNode.putPOJO("location", emptyObjectNode);
846 vfObjectNode.putPOJO("alarmCondition", emptyObjectNode);
847 ObjectNode emptyServiceObjectNode = mapper.createObjectNode();
848 emptyServiceObjectNode.putPOJO("", vfObjectNode);
849 return emptyServiceObjectNode;
852 private void createVfObjectNode(ObjectNode vfObjectNode2, ObjectMapper mapper,
853 List<CldsSdcResource> rawCldsSdcResourceList) throws IOException {
854 ObjectNode vfNode = mapper.createObjectNode();
857 // To remove repeated resource instance name from resourceInstanceList
858 List<CldsSdcResource> cldsSdcResourceList = sdcCatalogServices
859 .removeDuplicateSdcResourceInstances(rawCldsSdcResourceList);
861 * Creating vf resource node using cldsSdcResource Object
863 if (cldsSdcResourceList != null && cldsSdcResourceList.size() > 0) {
864 for (CldsSdcResource cldsSdcResource : cldsSdcResourceList) {
865 if (cldsSdcResource != null && cldsSdcResource.getResoucreType() != null
866 && cldsSdcResource.getResoucreType().equalsIgnoreCase("VF")) {
867 vfNode.put(cldsSdcResource.getResourceUUID(), cldsSdcResource.getResourceName());
871 vfObjectNode2.putPOJO("vf", vfNode);
872 String locationStringValue = refProp.getStringValue("ui.location.default");
873 String alarmStringValue = refProp.getStringValue("ui.alarm.default");
876 * creating location json object using properties file value
878 ObjectNode locationJsonNode = (ObjectNode) mapper.readValue(locationStringValue, JsonNode.class);
879 vfObjectNode2.putPOJO("location", locationJsonNode);
882 * creating alarm json object using properties file value
884 logger.info("value of alarm: {}", alarmStringValue);
885 ObjectNode alarmStringJsonNode = (ObjectNode) mapper.readValue(alarmStringValue, JsonNode.class);
886 vfObjectNode2.putPOJO("alarmCondition", alarmStringJsonNode);
889 private ObjectNode createByVFCObjectNode(ObjectMapper mapper, List<CldsSdcResource> cldsSdcResourceList) {
890 ObjectNode emptyObjectNode = mapper.createObjectNode();
891 ObjectNode emptyvfcobjectNode = mapper.createObjectNode();
892 ObjectNode vfCObjectNode = mapper.createObjectNode();
893 vfCObjectNode.putPOJO("vfC", emptyObjectNode);
894 ObjectNode subVfCObjectNode = mapper.createObjectNode();
895 subVfCObjectNode.putPOJO("vfc", emptyObjectNode);
896 if (cldsSdcResourceList != null && cldsSdcResourceList.size() > 0) {
897 for (CldsSdcResource cldsSdcResource : cldsSdcResourceList) {
898 if (cldsSdcResource != null && cldsSdcResource.getResoucreType() != null
899 && cldsSdcResource.getResoucreType().equalsIgnoreCase("VF")) {
900 vfCObjectNode.putPOJO(cldsSdcResource.getResourceUUID(), subVfCObjectNode);
904 emptyvfcobjectNode.putPOJO("", vfCObjectNode);
905 return emptyvfcobjectNode;
909 @Path("/deploy/{modelName}")
910 @Consumes(MediaType.APPLICATION_JSON)
911 @Produces(MediaType.APPLICATION_JSON)
912 public CldsModel deployModel(@PathParam("action") String action, @PathParam("modelName") String modelName,
913 @QueryParam("test") String test, CldsModel model) throws Exception {
914 Date startTime = new Date();
915 LoggingUtils.setRequestContext("CldsService: Deploy model", getPrincipalName());
916 String deploymentId = "closedLoop_" + UUID.randomUUID() + "_deploymentId";
917 String createNewDeploymentStatusUrl = dcaeDispatcherServices.createNewDeployment(deploymentId,
919 String operationStatus = "processing";
920 long waitingTime = System.nanoTime() + TimeUnit.MINUTES.toNanos(10);
921 while (operationStatus.equalsIgnoreCase("processing")) {
922 //Break the loop if waiting for more than 10 mins
923 if(waitingTime < System.nanoTime()){
926 operationStatus = dcaeDispatcherServices.getOperationStatus(createNewDeploymentStatusUrl);
928 if (operationStatus != null && operationStatus.equalsIgnoreCase("succeeded")) {
929 String artifactName = model.getControlName();
930 if (artifactName != null) {
931 artifactName = artifactName + ".yml";
933 DcaeEvent dcaeEvent = new DcaeEvent();
934 /* set dcae events */
935 dcaeEvent.setArtifactName(artifactName);
936 dcaeEvent.setEvent(DcaeEvent.EVENT_DEPLOYMENT);
937 CldsEvent.insEvent(cldsDao, dcaeEvent.getControlName(), getUserId(), dcaeEvent.getCldsActionCd(),
938 CldsEvent.ACTION_STATE_RECEIVED, null);
939 model.setDeploymentId(deploymentId);
940 model.save(cldsDao, getUserId());
943 logger.info("Deploy model (" + modelName + ") failed...Operation Status is - " + operationStatus);
944 throw new Exception("Deploy model (" + modelName + ") failed...Operation Status is - " + operationStatus);
946 logger.info("Deploy model (" + modelName + ") succeeded...Deployment Id is - " + deploymentId);
948 LoggingUtils.setTimeContext(startTime, new Date());
949 LoggingUtils.setResponseContext("0", "Deploy model success", this.getClass().getName());
950 auditLogger.info("Deploy model completed");
955 @Path("/undeploy/{modelName}")
956 @Consumes(MediaType.APPLICATION_JSON)
957 @Produces(MediaType.APPLICATION_JSON)
958 public CldsModel unDeployModel(@PathParam("action") String action, @PathParam("modelName") String modelName,
959 @QueryParam("test") String test, CldsModel model) throws Exception {
960 Date startTime = new Date();
961 LoggingUtils.setRequestContext("CldsService: Undeploy model", getPrincipalName());
962 String operationStatusUndeployUrl = dcaeDispatcherServices.deleteExistingDeployment(model.getDeploymentId(),
964 String operationStatus = "processing";
965 long waitingTime = System.nanoTime() + TimeUnit.MINUTES.toNanos(10);
966 while (operationStatus.equalsIgnoreCase("processing")) {
967 if(waitingTime < System.nanoTime()){
970 operationStatus = dcaeDispatcherServices.getOperationStatus(operationStatusUndeployUrl);
972 if (operationStatus != null && operationStatus.equalsIgnoreCase("succeeded")) {
973 String artifactName = model.getControlName();
974 if (artifactName != null) {
975 artifactName = artifactName + ".yml";
977 DcaeEvent dcaeEvent = new DcaeEvent();
979 dcaeEvent.setArtifactName(artifactName);
980 dcaeEvent.setEvent(DcaeEvent.EVENT_UNDEPLOYMENT);
981 CldsEvent.insEvent(cldsDao, model.getControlName(), getUserId(), dcaeEvent.getCldsActionCd(),
982 CldsEvent.ACTION_STATE_RECEIVED, null);
983 model.setDeploymentId(null);
984 model.save(cldsDao, getUserId());
987 logger.info("Undeploy model (" + modelName + ") failed...Operation Status is - " + operationStatus);
988 throw new Exception("Undeploy model (" + modelName + ") failed...Operation Status is - " + operationStatus);
990 logger.info("Undeploy model (" + modelName + ") succeeded.");
992 LoggingUtils.setTimeContext(startTime, new Date());
993 LoggingUtils.setResponseContext("0", "Undeploy model success", this.getClass().getName());
994 auditLogger.info("Undeploy model completed");
998 private String getGlobalCldsString() throws Exception {
999 if (null == globalCldsProperties) {
1000 globalCldsProperties = new Properties();
1001 globalCldsProperties.load(appContext.getResource(globalClds).getInputStream());
1003 return (String) globalCldsProperties.get("globalCldsProps");