kopia lustrzana https://github.com/bertrik/ttnhabbridge
Cleanup Ttnv2UplinkMessage
rodzic
1dc3101aff
commit
65a2cbf8b0
|
@ -1,46 +0,0 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
|
||||||
|
|
||||||
import java.time.Instant;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Representation of meta-data part of MQTT message.
|
|
||||||
*/
|
|
||||||
@JsonIgnoreProperties(ignoreUnknown = true)
|
|
||||||
public final class TtnMessageMetaData {
|
|
||||||
|
|
||||||
@JsonProperty("time")
|
|
||||||
private String time = "";
|
|
||||||
|
|
||||||
@JsonProperty("gateways")
|
|
||||||
private List<TtnMessageGateway> gateways = new ArrayList<>();
|
|
||||||
|
|
||||||
private TtnMessageMetaData() {
|
|
||||||
// empty jackson constructor
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Constructor.
|
|
||||||
*
|
|
||||||
* @param time the time
|
|
||||||
* @param gateways list of gateways
|
|
||||||
*/
|
|
||||||
public TtnMessageMetaData(String time, List<TtnMessageGateway> gateways) {
|
|
||||||
this();
|
|
||||||
this.time = time;
|
|
||||||
this.gateways = gateways;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Instant getTime() {
|
|
||||||
return Instant.parse(time);
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<TtnMessageGateway> getMqttGateways() {
|
|
||||||
return gateways;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,7 +1,8 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
package nl.sikken.bertrik.hab.ttn;
|
||||||
|
|
||||||
import java.util.HashMap;
|
import java.time.Instant;
|
||||||
import java.util.Map;
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
|
@ -13,29 +14,26 @@ import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
public final class Ttnv2UplinkMessage {
|
public final class Ttnv2UplinkMessage {
|
||||||
|
|
||||||
@JsonProperty("app_id")
|
@JsonProperty("app_id")
|
||||||
private String appId;
|
private String appId = "";
|
||||||
|
|
||||||
@JsonProperty("dev_id")
|
@JsonProperty("dev_id")
|
||||||
private String devId;
|
private String devId = "";
|
||||||
|
|
||||||
@JsonProperty("hardware_serial")
|
@JsonProperty("hardware_serial")
|
||||||
private String hardwareSerial;
|
private String hardwareSerial = "";
|
||||||
|
|
||||||
@JsonProperty("port")
|
@JsonProperty("port")
|
||||||
private int port;
|
private int port = 0;
|
||||||
|
|
||||||
@JsonProperty("counter")
|
@JsonProperty("counter")
|
||||||
private int counter;
|
private int counter = 0;
|
||||||
|
|
||||||
@JsonProperty("is_retry")
|
@JsonProperty("is_retry")
|
||||||
private boolean isRetry;
|
private boolean isRetry = false;
|
||||||
|
|
||||||
@JsonProperty("payload_raw")
|
@JsonProperty("payload_raw")
|
||||||
private byte[] payloadRaw = new byte[0];
|
private byte[] payloadRaw = new byte[0];
|
||||||
|
|
||||||
@JsonProperty("payload_fields")
|
|
||||||
private Map<String, Object> payloadFields = new HashMap<>();
|
|
||||||
|
|
||||||
@JsonProperty("metadata")
|
@JsonProperty("metadata")
|
||||||
private TtnMessageMetaData metaData;
|
private TtnMessageMetaData metaData;
|
||||||
|
|
||||||
|
@ -43,55 +41,41 @@ public final class Ttnv2UplinkMessage {
|
||||||
// Jackson constructor
|
// Jackson constructor
|
||||||
}
|
}
|
||||||
|
|
||||||
// constructor for testing
|
@JsonIgnoreProperties(ignoreUnknown = true)
|
||||||
public Ttnv2UplinkMessage(String devId, int counter, TtnMessageMetaData metaData, byte[] payloadRaw) {
|
final static class TtnMessageMetaData {
|
||||||
this();
|
|
||||||
this.devId = devId;
|
@JsonProperty("time")
|
||||||
this.counter = counter;
|
private String time = "";
|
||||||
this.metaData = metaData;
|
|
||||||
this.payloadRaw = payloadRaw.clone();
|
@JsonProperty("gateways")
|
||||||
|
private List<TtnMessageGateway> gateways = new ArrayList<>();
|
||||||
|
|
||||||
|
private TtnMessageMetaData() {
|
||||||
|
// empty jackson constructor
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getAppId() {
|
@JsonIgnoreProperties(ignoreUnknown = true)
|
||||||
return appId;
|
final static class TtnMessageGateway {
|
||||||
}
|
|
||||||
|
|
||||||
public String getDevId() {
|
@JsonProperty("gtw_id")
|
||||||
return devId;
|
private String id = "";
|
||||||
}
|
|
||||||
|
|
||||||
public String getHardwareSerial() {
|
@JsonProperty("latitude")
|
||||||
return hardwareSerial;
|
private double latitude = Double.NaN;
|
||||||
}
|
|
||||||
|
|
||||||
public int getPort() {
|
@JsonProperty("longitude")
|
||||||
return port;
|
private double longitude = Double.NaN;
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isRetry() {
|
@JsonProperty("altitude")
|
||||||
return isRetry;
|
private double altitude = Double.NaN;
|
||||||
}
|
|
||||||
|
|
||||||
public int getCounter() {
|
|
||||||
return counter;
|
|
||||||
}
|
|
||||||
|
|
||||||
public byte[] getPayloadRaw() {
|
|
||||||
return payloadRaw.clone();
|
|
||||||
}
|
|
||||||
|
|
||||||
public Map<String, Object> getPayloadFields() {
|
|
||||||
return payloadFields;
|
|
||||||
}
|
|
||||||
|
|
||||||
public TtnMessageMetaData getMetaData() {
|
|
||||||
return metaData;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public TtnUplinkMessage toUplinkMessage() {
|
public TtnUplinkMessage toUplinkMessage() {
|
||||||
TtnUplinkMessage message = new TtnUplinkMessage(metaData.getTime(), appId, devId, counter, port, payloadRaw, isRetry);
|
TtnUplinkMessage message = new TtnUplinkMessage(Instant.parse(metaData.time), appId, devId, counter, port,
|
||||||
for (TtnMessageGateway gw : metaData.getMqttGateways()) {
|
payloadRaw, isRetry);
|
||||||
message.addGateway(gw.getId(), gw.getLatitude(), gw.getLongitude(), gw.getAltitude());
|
for (TtnMessageGateway gw : metaData.gateways) {
|
||||||
|
message.addGateway(gw.id, gw.latitude, gw.longitude, gw.altitude);
|
||||||
}
|
}
|
||||||
return message;
|
return message;
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,7 +42,7 @@ public final class PayloadDecoderTest {
|
||||||
TtnUplinkMessage uplink = message.toUplinkMessage();
|
TtnUplinkMessage uplink = message.toUplinkMessage();
|
||||||
|
|
||||||
// check gateway field
|
// check gateway field
|
||||||
Assert.assertEquals(27, message.getMetaData().getMqttGateways().get(0).getAltitude(), 0.1);
|
Assert.assertEquals(27, uplink.getGateways().get(0).getLocation().getAlt(), 0.1);
|
||||||
|
|
||||||
// decode payload
|
// decode payload
|
||||||
PayloadDecoder decoder = new PayloadDecoder(EPayloadEncoding.SODAQ_ONE);
|
PayloadDecoder decoder = new PayloadDecoder(EPayloadEncoding.SODAQ_ONE);
|
||||||
|
|
|
@ -1,56 +0,0 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
|
||||||
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
||||||
|
|
||||||
import nl.sikken.bertrik.hab.habitat.Location;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Unit tests of TtnMessageGateway.
|
|
||||||
*/
|
|
||||||
public final class TtnMessageGatewayTest {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies serialization to JSON.
|
|
||||||
*
|
|
||||||
* @throws JsonProcessingException in case of a JSON error
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testJson() throws JsonProcessingException {
|
|
||||||
TtnMessageGateway gw = new TtnMessageGateway("id", true, "time", 0.0, 1.1, 2.2);
|
|
||||||
ObjectMapper mapper = new ObjectMapper();
|
|
||||||
String json = mapper.writeValueAsString(gw);
|
|
||||||
|
|
||||||
Assert.assertNotNull(json);
|
|
||||||
Assert.assertFalse(json.contains("location") || json.contains("Location"));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies that we can get a location.
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testLocation() {
|
|
||||||
TtnMessageGateway gw = new TtnMessageGateway("id", true, "time", 0.0, 1.1, 2.2);
|
|
||||||
Assert.assertTrue(gw.getLocation().isValid());
|
|
||||||
|
|
||||||
Location location = gw.getLocation();
|
|
||||||
Assert.assertNotNull(location);
|
|
||||||
Assert.assertEquals(1.1, location.getLon(), 0.01);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies that absence of location is detected.
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testNoLocation() {
|
|
||||||
TtnMessageGateway gw1 = new TtnMessageGateway("id", true, "time", Double.NaN, Double.NaN, Double.NaN);
|
|
||||||
Assert.assertFalse(gw1.getLocation().isValid());
|
|
||||||
|
|
||||||
TtnMessageGateway gw2 = new TtnMessageGateway("id", true, "time", Double.NaN, 1.1, 2.2);
|
|
||||||
Assert.assertFalse(gw2.getLocation().isValid());
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,33 +0,0 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
|
||||||
|
|
||||||
import java.time.Instant;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import nl.sikken.bertrik.hab.Sentence;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Unit test for TtnMessageMetaData.
|
|
||||||
*/
|
|
||||||
public final class TtnMessageMetaDataTest {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies time parsing.
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testTime() {
|
|
||||||
String time = "2017-08-23T17:18:02.509425571Z";
|
|
||||||
List<TtnMessageGateway> gws = new ArrayList<>();
|
|
||||||
TtnMessageMetaData data = new TtnMessageMetaData(time, gws);
|
|
||||||
Instant instant = data.getTime();
|
|
||||||
Assert.assertNotNull(instant);
|
|
||||||
|
|
||||||
Sentence sentence = new Sentence("call", 0, instant);
|
|
||||||
String line = sentence.format();
|
|
||||||
Assert.assertTrue(line.contains("17:18:02"));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,43 +0,0 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
import org.junit.Assert;
|
|
||||||
import org.junit.Before;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonParseException;
|
|
||||||
import com.fasterxml.jackson.databind.JsonMappingException;
|
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
||||||
|
|
||||||
public final class TtnMessageTest {
|
|
||||||
|
|
||||||
private ObjectMapper mapper;
|
|
||||||
|
|
||||||
@Before
|
|
||||||
public void before() {
|
|
||||||
mapper = new ObjectMapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies that a nominal valid uplink message can be parsed.
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testUplink() throws JsonParseException, JsonMappingException, IOException {
|
|
||||||
InputStream is = getClass().getClassLoader().getResourceAsStream("uplink_nominal.json");
|
|
||||||
Ttnv2UplinkMessage message = mapper.readValue(is, Ttnv2UplinkMessage.class);
|
|
||||||
Assert.assertEquals(false, message.isRetry());
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Verifies that an uplink message with "is_retry" can be parsed.
|
|
||||||
*/
|
|
||||||
@Test
|
|
||||||
public void testUplinkWithRetry() throws JsonParseException, JsonMappingException, IOException {
|
|
||||||
InputStream is = getClass().getClassLoader().getResourceAsStream("uplink_with_retry.json");
|
|
||||||
Ttnv2UplinkMessage message = mapper.readValue(is, Ttnv2UplinkMessage.class);
|
|
||||||
Assert.assertEquals(true, message.isRetry());
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
|
@ -1,10 +1,13 @@
|
||||||
package nl.sikken.bertrik.hab.ttn;
|
package nl.sikken.bertrik.hab.ttn;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import org.junit.Assert;
|
import org.junit.Assert;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.core.JsonParseException;
|
||||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
import com.fasterxml.jackson.databind.JsonMappingException;
|
import com.fasterxml.jackson.databind.JsonMappingException;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
@ -31,12 +34,12 @@ public final class Ttnv2UplinkMessageTest {
|
||||||
|
|
||||||
Assert.assertNotNull(message);
|
Assert.assertNotNull(message);
|
||||||
TtnUplinkMessage uplinkMessage = message.toUplinkMessage();
|
TtnUplinkMessage uplinkMessage = message.toUplinkMessage();
|
||||||
|
|
||||||
Assert.assertEquals("habhub", uplinkMessage.getAppId());
|
Assert.assertEquals("habhub", uplinkMessage.getAppId());
|
||||||
Assert.assertEquals("ttntest1", uplinkMessage.getDevId());
|
Assert.assertEquals("ttntest1", uplinkMessage.getDevId());
|
||||||
Assert.assertEquals(1, uplinkMessage.getPort());
|
Assert.assertEquals(1, uplinkMessage.getPort());
|
||||||
Assert.assertEquals(9, uplinkMessage.getCounter());
|
Assert.assertEquals(9, uplinkMessage.getCounter());
|
||||||
|
|
||||||
List<GatewayInfo> gateways = uplinkMessage.getGateways();
|
List<GatewayInfo> gateways = uplinkMessage.getGateways();
|
||||||
GatewayInfo gw = gateways.get(0);
|
GatewayInfo gw = gateways.get(0);
|
||||||
Assert.assertEquals("eui-008000000000b8b6", gw.getId());
|
Assert.assertEquals("eui-008000000000b8b6", gw.getId());
|
||||||
|
@ -44,6 +47,26 @@ public final class Ttnv2UplinkMessageTest {
|
||||||
Assert.assertEquals(4.70844, gw.getLocation().getLon(), 1E-4);
|
Assert.assertEquals(4.70844, gw.getLocation().getLon(), 1E-4);
|
||||||
Assert.assertEquals(27, gw.getLocation().getAlt(), 1E-1);
|
Assert.assertEquals(27, gw.getLocation().getAlt(), 1E-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verifies that a nominal valid uplink message can be parsed.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testUplink() throws JsonParseException, JsonMappingException, IOException {
|
||||||
|
InputStream is = getClass().getClassLoader().getResourceAsStream("uplink_nominal.json");
|
||||||
|
Ttnv2UplinkMessage message = MAPPER.readValue(is, Ttnv2UplinkMessage.class);
|
||||||
|
TtnUplinkMessage uplink = message.toUplinkMessage();
|
||||||
|
Assert.assertFalse(uplink.isRetry());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Verifies that an uplink message with "is_retry" can be parsed.
|
||||||
|
*/
|
||||||
|
@Test
|
||||||
|
public void testUplinkWithRetry() throws JsonParseException, JsonMappingException, IOException {
|
||||||
|
InputStream is = getClass().getClassLoader().getResourceAsStream("uplink_with_retry.json");
|
||||||
|
Ttnv2UplinkMessage message = MAPPER.readValue(is, Ttnv2UplinkMessage.class);
|
||||||
|
TtnUplinkMessage uplink = message.toUplinkMessage();
|
||||||
|
Assert.assertTrue(uplink.isRetry());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
Ładowanie…
Reference in New Issue