I'm using RestSharp to try to upload a video to Vimeo, but I keep getting an Http 413 RequestEntityTooLarge error. I think I'm sending just the bytes and not the encoded video, so I'm not sure what is wrong. This is my code:
//construct request
RestRequest request = new RestRequest(endpoint);
request.Method = Method.PUT;
//add headers
request.AddHeader("Authorization", string.Format("Bearer {0}", _accessToken));
request.AddHeader("Content-Length", fileSize.ToString());
request.AddHeader("Content-Type", mimeType);
request.AddParameter(mimeType, fileData, ParameterType.RequestBody);
//allow for the transfer of larger files (10min timeout)
request.Timeout = 2400000;
// Upload the file
IRestResponse uploadResponse = _client.Execute(request);
This has nothing to do with your code. Vimeo is telling you what's wrong; The file you're uploading is too large for them to accept.
Double check that your fileSize variable is correct. If incorrect, Vimeo may thing you're trying to upload a file that's much larger than it really is.
If the file is, in fact, too large, compress it using any number of file compressors and then upload that.
UPDATE: According to this forum post, you need to make sure you're not encoding your file in any way.
Related
I am trying to upload a PNG file using the Zendesk Attachments API and Restsharp. It seems to upload fine but when I click the content url it says the image cannot be displayed because it contains an error.
I am able to upload a pdf by using the same call after changing the file extensions to pdf and it works fine.
var request = new RestRequest("uploads.json? filename=file1.png", Method.POST);
request.AddHeader("Content-Type", "application/binary");
request.AddHeader($"Authorization", "Basic {config.api}");
request.AddFile("file1", path, "image/png");
var response = client.Execute(request);
The api call is successful but when I look at the content URL that is returned from the call I get "Image can't be displayed because it contains errors".
I figured this out finally. Here is the solution: https://stackoverflow.com/a/45382624
I removed these two lines:
request.AddHeader("Content-Type", "application/binary");
request.AddFile("file1.png", path, "application/binary");
And added this line:
request.AddParameter("application/binary", File.ReadAllBytes(pathToFile), ParameterType.RequestBody);
Now it works with all file types.
I have a library that I wrote a while ago that allows me to post a new status to Twitter. So handling of the OAuth headers etc is all working.
However, I now have a requirement to upload an image using the Twitter REST API:
https://upload.twitter.com/1.1/media/upload.json
When posting a status I normally put the following in the request stream 'status=<my tweet here>'
Ideally I want to post the raw image data rather than a Base64 string, however, I am having issues with each of them working.
According to Twitter, the OAuth should only be build up from the keys starting 'oauth_' - I am only putting the following in:
parameters.Add("oauth_consumer_key", consumerKey);
parameters.Add("oauth_signature_method", "HMAC-SHA1");
parameters.Add("oauth_timestamp", Base.Methods.UNIXTimestamp);
parameters.Add("oauth_nonce", Guid.NewGuid().ToString().Replace("-", ""));
parameters.Add("oauth_version", "1.0");
parameters.Add("oauth_token", token);
Twitter says that when in doubt to use a content type of application/octet-stream - when doing this, I get a response of:
Code: 38
Message: Missing Parameter Media
In fact, I also get the same response when setting the content type to multipart/form-data as suggested in other pages from Twitter
I have tried various combinations of add the image data to the webrequest, and all seem to fail.
media=<my image byte data here>
Add header of 'media' with image data in the request
and as many other combinations I can think of. I even get the same issues when trying to send the Base64 version (which I'd rather not do).
Having read through lots of other questions I don't seem to be able to see what I am doing wrong.
Can anyone help?
I have found the problem, and it all comes down to the content being sent in the request stream.
As twitter says, only send in the oauth_xxxx parameters, the content based ones are not needed for this request.
The trick is the building up of the multipart form, I have done the following:
I am using an HttpWebrequest, so set it up to send the multipart form headers:
string boundary = "----" + DateTime.UtcNow.Ticks.ToString("x");
webRequest.ContentType = "multipart/form-data; boundary=" + boundary;
Build the content to be sent, which has both a prefix and a suffix to the actual image data
StringBuilder prefixData = new StringBuilder();
prefixData.Append("--");
prefixData.Append(boundary);
prefixData.Append(Environment.NewLine);
prefixData.Append("Content-Disposition: form-data; name=\"media\"");
prefixData.Append(Environment.NewLine);
prefixData.Append(Environment.NewLine);
byte[] prefix = Encoding.UTF8.GetBytes(prefixData.ToString());
StringBuilder suffixData = new StringBuilder();
suffixData.Append(Environment.NewLine);
suffixData.Append("--");
suffixData.Append(boundary);
suffixData.Append("--");
byte[] suffix = Encoding.UTF8.GetBytes(suffixData.ToString());
Join each of the data sections together to post to the stream:
byte[] data = new byte[prefix.Length + imageData.LongLength + suffix.Length];
Buffer.BlockCopy(prefix, 0, data, 0, prefix.Length);
Buffer.BlockCopy(imageData, 0, data, prefix.Length, imageData.Length);
Buffer.BlockCopy(suffix, 0, data, prefix.Length + imageData.Length, suffix.Length);
Write the data to the request stream as normal.
I Am in need of knowing the last modification DateTime of a remote file prior to downloading the entire content. This to save up on downloading bytes I am never going to need anyway.
Currently I am using WebClient to download the file. It is not needed to keep the use of WebClient specifically. The Last-Modified key can be found within the response headers but the entire file is downloaded at that point in time.
WebClient webClient = new WebClient();
byte[] buffer = webClient.DownloadData( uri );
WebHeaderCollection webClientHeaders = webClient.ResponseHeaders;
String modified = webClientHeaders.GetKey( "Last-Modified" );
Also I am not sure if that key is always included at each file on the internet.
You can use the HTTP "HEAD" method to just get the file's headers.
...
var request = WebRequest.Create(uri);
request.Method = "HEAD";
...
Then you can extract the last modified date and check whether to download the file or not.
Just be aware that not all servers implement Last-modified properly.
I am attempting to upload a csv file but I can't seem to get it to work programatically. If I use Postman in Chrome to send the file it works and here is what it sends (Fiddler output):
------WebKitFormBoundary2YsMyLR3QAPruTy4
Content-Disposition: form-data; name="Content-Type"; filename="613022.csv"
Content-Type: application/vnd.ms-excel
// File Content here
------WebKitFormBoundary2YsMyLR3QAPruTy4--
However, using this code:
WebClient wc = new WebClient();
wc.Credentials = new NetworkCredential(user, pw);
wc.Headers[HttpRequestHeader.Cookie] = "OBBasicAuth=fromDialog";
wc.Headers[HttpRequestHeader.ContentType] = "application/vnd.ms-excel";
wc.UploadFile(baseURL + service + apiVersion + resource, "post", file);
Results in (Fiddler output):
-----------------------8d101dbe85fe96c
Content-Disposition: form-data; name="file"; filename="613022.csv"
Content-Type: application/vnd.ms-excel
// File Content here
-----------------------8d101dbe85fe96c--
Which does not work and the server returns a 503 error. The only difference I see is in the Content-Disposition name. How can I set this or is there a better way to accomplish this?
Perhaps you need "upload" instead of "post" in the method parameters - just guessing.
I believe the problem with your original approach is that WebClient.UploadFile generates the multipart/form-data request in a way that is unexpected by the server, hence the 5xx error code.
After looking around for a bit, I think the answer to this question should give you a starting point to tweak the request according to your needs.
I am trying to upload some avi file to server. It works fine with HttpRequest but i need to continue uploading even if i suspend app so thats why i am trying to use BackgroundUploader. I am following this guideline on msdn http://msdn.microsoft.com/en-us/library/windows/apps/jj152727.aspx. So my code looks something like this.
StorageFile storageFile = KnownFolders.VideosLibrary.GetFileAsync("fileName");
BackgroundUploader uploader = new BackgroundUploader();
uploader.Method = "POST";
uploader.SetRequestHeader("Content-Type", "multipart/form-data; boundary=" + boundary);
var fs = await storageFile.OpenAsync(Windows.Storage.FileAccessMode.ReadWrite);
IInputStream aaaa = fs.GetInputStreamAt(0);
UploadOperation upload = uploader.CreateUploadFromStreamAsync(new Uri("uploadUri"), aaaa);
await HandleUploadAsync(upload, true);
the rest is same as on MSDN. And i am getting exception Unsupported media type (415) in method HandleUploadAsync on line
await upload.StartAsync().AsTask(cts.Token, progressCallback);
What am i doing wrong? Or what can cause this kind of exception?
EDIT : I solved my problem as i commented down here and in my answer. I think at the end i am basically just sending some data to server that are recognized and interpreted as i want to. So if i use BackgroundUploader i am not only uploading some file i am also sending information about how am i doing that(as i mentioned in my answer). So by the same idea i can also upload folder to server and by that i am not sending any actual content only some description about how to do that. And if i compare request that i am making by HttpRequest and BackgroundUploader they are equal and thats what i wanted.
So the problem part was the header of request. I have some header in my request that is recognized by server and i was trying to put it to BackgroundUploader through SetRequestheader method but it did not work. As Kieqic suggested i used Fiddler and by that i compare request made by HttpRequest and BackgroundUploader. I found out they are completely different. So through SetRequestheader i add some parts like expected Content-Type and for the rest parts of header to make them equal i add it before content of my file as array of bytes. And this works so conclusion is in my case using Fiddler that helped my how to construct request header.