2 * ============LICENSE_START=======================================================
3 * PNF-REGISTRATION-HANDLER
4 * ================================================================================
5 * Copyright (C) 2018 Nokia. 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.onap.pnfsimulator.rest;
23 import com.google.common.collect.ImmutableMap;
24 import com.google.gson.JsonSyntaxException;
25 import org.json.JSONException;
26 import org.onap.pnfsimulator.event.EventData;
27 import org.onap.pnfsimulator.event.EventDataService;
28 import org.onap.pnfsimulator.rest.model.FullEvent;
29 import org.onap.pnfsimulator.rest.model.SimulatorRequest;
30 import org.onap.pnfsimulator.rest.util.DateUtil;
31 import org.onap.pnfsimulator.rest.util.ResponseBuilder;
32 import org.onap.pnfsimulator.simulator.SimulatorService;
33 import org.onap.pnfsimulator.simulatorconfig.SimulatorConfig;
34 import org.quartz.SchedulerException;
35 import org.slf4j.Logger;
36 import org.slf4j.LoggerFactory;
38 import org.slf4j.Marker;
39 import org.slf4j.MarkerFactory;
40 import org.springframework.beans.factory.annotation.Autowired;
41 import org.springframework.http.HttpHeaders;
42 import org.springframework.http.HttpStatus;
43 import org.springframework.http.ResponseEntity;
44 import org.springframework.web.bind.annotation.GetMapping;
45 import org.springframework.web.bind.annotation.PathVariable;
46 import org.springframework.web.bind.annotation.PostMapping;
47 import org.springframework.web.bind.annotation.PutMapping;
48 import org.springframework.web.bind.annotation.RequestBody;
49 import org.springframework.web.bind.annotation.RequestHeader;
50 import org.springframework.web.bind.annotation.RequestMapping;
51 import org.springframework.web.bind.annotation.RestController;
53 import javax.validation.Valid;
54 import java.io.IOException;
55 import java.net.MalformedURLException;
56 import java.security.GeneralSecurityException;
57 import java.text.DateFormat;
58 import java.text.SimpleDateFormat;
59 import java.util.List;
61 import java.util.UUID;
63 import static org.onap.pnfsimulator.logging.MDCVariables.INSTANCE_UUID;
64 import static org.onap.pnfsimulator.logging.MDCVariables.INVOCATION_ID;
65 import static org.onap.pnfsimulator.logging.MDCVariables.REQUEST_ID;
66 import static org.onap.pnfsimulator.logging.MDCVariables.RESPONSE_CODE;
67 import static org.onap.pnfsimulator.logging.MDCVariables.SERVICE_NAME;
68 import static org.onap.pnfsimulator.logging.MDCVariables.X_INVOCATION_ID;
69 import static org.onap.pnfsimulator.logging.MDCVariables.X_ONAP_REQUEST_ID;
70 import static org.onap.pnfsimulator.rest.util.ResponseBuilder.MESSAGE;
71 import static org.onap.pnfsimulator.rest.util.ResponseBuilder.TIMESTAMP;
72 import static org.springframework.http.HttpStatus.ACCEPTED;
73 import static org.springframework.http.HttpStatus.BAD_REQUEST;
74 import static org.springframework.http.HttpStatus.INTERNAL_SERVER_ERROR;
75 import static org.springframework.http.HttpStatus.NOT_FOUND;
76 import static org.springframework.http.HttpStatus.OK;
79 @RequestMapping("/simulator")
80 public class SimulatorController {
82 private static final Logger LOGGER = LoggerFactory.getLogger(SimulatorController.class);
83 private static final Marker ENTRY = MarkerFactory.getMarker("ENTRY");
84 private static final String INCORRECT_TEMPLATE_MESSAGE = "Cannot start simulator, template %s is not in valid format: %s";
85 private static final String NOT_EXISTING_TEMPLATE = "Cannot start simulator - template %s not found.";
86 private final DateFormat responseDateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss,SSS");
87 private final SimulatorService simulatorService;
88 private EventDataService eventDataService;
91 public SimulatorController(SimulatorService simulatorService,
92 EventDataService eventDataService) {
93 this.simulatorService = simulatorService;
94 this.eventDataService = eventDataService;
99 public ResponseEntity test(@Valid @RequestBody SimulatorRequest simulatorRequest) {
100 MDC.put("test", "test");
101 LOGGER.info(ENTRY, simulatorRequest.toString());
102 return buildResponse(OK, ImmutableMap.of(MESSAGE, "message1234"));
105 @PostMapping(value = "start")
106 public ResponseEntity start(@RequestHeader HttpHeaders headers,
107 @Valid @RequestBody SimulatorRequest triggerEventRequest) {
108 logContextHeaders(headers, "/simulator/start");
109 LOGGER.info(ENTRY, "Simulator started");
112 return processRequest(triggerEventRequest);
114 } catch (JSONException | JsonSyntaxException e) {
115 MDC.put(RESPONSE_CODE, BAD_REQUEST.toString());
116 LOGGER.warn("Cannot trigger event, invalid json format: {}", e.getMessage());
117 LOGGER.debug("Received json has invalid format", e);
118 return buildResponse(BAD_REQUEST, ImmutableMap.of(MESSAGE, String
119 .format(INCORRECT_TEMPLATE_MESSAGE, triggerEventRequest.getTemplateName(),
121 } catch (GeneralSecurityException e ){
122 MDC.put(RESPONSE_CODE, INTERNAL_SERVER_ERROR.toString() );
123 LOGGER.error("Client certificate validation failed: {}", e.getMessage());
124 return buildResponse(INTERNAL_SERVER_ERROR,
125 ImmutableMap.of(MESSAGE, "Invalid or misconfigured client certificate"));
127 catch (IOException e) {
128 MDC.put(RESPONSE_CODE, BAD_REQUEST.toString());
129 LOGGER.warn("Json validation failed: {}", e.getMessage());
130 return buildResponse(BAD_REQUEST,
131 ImmutableMap.of(MESSAGE, String.format(NOT_EXISTING_TEMPLATE, triggerEventRequest.getTemplateName())));
132 } catch (Exception e) {
133 MDC.put(RESPONSE_CODE, INTERNAL_SERVER_ERROR.toString());
134 LOGGER.error("Cannot trigger event - unexpected exception", e);
135 return buildResponse(INTERNAL_SERVER_ERROR,
136 ImmutableMap.of(MESSAGE, "Unexpected exception: " + e.getMessage()));
142 @GetMapping("all-events")
144 public ResponseEntity allEvents() {
145 List<EventData> eventDataList = eventDataService.getAllEvents();
146 StringBuilder sb = new StringBuilder();
147 eventDataList.forEach(e -> sb.append(e).append(System.lineSeparator()));
149 return ResponseBuilder
150 .status(OK).put(MESSAGE, sb.toString())
154 @GetMapping("config")
155 public ResponseEntity getConfig() {
156 SimulatorConfig configToGet = simulatorService.getConfiguration();
157 return buildResponse(OK, ImmutableMap.of("simulatorConfig", configToGet));
160 @PutMapping("config")
161 public ResponseEntity updateConfig(@Valid @RequestBody SimulatorConfig newConfig) {
162 SimulatorConfig updatedConfig = simulatorService.updateConfiguration(newConfig);
163 return buildResponse(OK, ImmutableMap.of("simulatorConfig", updatedConfig));
166 @PostMapping("cancel/{jobName}")
167 public ResponseEntity cancelEvent(@PathVariable String jobName) throws SchedulerException {
168 LOGGER.info(ENTRY, "Cancel called on {}.", jobName);
169 boolean isCancelled = simulatorService.cancelEvent(jobName);
170 return createCancelEventResponse(isCancelled);
173 @PostMapping("cancel")
174 public ResponseEntity cancelAllEvent() throws SchedulerException {
175 LOGGER.info(ENTRY, "Cancel called on all jobs");
176 boolean isCancelled = simulatorService.cancelAllEvents();
177 return createCancelEventResponse(isCancelled);
180 @PostMapping("event")
181 public ResponseEntity sendEventDirectly(@RequestHeader HttpHeaders headers, @Valid @RequestBody FullEvent event)
182 throws IOException, GeneralSecurityException{
183 logContextHeaders(headers, "/simulator/event");
184 LOGGER.info(ENTRY, "Trying to send one-time event directly to VES Collector");
185 simulatorService.triggerOneTimeEvent(event);
186 return buildResponse(ACCEPTED, ImmutableMap.of(MESSAGE, "One-time direct event sent successfully"));
189 private ResponseEntity processRequest(SimulatorRequest triggerEventRequest)
190 throws IOException, SchedulerException, GeneralSecurityException {
192 String jobName = simulatorService.triggerEvent(triggerEventRequest);
193 MDC.put(RESPONSE_CODE, OK.toString());
194 return buildResponse(OK, ImmutableMap.of(MESSAGE, "Request started", "jobName", jobName));
197 private ResponseEntity buildResponse(HttpStatus endStatus, Map<String, Object> parameters) {
198 ResponseBuilder builder = ResponseBuilder
200 .put(TIMESTAMP, DateUtil.getTimestamp(responseDateFormat));
201 parameters.forEach(builder::put);
202 return builder.build();
205 private void logContextHeaders(HttpHeaders headers, String serviceName) {
206 MDC.put(REQUEST_ID, headers.getFirst(X_ONAP_REQUEST_ID));
207 MDC.put(INVOCATION_ID, headers.getFirst(X_INVOCATION_ID));
208 MDC.put(INSTANCE_UUID, UUID.randomUUID().toString());
209 MDC.put(SERVICE_NAME, serviceName);
212 private ResponseEntity createCancelEventResponse(boolean isCancelled) {
214 return buildResponse(OK, ImmutableMap.of(MESSAGE, "Event(s) was cancelled"));
216 return buildResponse(NOT_FOUND, ImmutableMap.of(MESSAGE, "Simulator was not able to cancel event(s)"));