package org.jboss.resteasy.test.providers.jaxb.collection;
import org.jboss.resteasy.annotations.providers.jaxb.WrappedMap;
import org.jboss.resteasy.client.ClientRequest;
import org.jboss.resteasy.client.ClientResponse;
import org.jboss.resteasy.test.BaseResourceTest;
import static org.jboss.resteasy.test.TestPortProvider.*;
import org.jboss.resteasy.util.GenericType;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.w3c.dom.Element;
import javax.ws.rs.Consumes;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBElement;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlAnyAttribute;
import javax.xml.bind.annotation.XmlAnyElement;
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.bind.annotation.XmlTransient;
import javax.xml.namespace.QName;
import javax.xml.transform.stream.StreamSource;
import java.io.ByteArrayInputStream;
import java.io.StringWriter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
* @version $Revision: 1 $
*/
public class MapTest extends BaseResourceTest
{
@XmlAccessorType(XmlAccessType.FIELD)
public static class JaxbMap
{
@XmlAnyElement
List<JAXBElement<Entry>> value = new ArrayList<JAXBElement<Entry>>();
@XmlTransient
private String entryName;
@XmlTransient
private String keyAttributeName;
@XmlTransient
private String namespace;
public JaxbMap()
{
}
public JaxbMap(String entryName, String keyAttributeName, String namespace)
{
this.entryName = entryName;
this.namespace = namespace;
this.keyAttributeName = keyAttributeName;
}
@XmlAccessorType(XmlAccessType.FIELD)
public static class Entry
{
@XmlAnyElement
Object value;
@XmlAnyAttribute
Map<QName, Object> attribute = new HashMap<QName, Object>();
@XmlTransient
private String key;
@XmlTransient
private String keyAttributeName;
public Entry()
{
}
public Entry(String keyAttributeName, String key, Object value)
{
this.value = value;
this.keyAttributeName = keyAttributeName;
setKey(key);
}
public Object getValue()
{
return value;
}
public void setValue(Object value)
{
this.value = value;
}
public String getKey()
{
if (key != null) return key;
key = (String) attribute.values().iterator().next();
return key;
}
public void setKey(String keyValue)
{
this.key = keyValue;
attribute.clear();
QName name = new QName(keyAttributeName);
attribute.put(name, keyValue);
}
}
public void addEntry(String key, Object val)
{
Entry entry = new Entry(keyAttributeName, key, val);
//JAXBElement<Entry> element = new JAXBElement<Entry>(new QName(namespace, entryName, prefix), Entry.class, entry);
JAXBElement<Entry> element = new JAXBElement<Entry>(new QName(namespace, entryName), Entry.class, entry);
//JAXBElement<Entry> element = new JAXBElement<Entry>(new QName(entryName), Entry.class, entry);
value.add(element);
}
public List<JAXBElement<Entry>> getValue()
{
return value;
}
}
@XmlRootElement(namespace = "http://foo.com")
public static class Foo
{
@XmlAttribute
private String name;
public Foo()
{
}
public Foo(String name)
{
this.name = name;
}
public String getName()
{
return name;
}
}
@Path("/map")
public static class MyResource
{
@POST
@Produces("application/xml")
@Consumes("application/xml")
public Map<String, Foo> post(Map<String, Foo> map)
{
Assert.assertEquals(2, map.size());
Assert.assertNotNull(map.get("bill"));
Assert.assertNotNull(map.get("monica"));
Assert.assertEquals(map.get("bill").getName(), "bill");
Assert.assertEquals(map.get("monica").getName(), "monica");
return map;
}
@POST
@Produces("application/xml")
@Consumes("application/xml")
@Path("/wrapped")
@WrappedMap(namespace = "")
public Map<String, Foo> postWrapped(@WrappedMap(namespace = "") Map<String, Foo> map)
{
Assert.assertEquals(2, map.size());
Assert.assertNotNull(map.get("bill"));
Assert.assertNotNull(map.get("monica"));
Assert.assertEquals(map.get("bill").getName(), "bill");
Assert.assertEquals(map.get("monica").getName(), "monica");
return map;
}
}
@Before
public void setup()
{
addPerRequestResource(MyResource.class);
}
@Test
public void testMap() throws Exception
{
JAXBContext ctx = JAXBContext.newInstance(JaxbMap.class, JaxbMap.Entry.class, Foo.class);
JaxbMap map = new JaxbMap("entry", "key", "http://jboss.org/resteasy");
map.addEntry("bill", new Foo("hello"));
JAXBElement<JaxbMap> element = new JAXBElement<JaxbMap>(new QName("http://jboss.org/resteasy", "map", "resteasy"), JaxbMap.class, map);
StringWriter writer = new StringWriter();
ctx.createMarshaller().marshal(element, writer);
String s = writer.toString();
System.out.println(s);
ByteArrayInputStream is = new ByteArrayInputStream(s.getBytes());
StreamSource source = new StreamSource(is);
JAXBContext ctx2 = JAXBContext.newInstance(JaxbMap.class);
element = ctx2.createUnmarshaller().unmarshal(source, JaxbMap.class);
Element entry = (Element) element.getValue().getValue().get(0);
JAXBContext ctx3 = JAXBContext.newInstance(JaxbMap.Entry.class);
JAXBElement<JaxbMap.Entry> e = ctx3.createUnmarshaller().unmarshal(entry, JaxbMap.Entry.class);
System.out.println("hello");
}
@Test
public void testProvider() throws Exception
{
String xml = "<resteasy:map xmlns:resteasy=\"http://jboss.org/resteasy\">"
+ "<resteasy:entry key=\"bill\" xmlns=\"http://foo.com\">"
+ "<foo name=\"bill\"/></resteasy:entry>"
+ "<resteasy:entry key=\"monica\" xmlns=\"http://foo.com\">"
+ "<foo name=\"monica\"/></resteasy:entry>"
+ "</resteasy:map>";
ClientRequest request = new ClientRequest(generateURL("/map"));
request.body("application/xml", xml);
ClientResponse<Map<String, Foo>> response = request.post(new GenericType<Map<String, Foo>>()
{
});
Assert.assertEquals(200, response.getStatus());
Map<String, Foo> map = response.getEntity();
Assert.assertEquals(2, map.size());
Assert.assertNotNull(map.get("bill"));
Assert.assertNotNull(map.get("monica"));
Assert.assertEquals(map.get("bill").getName(), "bill");
Assert.assertEquals(map.get("monica").getName(), "monica");
request = new ClientRequest(generateURL("/map"));
request.body("application/xml", xml);
ClientResponse<String> response2 = request.post(String.class);
System.out.println(response2.getEntity());
}
@Test
public void testWrapped() throws Exception
{
String xml = "<map xmlns:foo=\"http://foo.com\">"
+ "<entry key=\"bill\">"
+ "<foo:foo name=\"bill\"/></entry>"
+ "<entry key=\"monica\">"
+ "<foo:foo name=\"monica\"/></entry>"
+ "</map>";
ClientRequest request = new ClientRequest(generateURL("/map/wrapped"));
request.body("application/xml", xml);
ClientResponse<String> response2 = request.post(String.class);
Assert.assertEquals(200, response2.getStatus());
System.out.println(response2.getEntity());
request = new ClientRequest(generateURL("/map/wrapped"));
request.body("application/xml", xml);
ClientResponse<Map<String, Foo>> response = request.post(new GenericType<Map<String, Foo>>()
{
});
Assert.assertEquals(200, response.getStatus());
Map<String, Foo> map = response.getEntity();
Assert.assertEquals(2, map.size());
Assert.assertNotNull(map.get("bill"));
Assert.assertNotNull(map.get("monica"));
Assert.assertEquals(map.get("bill").getName(), "bill");
Assert.assertEquals(map.get("monica").getName(), "monica");
}
@Test
public void testBadWrapped() throws Exception
{
String xml = "<resteasy:map xmlns:resteasy=\"http://jboss.org/resteasy\">"
+ "<resteasy:entry key=\"bill\" xmlns=\"http://foo.com\">"
+ "<foo name=\"bill\"/></resteasy:entry>"
+ "<resteasy:entry key=\"monica\" xmlns=\"http://foo.com\">"
+ "<foo name=\"monica\"/></resteasy:entry>"
+ "</resteasy:map>";
ClientRequest request = new ClientRequest(generateURL("/map/wrapped"));
request.body("application/xml", xml);
ClientResponse<String> response2 = request.post(String.class);
Assert.assertEquals(400, response2.getStatus());
}
}