问题
I have a Front-end application on a separate domain that is communicating with the Restlet backend on a different domain. So far, CORS work properly and the only issue is the bean serialization.
As I check the request it has this Accept
type: application/x-java-serialized-object+gwt
However for some reason I don't know when the backend runs on localhost my GWT app works fine in sending/receiving data to/from the backend (at localhost), but when the backend is deployed in GAE cloud (i.e. appspot.com) then things break. It throws 422 Unprocessable Entity
What could be a solution for the problem above?
I think this is a Restlet framework bug (I am not sure). Now what I want to do now is to simply just get off the serialized GWT processing and just use either JSON or XML (application/json
or application/xml
) on the GWT ClientProxy side, is that possible?
Such that the same app we have should work:
StuffResourceProxy stuffResource = GWT.create(StuffResourceProxy.class);
stuffResource.getClientResource().setReference("http://path.to/resource");
stuffResource.createStuff(model, new Result<Stuff>() {
@Override
public void onFailure(Throwable throwable) {
// handle error
}
@Override
public void onSuccess(Stuff stuff) {
// do thing with stuff
}
});
Update:
Here's what I have tried, adding:
stuffResource.getClientResource().getClientInfo().getAcceptedMediaTypes()
.add(new Preference<MediaType>(MediaType.APPLICATION_JSON));
GWT client was able to send data and server was able to store it, however from Server-to-GWT-client side does not work.
I can see from the request headers that the Content-Type
type sent by the GWT app is application/x-java-serialized-object+gwt
is there a way to force Restlet ClientProxy to send out application/json
instead?
Yet right now the server can process that application/x-java-serialized-object+gwt
POJO on the server side, the issue is with the client side not being able to convert the application/json
response from server.
回答1:
there is no evident reason to stop using GWT serialization between client and server. I you can isolate a sample code, I will be pleased to debug it.
Just a few words before showing you a way to retrieve json. There is an extension for the GWT edition called org.restlet.ext.json (see http://restlet.com/technical-resources/restlet-framework/guide/2.3/editions/gwt/json) which provides a JsonRepresentation class, and provides also a mean to simple handle JSON objects. The main difference is that by doing so, you will only have access to the Json objects provided by GWT library (such as JSONArray, JSONObject), not to your own bean directly. This is a quite difficult task, that require to write dynamically, at compilation time, the deserialization code from the payload to the beans. This task has been done for the GWT serialization format, because most part of the job were already provided by the GWT library. I can assure you the other part is not very easy, see https://github.com/restlet/restlet-framework-java/blob/master/modules/org.restlet/src/org/restlet/rebind/ClientProxyGenerator.java.gwt.
Having said that, if you want to send GWT-serialized payload, and receive json, you can do as follow:
- update the annotated interface in order to receive the payload as a String.
- import the org.restlet.client.ext.json extension to your project
- specify the media type preference to any instance of client resource
- Instantiate manually a JsonRepresentation with the String value
e.g.
Annotated interface:
@Put
public void store(Contact contact, Result<String> callback);
Update of the module.gwt.xml
<inherits name="org.restlet.JSON" />
Media type preference
stuffResource.getClientResource().accept(MediaType.APPLICATION_JSON);
Response consumption (detail):
public void onSuccess(String response) {
try {
JsonRepresentation jRep = new JsonRepresentation(response);
dialogBox.setText("Update contact"
+ jRep.getJsonObject().get("lastName"));
} catch (IOException e) {
}
I hope this will help you.
来源:https://stackoverflow.com/questions/29207489/422-unprocessable-entity-on-restlet-clientproxy-and-gae-server