[Solved] Video Upload API Error 413 - Request Entity too Large

I finally decided to implement the videos-upload api into my library after a while of putting it off. Steps one and two went smoothly, however I’m hung up on step 3, uploading each part.

I have separated the video file into each 20MB segments and I’m passing the byte arrays to the following method:

public async Task<HttpStatusCode> UploadVideoPartAsync(string video_id, string part, string upload_token, byte[] data)
{
    RestRequest request = Request("upload/{video_id}", Method.PUT, ApiVersion.v4);
    request.AddHeader("Content-Length", data.Length.ToString());
    request.AddUrlSegment("video_id", video_id);
    request.AddQueryParameter("part", part);
    request.AddQueryParameter("upload_token", upload_token);
    request.RequestFormat = DataFormat.Json;
    request.AddBody(data);

    IRestResponse<object> response = await client.ExecuteTaskAsync<object>(request);

    return response.StatusCode;
}

However, I always get status 413: Request entity too large. I double checked my byte arrays and they are definitely 20MB in size and am passing through the right byte array to the method. I’ve also tried just about every option to add a body with RestSharp, the rest request library that I’ve been using, yet nothing works and I always get status 413.

UPDATE
So it turns out with the newest version of RestSharp, you can specify custom Content-Types through parameters as well as pass through the data to be sent without needing to use request.AddBody(). This allows you to bypass the two native serialize method RestSharp uses, Json and XML, and send the raw bytes instead. By doing this I was able to upload the video in 20MB segments instead of 5MB using this very small modification to the method:

public async Task<HttpStatusCode> UploadVideoPartAsync(string video_id, string part, string upload_token, byte[] raw_data)
{
    RestRequest request = Request("upload/{video_id}", Method.PUT, ApiVersion.v4);               
    request.AddUrlSegment("video_id", video_id);
    request.AddQueryParameter("part", part);
    request.AddQueryParameter("upload_token", upload_token);

    //simple, yet effective
    request.AddHeader("Content-Length", raw_data.Length.ToString()); 
    request.AddParameter("application/bson", raw_data, ParameterType.RequestBody);

    IRestResponse<object> response = await uploads_api_client.ExecuteTaskAsync<object>(request);

    return response.StatusCode;
}

Okay, I did a little digging and eventually got the upload portion to work as well as figuring out why I was getting error 413. Here were my discoveries:

When I was initially trying to send the request, I was assuming that it was sending the raw bytes using binary serialization even though I was specifying JSON. Idiocy at its finest, I know. RestSharp by default serializes all requests into either XML or JSON format. Doing so inflates the size of the request by a considerable amount. Switching to binary serialization would solve the request size inflation issue and would allow the the max 25MB limit to be sent. However, RestSharp does not natively support binary serialization so this is not an option to me or anyone else using this library.

There is a work around while still using RestSharp and JSON serialization. Bumping the video segment size all the way down to 5MB from 20MB resulted in status 200 ‘OK’, a successful upload. Another option would be to use a different library which uses binary serialization to avoid the request size inflation. But this solution adds yet another dependency, something I’m not sure is worth doing at this point, but maybe sometime in the future.

Just food for thought and a heads up for anyone else who has a similar issue.

Posted an update with how to send binary data with BSON and RestSharp to avoid using JSON or XML.

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.