package net.ivoa.xml.vospace.v2; import com.fasterxml.jackson.databind.ObjectMapper; import static com.jayway.jsonpath.matchers.JsonPathMatchers.hasJsonPath; import java.io.StringReader; import java.io.StringWriter; import java.util.ArrayList; import java.util.List; import java.util.function.Function; import javax.xml.bind.JAXB; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertTrue; import org.junit.jupiter.api.Test; import org.w3c.dom.Document; import static net.ivoa.xml.VOSpaceXmlTestUtil.loadDocument; import static org.hamcrest.CoreMatchers.is; import static org.hamcrest.MatcherAssert.assertThat; public class NodeTest { private static final ObjectMapper MAPPER = new ObjectMapper(); private static final String URI_PREFIX = "vos://example.com!vospace"; @Test public void testXmlSerialization() throws Exception { ContainerNode root = getRoot(); String xml; try ( StringWriter sw = new StringWriter()) { JAXB.marshal(root, sw); xml = sw.toString(); System.out.println(xml); } Document doc = loadDocument(xml); assertEquals("vos:node", doc.getDocumentElement().getNodeName()); assertEquals("vos:ContainerNode", doc.getDocumentElement().getAttribute("xsi:type")); assertTrue(xml.contains("")); assertTrue(xml.contains("xsi:type=\"vos:DataNode\"")); assertTrue(xml.contains("xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"")); ContainerNode deserialized; try ( StringReader sr = new StringReader(xml)) { deserialized = JAXB.unmarshal(sr, ContainerNode.class); } verifyNodesAreEquals(root, deserialized); verifyConstraints(deserialized); } @Test public void testJsonSerialization() throws Exception { ContainerNode root = getRoot(); String json = MAPPER.writeValueAsString(root); System.out.println(json); assertThat(json, hasJsonPath("$.type", is("vos:ContainerNode"))); assertThat(json, hasJsonPath("$.nodes[0].type", is("vos:DataNode"))); assertThat(json, hasJsonPath("$.nodes[0].uri", is("vos://example.com!vospace/node1"))); ContainerNode deserialized = MAPPER.readValue(json, ContainerNode.class); verifyNodesAreEquals(root, deserialized); verifyConstraints(deserialized); } private ContainerNode getRoot() { ContainerNode root = getContainerNode("/", true, "g1", "g2"); List nodes = new ArrayList<>(); nodes.add(getDataNode("/node1", false, "g1", "g2", 808009979)); nodes.add(getDataNode("/node2", true, "g1", "g2", 305919869)); nodes.add(getContainerNode("/node3", true, "g1", "g2")); root.setNodes(nodes); return root; } private ContainerNode getContainerNode(String path, boolean isPublic, String groupRead, String groupWrite) { ContainerNode node = new ContainerNode(); fillNode(node, path, isPublic, groupRead, groupWrite, 0); return node; } private DataNode getDataNode(String path, boolean isPublic, String groupRead, String groupWrite, long size) { DataNode node = new DataNode(); fillNode(node, path, isPublic, groupRead, groupWrite, size); return node; } private void fillNode(Node node, String path, boolean isPublic, String groupRead, String groupWrite, long size) { node.setUri(URI_PREFIX + path); List properties = new ArrayList<>(); properties.add(createProperty("ivo://ivoa.net/vospace/core#ispublic", String.valueOf(isPublic))); properties.add(createProperty("ivo://ivoa.net/vospace/core#groupread", groupRead)); properties.add(createProperty("ivo://ivoa.net/vospace/core#groupwrite", groupWrite)); properties.add(createProperty("ivo://ivoa.net/vospace/core#length", String.valueOf(size))); PropertyList propertyList = new PropertyList(); propertyList.getProperty().addAll(properties); node.setProperties(propertyList); } private Property createProperty(String uri, String value) { Property prop = new Property(); prop.setUri(uri); prop.setValue(value); return prop; } private void verifyNodesAreEquals(ContainerNode serialized, ContainerNode deserialized) { verifyItem(serialized, deserialized, n -> n.getType()); verifyItem(serialized, deserialized, n -> n.getNodes().size()); verifyItem(serialized, deserialized, n -> getProperty(n, "ivo://ivoa.net/vospace/core#ispublic")); verifyItem(serialized, deserialized, n -> getProperty(n, "ivo://ivoa.net/vospace/core#groupread")); verifyItem(serialized, deserialized, n -> getProperty(n, "ivo://ivoa.net/vospace/core#groupwrite")); verifyItem(serialized, deserialized, n -> getProperty(n, "ivo://ivoa.net/vospace/core#length")); } private void verifyItem(ContainerNode serialized, ContainerNode deserialized, Function function) { assertEquals(function.apply(serialized), function.apply(deserialized)); } private String getProperty(Node node, String uri) { for (Property property : node.getProperties().getProperty()) { if (uri.equals(property.getUri())) { return property.getValue(); } } throw new IllegalArgumentException("Node doesn't contain property having uri " + uri); } private void verifyConstraints(ContainerNode deserialized) { DataNode node1 = (DataNode) getChildNodeByPath(deserialized, "/node1"); ContainerNode node3 = (ContainerNode) getChildNodeByPath(deserialized, "/node3"); assertEquals("vos:DataNode", node1.getType()); assertEquals("vos:ContainerNode", node3.getType()); } private Node getChildNodeByPath(ContainerNode parent, String path) { for (Node node : parent.getNodes()) { if ((URI_PREFIX + path).equals(node.getUri())) { return node; } } throw new IllegalArgumentException("Node not found for path " + path); } }