Error while using part="...,processingDetails" in a youtube.videos.insert() request - java

We're developing in java 7 and YouTube Data API v3.
When we are calling the upload service with "processingDetails" part, we are getting a 503 Service Unavailable Error. What are we doing wrong? If we remove it, we can upload the video just fine. But we want/need to know about processingDetails.
Here is the code:
YouTube.Videos.Insert videoInsert = this.youtube.videos().insert("snippet,statistics,status,processingDetails", videoObjectDefiningMetadata, mediaContent);
everything else it's the same as the java client provided in google API.
Here is the request:
https://www.googleapis.com/upload/youtube/v3/videos?part=snippet,statistics,status,processingDetails
And here is the exception stack trace:
2013-06-14 17:50:40,375 ERROR [] [main] (...)despegar.client.impl.YouTubeMediaClient (YouTubeMediaClient.java:264) : Error
com.google.api.client.googleapis.json.GoogleJsonResponseException: 503 Service Unavailable
at com.google.api.client.googleapis.json.GoogleJsonResponseException.from(GoogleJsonResponseException.java:145)
at com.google.api.client.googleapis.services.json.AbstractGoogleJsonClientRequest.newExceptionOnError(AbstractGoogleJsonClientRequest.java:111)
at com.google.api.client.googleapis.services.json.AbstractGoogleJsonClientRequest.newExceptionOnError(AbstractGoogleJsonClientRequest.java:38)
at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.executeUnparsed(AbstractGoogleClientRequest.java:423)
at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.executeUnparsed(AbstractGoogleClientRequest.java:343)
at com.google.api.client.googleapis.services.AbstractGoogleClientRequest.execute(AbstractGoogleClientRequest.java:460)
at com.despegar.client.impl.YouTubeMediaClient.uploadVideoWithFailureRecovery(YouTubeMediaClient.java:285)
at com.despegar.client.impl.YouTubeMediaClient.uploadAttempt(YouTubeMediaClient.java:260)
Thanks!

