aboutsummaryrefslogtreecommitdiffstats
path: root/models-interactions/model-actors
diff options
context:
space:
mode:
authorJim Hahn <jrh3@att.com>2020-05-15 09:52:35 -0400
committerJim Hahn <jrh3@att.com>2020-05-15 11:53:17 -0400
commitafe5abed95c6cbfe239066e267d9c10a71f20623 (patch)
tree89325042e014a2685d54d7cce13f26bb4bfde6b1 /models-interactions/model-actors
parent4e50a58565461839df6a1fe65f571a04b2404616 (diff)
Cannot parse finishTime in SO responses
The timestamp in SO responses appears to follow RFC-1123/RFC-822 format instead of ISO format. Added a type adapter for SO. In Guilin, we may want to consider combining the two type adapters for LocalDateTime so that either format is accepted. Also modified the SO simulator to return responses that are actual samples from SO. As part of that work, discovered that the legacy SO actor is not able to parse these timestamps either. However, as that code is now deprecated, left it as is. Issue-ID: POLICY-2570 Change-Id: I322318d1007e36eef47bb8867fd8ed01cb60223a Signed-off-by: Jim Hahn <jrh3@att.com>
Diffstat (limited to 'models-interactions/model-actors')
-rw-r--r--models-interactions/model-actors/actor.so/src/main/java/org/onap/policy/controlloop/actor/so/SoOperation.java85
-rw-r--r--models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/BasicSoOperation.java4
-rw-r--r--models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/SoOperationTest.java17
3 files changed, 103 insertions, 3 deletions
diff --git a/models-interactions/model-actors/actor.so/src/main/java/org/onap/policy/controlloop/actor/so/SoOperation.java b/models-interactions/model-actors/actor.so/src/main/java/org/onap/policy/controlloop/actor/so/SoOperation.java
index a4c802c9a..2a00edda4 100644
--- a/models-interactions/model-actors/actor.so/src/main/java/org/onap/policy/controlloop/actor/so/SoOperation.java
+++ b/models-interactions/model-actors/actor.so/src/main/java/org/onap/policy/controlloop/actor/so/SoOperation.java
@@ -20,6 +20,17 @@
package org.onap.policy.controlloop.actor.so;
+import com.google.gson.Gson;
+import com.google.gson.GsonBuilder;
+import com.google.gson.JsonParseException;
+import com.google.gson.TypeAdapter;
+import com.google.gson.stream.JsonReader;
+import com.google.gson.stream.JsonToken;
+import com.google.gson.stream.JsonWriter;
+import java.io.IOException;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.format.DateTimeParseException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
@@ -39,9 +50,11 @@ import org.onap.policy.aai.AaiConstants;
import org.onap.policy.aai.AaiCqResponse;
import org.onap.policy.common.endpoints.event.comm.Topic.CommInfrastructure;
import org.onap.policy.common.endpoints.utils.NetLoggerUtil.EventType;
+import org.onap.policy.common.gson.GsonMessageBodyHandler;
import org.onap.policy.common.utils.coder.Coder;
import org.onap.policy.common.utils.coder.CoderException;
import org.onap.policy.common.utils.coder.StandardCoder;
+import org.onap.policy.common.utils.coder.StandardCoderObject;
import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome;
import org.onap.policy.controlloop.actorserviceprovider.impl.HttpOperation;
import org.onap.policy.controlloop.actorserviceprovider.parameters.ControlLoopOperationParams;
@@ -64,7 +77,7 @@ import org.slf4j.LoggerFactory;
*/
public abstract class SoOperation extends HttpOperation<SoResponse> {
private static final Logger logger = LoggerFactory.getLogger(SoOperation.class);
- private static final Coder coder = new StandardCoder();
+ private static final Coder coder = new SoCoder();
public static final String PAYLOAD_KEY_VF_COUNT = "vfCount";
public static final String FAILED = "FAILED";
@@ -479,4 +492,74 @@ public abstract class SoOperation extends HttpOperation<SoResponse> {
public int getWaitSecGet() {
return config.getWaitSecGet();
}
+
+ @Override
+ protected Coder makeCoder() {
+ return coder;
+ }
+
+ /*
+ * TODO: combine this adapter with existing LocalDateTimeTypeAdapter and eliminate the
+ * following two classes.
+ */
+
+ /**
+ * GSON Type Adapter for "LocalDateTime" fields, that uses the standard
+ * RFC_1123_DATE_TIME formatter.
+ */
+ private static class SoLocalDateTimeTypeAdapter extends TypeAdapter<LocalDateTime> {
+ private static final DateTimeFormatter FORMATTER = DateTimeFormatter.RFC_1123_DATE_TIME;
+
+ @Override
+ public LocalDateTime read(JsonReader in) throws IOException {
+ try {
+ if (in.peek() == JsonToken.NULL) {
+ in.nextNull();
+ return null;
+ } else {
+ return LocalDateTime.parse(in.nextString(), FORMATTER);
+ }
+
+ } catch (DateTimeParseException e) {
+ throw new JsonParseException("invalid date", e);
+ }
+ }
+
+ @Override
+ public void write(JsonWriter out, LocalDateTime value) throws IOException {
+ if (value == null) {
+ out.nullValue();
+ } else {
+ String text = value.format(FORMATTER);
+ out.value(text);
+ }
+ }
+ }
+
+ private static class SoCoder extends StandardCoder {
+
+ /**
+ * Gson object used to encode and decode messages.
+ */
+ private static final Gson SO_GSON;
+
+ /**
+ * Gson object used to encode messages in "pretty" format.
+ */
+ private static final Gson SO_GSON_PRETTY;
+
+ static {
+ GsonBuilder builder = GsonMessageBodyHandler
+ .configBuilder(new GsonBuilder().registerTypeAdapter(StandardCoderObject.class,
+ new StandardTypeAdapter()))
+ .registerTypeAdapter(LocalDateTime.class, new SoLocalDateTimeTypeAdapter());
+
+ SO_GSON = builder.create();
+ SO_GSON_PRETTY = builder.setPrettyPrinting().create();
+ }
+
+ public SoCoder() {
+ super(SO_GSON, SO_GSON_PRETTY);
+ }
+ }
}
diff --git a/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/BasicSoOperation.java b/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/BasicSoOperation.java
index 0232226e0..aaecb46a8 100644
--- a/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/BasicSoOperation.java
+++ b/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/BasicSoOperation.java
@@ -96,11 +96,11 @@ public abstract class BasicSoOperation extends BasicHttpOperation<SoRequest> {
.serializationProvider(GsonMessageBodyHandler.class.getName()).build();
HttpClientFactoryInstance.getClientFactory().build(clientParams);
- SoSimulatorJaxRs.setYieldIncomplete(true);
+ SoSimulatorJaxRs.setRequirePolling(true);
}
protected static void destroyAfterClass() {
- SoSimulatorJaxRs.setYieldIncomplete(false);
+ SoSimulatorJaxRs.setRequirePolling(false);
HttpClientFactoryInstance.getClientFactory().destroy();
HttpServletServerFactoryInstance.getServerFactory().destroy();
}
diff --git a/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/SoOperationTest.java b/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/SoOperationTest.java
index 70093967c..644521869 100644
--- a/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/SoOperationTest.java
+++ b/models-interactions/model-actors/actor.so/src/test/java/org/onap/policy/controlloop/actor/so/SoOperationTest.java
@@ -32,6 +32,8 @@ import static org.mockito.ArgumentMatchers.any;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
+import java.time.LocalDateTime;
+import java.time.Month;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.CompletableFuture;
@@ -46,6 +48,7 @@ import org.onap.aai.domain.yang.GenericVnf;
import org.onap.aai.domain.yang.ServiceInstance;
import org.onap.aai.domain.yang.Tenant;
import org.onap.policy.aai.AaiCqResponse;
+import org.onap.policy.common.utils.coder.Coder;
import org.onap.policy.common.utils.coder.CoderException;
import org.onap.policy.controlloop.ControlLoopOperation;
import org.onap.policy.controlloop.actorserviceprovider.OperationOutcome;
@@ -422,4 +425,18 @@ public class SoOperationTest extends BasicSoOperation {
when(cq.getDefaultCloudRegion()).thenReturn(region);
assertSame(region, oper.getDefaultCloudRegion(cq));
}
+
+ @Test
+ public void testMakeCoder() throws CoderException {
+ Coder opcoder = oper.makeCoder();
+
+ // ensure we can decode an SO timestamp
+ String json = "{'request':{'finishTime':'Fri, 15 May 2020 12:14:21 GMT'}}";
+ SoResponse resp = opcoder.decode(json.replace('\'', '"'), SoResponse.class);
+
+ LocalDateTime tfinish = resp.getRequest().getFinishTime();
+ assertNotNull(tfinish);
+ assertEquals(2020, tfinish.getYear());
+ assertEquals(Month.MAY, tfinish.getMonth());
+ }
}