EDIT shorter version
Ok so looking at my own post I realize this is perhaps not the shortest thing to read, so I thought I would write a more concise version with some more hands-on details.
I am using Jersey 2 client framework to code against the Documentum REST API, hosted for the time being on my local machine. If I execute the following code:
WebTarget target = client.target("http://localhost:8080/dctm-rest/repositories/repo");
Response response = t.request().get();
and the XML which is returned looks like this
<?xml version="1.0" encoding="UTF-8"?>
<repository xmlns="http://identifiers.emc.com/vocab/documentum" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<... metadata entries></>
<links>
<link rel="self" href="http://localhost:8080/dctm-rest/repositories/repo"/>
<link rel="http://identifiers.emc.com/linkrel/users" href="http://localhost:8080/dctm-rest/repositories/darwin_test/users"/>
<... more links />
</links>
</repository>
... then what do I have to do in order to get the links in the response in the following manner:
Link self = response.getLink("self");
The above command just ends up with self
being null
.
END EDIT
I've tried my best finding a solution to this but with no luck so far.
Basically I am consuming a REST webservice which by default returns JSON formatted resources, which is pretty nice (alot nicer than xml anyway). I am using Jersey 2.4.1 to consume the service, and while I am pretty new to coding against REST-services, I haven't had any real issues besides this (and this is really more Jersey-related than REST as far as I can tell).
Basically, I am having no luck whatsoever in utilizing the Jersey 2 API for retrieving and traversing links, which are returned by the service. Jersey 2 has the following (short) example in its documentation:
// server side - adding links to a response:
Response r = Response.ok().
link("http://oracle.com", "parent").
link(new URI("http://jersey.java.net"), "framework").
build();
Which imho is the equivalence of the following returned data:
<link rel="parent" href="http://oracle.com"/>
<link rel="framework" href="http://jersey.java.net"/>
Now to get the links for these relations, the clientside code in the documentation looks like this:
// client-side processing:
final Response response = target.request().get();
URI u = response.getLink("parent").getUri();
URI u = response.getLink("framework").getUri();
I think this is pretty straightforward. Now my service, in the URL that my WebTarget object is pointing at, has roughly 10 links in the following JSON format:
{
... <metadata before the links> ...
"links" :
[
{
"rel" : "some relation",
"href" : "some http url"
}
... about 10 more entries like this
]
}
The problem is that if I do the client-side equivalence of what was in the documentation:
WebTarget t = client.target("url");
t.request().get().getLinks();
..then I get back nothing but an empty Set<Link>
.
I suspect it might have to do with enabling JSON-binding in the Client
somehow, but I have tried adding the dependency for MOXy, which appearently should be self-enabled if it's in the classpath, and that didn't help.
I'm sure I am missing something extremely basic but I've been searching all day, testing different media-type requests and anything I can think of but with no luck. And while my application is working fine without this sort of link-processing, I still want to get this working.
Thanks for any help on this.
// Andreas
EDIT Response to user1888440
I agree, the links are indeed in the entity returned when the resource is queried. This also aligns with the way I've been processing resources, where I use:
JsonObject o = Json.createReader(target.request().get().readEntity(InputStream.class)).readObject();
.. and then query the object for links in the following manner: I need to first get the "links"-JsonArray from the JsonObject o, then iterate over all links found, compare the "rel"-description with what I'm after and return the correct "href"-value.
However I think there should be a smoother way to get to the links in an entity, especially if we compare this procedure with the following:
response = target.request().get();
URI u = response.getLink("parent").getUri();
URI u = response.getLink("framework").getUri();
And I get what you're saying, that the above getLink("rel") / getLinks() methods only apply to links in the header of the response. But surely there must be some equivalent way of processing links inside an entity, which isn't as verbose as what I've described above?
PS: The example you suggested, to read an resource entity into a Map
:
Map entity = t.get( Map.class );
.. doesn't work and results in a null
value for entity
.
The vendor is sending you the links in the entity that is embedded in the response not links in the response itself. Try this:
Map entity = t.get( Map.class );
Map<String,String> links = (Map<String,String>)entity.get( "links );
URI uriSelf = URI.create( links.get( "self" ) );
You see the links are in the entity not in the header of the request. The response links are for header links. You can also make a more specific object, this is just using maps to get at the property data.