Two things:
The part parameter values you include in your youtube.videos.insert() request should correspond to the parts you're specifying in the upload metadata. Normally this would be snippet (since that's the part containing the required title and description) and sometimes status (if you're also setting the public/private status of the video). You can't set statistics or processingDetails during an upload, so you shouldn't include them in the list of parts. You can still request the statistics or processingDetails parts after the upload completes, via a youtube.videos.list() call.
The API should return a meaningful error message explaining this to you instead of returning a generic 503. I'll file a bug with the engineering team asking them to take care of that.

Related

Unable to retrieve data from Sabre PriceQuoteServicesRQ 4.10 SOAP API: XML request schema validation failed: PriceQuoteInfo element is not complete

I have a problem when trying to retrieve data from Manage Price Quote Details (PriceQuoteServicesRQ) 4.10 Sabre SOAP API.
I generated Java classes using the WSDL from Sabre website (https://developer.sabre.com/docs/soap_apis/air/fulfill/manage_price_quote_details/resources).
I am constructing my request object in a following way:
ReservationTypeShort reservation = new ReservationTypeShort();
reservation.setValue("YEZUYS");
PriceQuoteInfoSearchParameters info = new PriceQuoteInfoSearchParameters();
info.setReservation(reservation);
PriceQuoteSearchParameters searchParameters = new PriceQuoteSearchParameters();
searchParameters.getPriceQuoteInfo().add(info);
searchParameters.setResultType(StringResultType.S);
GetPriceQuoteRQ req = new GetPriceQuoteRQ();
req.setSearchParameters(searchParameters);
req.setVersion("4.1.0");
I pretty-printed the object and this is what I got:
"priceQuoteInfo" : [ {
"reservation" : {
"value" : "YEZUYS",
"createDate" : null
},
"status" : [ ],
"type" : null,
"priceQuote" : [ ],
"travelItinerary" : null
} ],
So according to their documentation:
I am supplying all fields that are necessary, however it still doesn't work for me.
Did anybody else had the same problem? What am I missing/what am I doing wrong?
This is the error message I am getting:
XML request schema validation failed: PriceQuoteInfo element is not complete. One of the following fields: Status, Type, PriceQuote, TravelItinerary should be used. Please amend your request and try again.
What I have tried so far?
I asked Sabre Support for help, but they responded with a message that basically says "it works on my end".
I intercepted the XML body:
<ns5:GetPriceQuoteRQ version="4.1.0">
<ns5:SearchParameters resultType="S">
<ns5:PriceQuoteInfo>
<ns5:Reservation>YEZUYS</ns5:Reservation>
</ns5:PriceQuoteInfo>
</ns5:SearchParameters>
</ns5:GetPriceQuoteRQ>
I was missing an empty element <PriceQuote/> in my request.
It can be added by doing:
PriceQuoteInfoSearchParameters info = new PriceQuoteInfoSearchParameters();
info.setReservation(reservation);
info.getPriceQuote().add(new PriceQuoteSearch());
So according to their documentation I am supplying all fields that are necessary [...]
By documentation do you mean the WSDL or some human readable documentation (like PDF, DOCX, web pages, etc)? According to the error message you get, your SOAP request isn't valid. Sabre Support responding with "it works on my end" is another way of saying that you are not doing something correctly on your end. You need to troubleshoot your request.
From what I see, the error message is saying Status, Type, PriceQuote, and TravelItinerary but you are sending status, type, priceQuote, and travelItinerary. XML is case sensitive, and it's possible the service field names are too, so this might be the first thing to check.
Then, two of your fields (type and travelItinerary) are null. Also, priceQuote is empty. Is that OK? This is the next thing to check.
The object you pretty-printed shows a JSON format. Is this actually the format you are sending on the wire to the service? SOAP wants XML, not JSON. You also mention you generated the code from the WSDL. Using what framework or library? Does the generated code send XML?
Like I said, you need to troubleshoot the call:
download SoapUI
feed the WSDL file to SoapUI so that it can generate sample requests for you
fill in those request with real data and make calls to the web service until you get back a successful and expected response
using the same parameters from 3) in your code, perform the same call using your code
use SoapUI's monitoring tools to intercept the request at 4) and inspect the SOAP message you are sending
check the request you are making with your code against the successful request you got by using SoapUI directly
correct any differences until your request made by code is like the one send from SoapUI and it returns a successful and expected response.

Amazon API Gateway 403 Forbidden

Recently, I used the Amazon API Gateway .I created an api ,but the API failed all the time.
At the beginning,I didn't add request headers.The result that API responsed is as follows:
HTTP/1.1 403 Forbidden
{"message":null, "type": "ACCESS_DENIED", "status":"", "other":"" }
Then ,I added a header which named host,the result changed.
HTTP/1.1 403 Forbidden
{"message":"Forbidden"}
I didn't use other AWS.
I set the authorization is none and the API key required is false.
enter image description here
Could you help me?
Thanks!
A cause of {"message":"Forbidden"} which I had which had me stumped was that I had not deployed my API.
For anyone having this issue, check if your gateway has been deployed.
First you will need a Stage, with which you can click Deploy API from the Actions dropdown, selecting your stage.
Deploying will give you an invoke_url, (which ends in /{stage-name}.
For those using Terraform....
You can define an aws_api_gateway_stage which depends on aws_api_gateway_deployment. There is a known issue, at the time of writing, where the deployment doesn't re-trigger, which was the original cause of my forbidden error.
To fix this and get the deployment to run everytime a change has been made, add to aws_api_gateway_deployment:
resource "aws_api_gateway_deployment" "gateway-deployment" {
...
stage_description = "Terraform hash ${md5(join(",", local.all_resources))}"
lifecycle {
create_before_destroy = true
}
}
locals {
all_resources = [
"${aws_api_gateway_resource.simulator-gateway-resource.path}:${aws_api_gateway_method.simulator-gateway-method.http_method}:${aws_api_gateway_integration.simulator-gateway-integration.uri}",
]
}```

Proper Http status codes for uploading files on rest end point

We are developing an application that allows a user to upload file on rest end point.
Could someone please guide if it is correct to send 400 error code for the failure of following validation scenario:
1) The Length of file name exceeds permissible limit.
2) File name contains special characters
3) Uploaded file was empty
4) The System failed to read the uploaded file from disk.
Regards,
Tarun
The Length of file name exceeds permissible limit.
I think the 400 is not an appropriate because syntax of the request is correct in this case. The 422 Unprocessable Entity is better in this case.
File name contains special characters
Illegal characters mean the syntax is broken. So 400 Bad Request is a proper response in this case. Someone may claim that a definition of illegal characters is needed so the server may authoritatively send 400.
Uploaded file was empty
I think it is not an error because an empty file is a legal file.
The System failed to read the uploaded file from disk.
Does the system mean the server? Then the server should return a 5xx response because it is not a client failure. In case of general read error the server should return 500.
EDIT:
Uploaded file was empty.
When application semantic forbids an empty file the 400 or 422 appropriate. More details about them is at 400 vs 422 response to POST of data
4xx statuses are for client-side errors, 5xx are for server-side errors. So, generally you need 4xx codes for your cases 1) to 3), while 4) should be a 5xx error.
Let’s first say that for your case 4), a simple HTTP 500 seems appropriate. If you want to indicate that the client could try again later, HTTP 503 would be more suitable.
Now for 1) to 3): According to RFC 2616, HTTP 400 indicates syntax errors; this would usually be protocoll errors, e.g. invalid headers. Semantical or payload errors aren’t really defined in this generic RFC, however, (as Zaboj mentions) WebDAV offers HTTP 422, which seems suitable, though it’s not really meant for generic HTTP.
In the end, it doesn’t really matter which particular codes you send. If your upload fails with HTTP 400 or 422, in either case the client will perform some error routine (e.g. show or log the error message).
The important thing to know is that some codes can trigger client behaviour (e.g. HTTP 401 combined with certain headers can trigger an authentication dialog in a browser), and you should be aware of these side effects.
In my opinion, it is much more important to send a useful error description in the response body to help the client fix their problem, than finding the “perfect” HTTP status code. I know that REST zealots will disagree, but none of them will be able to give you the right HTTP status code for every situation.
That said, if you want to issue fine-grained error codes/messages for automated processing, you can introduce custom HTTP header fields, e.g.
X-MyApp-Error-Code: 2.1.6
X-MyApp-Error-Message: The uploaded file is empty
Then you would provide a documentation and/or SDK which reveals all possible error code values for X-MyApp-Error-Code to your API consumers.

Exchange authorizational code works only once - Oauth2.0

I'm trying to implement this code. https://developers.google.com/drive/web/credentials#retrieve_oauth_20_credentials
I have my client id and client_secrets json for webapps, because I'm extracting some values from a spreadsheet, everything is ok and I already have spreadsheet's data in my application. But my question is How can I make to re-use that authorization code multiple times?, because I have to extract more data from that spreadsheet, my URL is http://localhost:8080/cluster/?state=/profile&code=xxxxxxx but for example when I try to refresh that page this error appears.
An error occurred: com.google.api.client.auth.oauth2.TokenResponseException: 400 Bad Request
{
"error" : "invalid_grant",
"error_description" : "Code was already redeemed."
}
I have the same implementation of the url, but the only difference is I changed this methods storeCredentials(userId, credentials) - getStoredCredentials(userId) and put that values into a db table.
So, How can I implement 'exchange authorization code'? and how can I link my application to the new url?
Thanks for your help! :D
First at all, following the protocol the authorization code MUST BE used once, so the auth server must invalidate it after the first use.
If you want to use it for another part of your implementation, you can save it, use it and send a 302 redirect to your other page witch use your getStoredCredentials method

Play 2 GET method maximum length

I am using Play framework (Java) to create REST apis for my application.
I am facing problem with length of REST API with GET.
I need below web method to be used:
public static Result getregistereduser(String userlist)
{
//userlist is string of user numbers seperated by "$" ,
.....
....
}
in routes I have :
GET /getregistereduser controllers.Application.getregistereduser(userlist)
Problem I am facing is when userlist is large it only takes partial string.
I'm not sure what version of Play you're using, but Play shouldn't truncate long GET requests. You should get an error response if the GET request is too large for it to handle.
Up until recently that error would be a 500 Internal Server Error caused by an org.jboss.netty.handler.codec.frame.TooLongFrameException. With Play 2.3.0 (not yet released) you'll get a 414 Request URI too long response instead.
Play inherits its HTTP header parsing from Netty. The first line of the header (GET /path HTTP/1.1) can be up to 4096 bytes by default. This can be configured by with the http.netty.maxInitialLineLength system property (see this mailing list thread).
I agree that you're most likely seeing problem with your HTTP client. I'd recommend using a debugging proxy like Charles (or a free alternative) to look at exactly what HTTP requests your client is sending.

Categories