JAX-RS: How to return two-dimensional array - jersey

How can I return a two-dimensional array through JAX-RS? The following gets an error:
#Produces(MediaType.APPLICATION_JSON)
public Response getPicks(#PathParam("season") String season, #PathParam("week") int week)
...
Pick[][] allPicks = Pick.Fetch(gameIds);
return Response.status(200).entity(allPicks).build();
SEVERE [http-nio-8079-exec-49]
org.glassfish.jersey.message.internal.WriterInterceptorExecutor$TerminalWriterInterceptor.aroundWriteTo MessageBodyWriter not found for media type=application/json, type=class [[Lcom.lordbah.footballbeans.Pick;, genericType=class [[Lcom.lordbah.footballbeans.Pick;.
while returning a one-dimensional array of the same object works fine:
return Response.status(200).entity(allPicks[0]).build();
The web client gets back a JSON array of Picks.
org.glassfish jaxb-core is back at 2.3.0.1, jersey-* at 2.31, in case it's a known add in later versions. I didn't see anything suggesting so.
It doesn't have any issue with the base object, or with an array of them, but the second dimension confuses it.

Related

How do I return different response in the webflux based on whether the Flux object has elements?

I know there is a function named "hasElements" on a Flux object. But it behaves a bit strangeļ¼
Flux<RoomBO> rooms=serverRequest.bodyToMono(PageBO.class).flatMapMany(roomRepository::getRooms);
return rooms.hasElements().flatMap(aBool -> aBool?ServerResponse.ok().body(rooms,RoomBO.class):ServerResponse.badRequest().build());
return ServerResponse.ok().body(rooms,RoomBO.class)
The second return statement can return the right things I need when the flux object is not empty,but the first return statement only returns a empty array,which likes "[]" in json.I don't know why this could happen!I use the same data to test.The only difference is that I call the hasElements function in the first situation.But I need to return badRequest when the flux object is empty. And the hasElements function seems to make my flux object empty,though I know it doesn't do this actually.
well, finally I decide to call switchIfEmpty(Mono.error()) to throw an error and then I deal with the special error globally(Sometimes it's not suitable to use onErrorReturn or onErrorResume). I think this can avoid the collect operation in memory when meets big data. But it's still not a good solution for the global error handler can be hard to maintain. I'd expect someone to give a better solution.
In your example you are transforming class Flux to class RoomBO, it is one of the reasons, why you get an empty array.
If you need to return the processed list of rooms, then, I think, collectList should be your choice. https://projectreactor.io/docs/core/release/api/reactor/core/publisher/Flux.html#collectList--
Flux<RoomBO> roomsFlux = serverRequest.bodyToMono(PageBO.class)
.flatMapMany(roomRepository::getRooms);
return rooms
.collectList()
.flatMap(rooms -> !rooms.isEmpty() ? ServerResponse.ok().bodyValue(rooms) : ServerResponse.badRequest().build());

Java 8: Comparator returns stream of Object instead of specific type

my question is about the new java 8 collection streaming possibilities. I do have a sorted map with Date objects as keys. Now I have written the method below, which has to find the previous key in the keyset of a given Date. So iterating over the keyset in reverse order it would be the first date which is prior to the given search date. Here is my implementation:
private Date getPreviousKey(Date searchKey, Map<Date, SchluesselSum> timesAndSums) {
return timesAndSums.keySet().stream()
.sorted(Comparator.<Date>reverseOrder())
.filter(date -> date.before(searchKey))
.findFirst()
.orElse(null);
}
Now the problem is, that the call to .sorted(Comparator.reverserOrder()) returns a stream of java.lang.Object instead of Date and my compiler can't find .isLessOrEqual(...) in the .filter(...) call in the class Object.
How can I tell the .sorted method, or to be more precisely, the Comparator to return Date instead of Object?
Thank you in advance for any help!
The problem seemed to be due to your custom Date class.
Note however that if your map also happens to be a NavigableMap (all SortedMaps in the JDK are navigable), you can call NavigableMap#lowerKey:
private Date getPreviousKey(Date searchKey, NavigableMap<Date, SchluesselSum> timesAndSums) {
return timesAndSums.lowerKey(searchKey);
}
This will be more efficient (in terms of lines of code, readability and performance) than your current approach.

Returning a NSUniqueIDSpecifier in -objectSpecifier with key Key does not result in valueIn<Key>WithUniqueID: getting evaluated

The reference documentation for the class NSUniqueIdentifier claims that unique ID specifiers are evaluated in the following scheme:
If the container implements a method whose selector matches the relevant valueIn<Key>WithUniqueID: pattern established by scripting
key-value coding, the method is invoked. This method can potentially
be very fast, and it may be relatively easy to implement.
As is the case when evaluating any script object specifier, the container of the specified object is given a chance to evaluate the
object specifier. If the container class implements the
indicesOfObjectsByEvaluatingObjectSpecifier: method, the method is
invoked. This method can potentially be very fast, but it is
relatively difficult to implement.
An NSWhoseSpecifier object that specifies the first object whose relevant 'ID ' attribute matches the ID is synthesized and evaluated.
The NSWhoseSpecifier object must search through all of the keyed
elements in the container, looking for a match. The search is
potentially very slow.
However, I am not seeing valueIn<Key>WithUniqueID: getting called. To give you an example, I have a class where I describe the object specifier in the following way:
- (NSScriptObjectSpecifier *)objectSpecifier
{
assert(self.documentID);
assert(self.controller);
NSScriptObjectSpecifier *containerRef = self.controller.objectSpecifier;
assert(containerRef);
assert(containerRef.keyClassDescription);
return [[NSUniqueIDSpecifier alloc] initWithContainerClassDescription:containerRef.keyClassDescription
containerSpecifier:containerRef
key:#"allObjects"
uniqueID:self.documentID];
}
The method I have defined in the container class is - (id)valueInAllObjectsWithUniqueID:(NSString *)uniqueID is the method I have defined:
- (id)valueInAllObjectsWithUniqueID:(NSString *)uniqueID {
return [self objectWithIdentifier:uniqueID];
}
In the class corresponding to the container I've also overridden -respondsToSelector: to debug this further, and observe that the only relevant method the scripting system queries is indicesOfObjectsByEvaluatingObjectSpecifier: right after -objectSpecifier above is called (and confirmed to return a non-nil result with the container class description and container specifier consistent with the container's class receiving method calls right after the object specifier is evaluated).
Any ideas? This is on OSX Mavericks (10.9.4).

Sorting JDOM elements using Java API

I need your help with following issue:
In my code I have a list of elements, I need to sort this list according to 2 attributes: season and number.
List example:
<episode_list>
<episode id="280" number="13" season="1">
<title><![CDATA[Bowl Game]]></title>
</episode>
<episode id="314" number="12" season="1">
<title><![CDATA[Piss Test]]></title>
</episode>
<episode id="730" number="11" season="1">
I use Collections.sort(), but getting exception. As I understand I can't use it with JDOM Elements:
List<Element> episodes;
Collections.sort(episodes, new Comparator<Element>() {
#Override
public int compare(Element elem1, Element elem2) {
Integer seasonNumber1 = Integer.valueOf(myService.valueOfAttribute("season", elem1));
Integer seasonNumber2 = Integer.valueOf(myService.valueOfAttribute("season", elem2));
int seasonComp = seasonNumber1.compareTo(seasonNumber2);
if (seasonComp != 0) {
return seasonComp;
} else {
Integer episodeNumber1 = Integer.valueOf(myService.valueOfAttribute("number", elem1));
Integer episodeNumber2 = Integer.valueOf(myService.valueOfAttribute("number", elem2));
return episodeNumber1.compareTo(episodeNumber2);
}
}
});
Exception: java.util.Collections$UnmodifiableList$1.set(Unknown Source)
java.util.Collections.sort(Unknown Source)
Actually I don't need sorted xml, the only thing I need is the episode attribute "id" (for the lowest season and the lowest episode number).
What could you recommend? I have another implementation, where I go through all elements, but I don't think it's a nice solution...I also can create Java class Episode(id, episode, season), transform List to List and sort it, but also don't think it's a good idea. There is also sortContent method for Element, but I'm not sure how to implement it.
I'll appreciate any help.
Content attached to JDOM Elements cannot be sorted using the standard Collections.sort() mechanism because that process does not honour the only-attached-at-one-place-at-a-time rule for XML content.
JDOM has sort() methods built in to the Element class that allows you to sort the chile Elements or other Child content: See The Element.sortChildren() Javadoc for the JDOM way to do it.
Update: Also, for your reference, the error you are getting is because at some point you created an unmodifiable version of the List.... this is not something that happens from JDOM method calls. The error you are getting is because you are trying to modify a List that has been intentionally made read-only.
What's wrong with going through the list and finding the minimum. It is O(n), while sorting is O(n*log(n)). You might use a generic min function, such as the one in guava
Element firstEpisode = Ordering.from(your-comparator).min(episodes.iterator());
If you really want to sort it, why don't you sort new ArrayList<Element>(episodes) (I agree with rolfl that you cannot use Collections.sort for JDOM lists and that the error comes from your use of unmodifiable list).

Gson, How to write a JsonDeserializer for Generic Typed Classes?

Situation
I have a class that holds a generic type, and it also has a non-zero arg constructor. I don't want to expose a zero arg constructor because it can lead to erroneous data.
public class Geometries<T extends AbstractGeometry>{
private final GeometryType geometryType;
private Collection<T> geometries;
public Geometries(Class<T> classOfT) {
this.geometryType = lookup(classOfT);//strict typing.
}
}
There are several (known and final) classes that may extend AbstractGeometry.
public final Point extends AbstractGeometry{ ....}
public final Polygon extends AbstractGeometry{ ....}
Example json:
{
"geometryType" : "point",
"geometries" : [
{ ...contents differ... hence AbstractGeometry},
{ ...contents differ... hence AbstractGeometry},
{ ...contents differ... hence AbstractGeometry}
]
}
Question
How can I write a JsonDeserializer that will deserialize a Generic Typed class (such as Geometires)?
CHEERS :)
p.s. I don't believe I need a JsonSerializer, this should work out of the box :)
Note: This answer was based on the first version of the question. The edits and subsequent question(s) change things.
p.s. I don't believe I need a JsonSerializer, this should work out of the box :)
That's not the case at all. The JSON example you posted does not match the Java class structure you apparently want to bind to and generate.
If you want JSON like that from Java like that, you'll definitely need custom serialization processing.
The JSON structure is
an object with two elements
element 1 is a string named "geometryType"
element 2 is an object named "geometries", with differing elements based on type
The Java structure is
an object with two fields
field 1, named "geometryType", is a complex type GeometryType
field 2, named "geometries" is a Collection of AbstractGeometry objects
Major Differences:
JSON string does not match Java type GeometryType
JSON object does not match Java type Collection
Given this Java structure, a matching JSON structure would be
an object with two elements
element 1, named "geometryType", is a complex object, with elements matching the fields in GeometryType
element 2, named "geometries", is a collection of objects, where the elements of the different objects in the collection differ based on specific AbstractGeometry types
Are you sure that what you posted is really what you intended? I'm guessing that either or both of the structures should be changed.
Regarding any question on polymorphic deserialization, please note that the issue was discussed a few times on StackOverflow.com already. I posted a link to four different such questions and answers (some with code examples) at Can I instantiate a superclass and have a particular subclass be instantiated based on the parameters supplied.

Resources