Skip to content
This repository has been archived by the owner on Dec 24, 2022. It is now read-only.

Commit

Permalink
Extract .NET 4.5 HttpUtils + add async overloads
Browse files Browse the repository at this point in the history
  • Loading branch information
mythz committed Oct 27, 2020
1 parent 4708869 commit 1e1e0ad
Show file tree
Hide file tree
Showing 2 changed files with 166 additions and 59 deletions.
170 changes: 166 additions & 4 deletions src/ServiceStack.Text/HttpUtils.cs
Original file line number Diff line number Diff line change
Expand Up @@ -1076,6 +1076,15 @@ public static Task<HttpWebResponse> GetResponseAsync(this HttpWebRequest request
return tcs.Task;
}

private static byte[] GetHeaderBytes(string fileName, string mimeType, string field, string boundary)
{
var header = "\r\n--" + boundary +
$"\r\nContent-Disposition: form-data; name=\"{field}\"; filename=\"{fileName}\"\r\nContent-Type: {mimeType}\r\n\r\n";

var headerBytes = header.ToAsciiBytes();
return headerBytes;
}

public static void UploadFile(this WebRequest webRequest, Stream fileStream, string fileName, string mimeType,
string accept = null, Action<HttpWebRequest> requestFilter = null, string method = "POST", string field = "file")
{
Expand All @@ -1093,10 +1102,7 @@ public static void UploadFile(this WebRequest webRequest, Stream fileStream, str

var boundaryBytes = ("\r\n--" + boundary + "--\r\n").ToAsciiBytes();

var header = "\r\n--" + boundary +
$"\r\nContent-Disposition: form-data; name=\"{field}\"; filename=\"{fileName}\"\r\nContent-Type: {mimeType}\r\n\r\n";

var headerBytes = header.ToAsciiBytes();
var headerBytes = GetHeaderBytes(fileName, mimeType, field, boundary);

var contentLength = fileStream.Length + headerBytes.Length + boundaryBytes.Length;
PclExport.Instance.InitHttpWebRequest(httpReq,
Expand All @@ -1115,6 +1121,43 @@ public static void UploadFile(this WebRequest webRequest, Stream fileStream, str
PclExport.Instance.CloseStream(outputStream);
}

public static async Task UploadFileAsync(this WebRequest webRequest, Stream fileStream, string fileName, string mimeType,
string accept = null, Action<HttpWebRequest> requestFilter = null, string method = "POST", string field = "file",
CancellationToken token=default)
{
var httpReq = (HttpWebRequest)webRequest;
httpReq.Method = method;

if (accept != null)
httpReq.Accept = accept;

requestFilter?.Invoke(httpReq);

var boundary = Guid.NewGuid().ToString("N");

httpReq.ContentType = "multipart/form-data; boundary=\"" + boundary + "\"";

var boundaryBytes = ("\r\n--" + boundary + "--\r\n").ToAsciiBytes();

var headerBytes = GetHeaderBytes(fileName, mimeType, field, boundary);

var contentLength = fileStream.Length + headerBytes.Length + boundaryBytes.Length;
PclExport.Instance.InitHttpWebRequest(httpReq,
contentLength: contentLength, allowAutoRedirect: false, keepAlive: false);

if (ResultsFilter != null)
{
ResultsFilter.UploadStream(httpReq, fileStream, fileName);
return;
}

using var outputStream = PclExport.Instance.GetRequestStream(httpReq);
await outputStream.WriteAsync(headerBytes, 0, headerBytes.Length, token).ConfigAwait();
await fileStream.CopyToAsync(outputStream, 4096, token).ConfigAwait();
await outputStream.WriteAsync(boundaryBytes, 0, boundaryBytes.Length, token).ConfigAwait();
PclExport.Instance.CloseStream(outputStream);
}

public static void UploadFile(this WebRequest webRequest, Stream fileStream, string fileName)
{
if (fileName == null)
Expand All @@ -1126,6 +1169,17 @@ public static void UploadFile(this WebRequest webRequest, Stream fileStream, str
UploadFile(webRequest, fileStream, fileName, mimeType);
}

public static async Task UploadFileAsync(this WebRequest webRequest, Stream fileStream, string fileName, CancellationToken token=default)
{
if (fileName == null)
throw new ArgumentNullException(nameof(fileName));
var mimeType = MimeTypes.GetMimeType(fileName);
if (mimeType == null)
throw new ArgumentException("Mime-type not found for file: " + fileName);

await UploadFileAsync(webRequest, fileStream, fileName, mimeType, token: token).ConfigAwait();
}

public static string PostXmlToUrl(this string url, object data,
Action<HttpWebRequest> requestFilter = null, Action<HttpWebResponse> responseFilter = null)
{
Expand Down Expand Up @@ -1153,6 +1207,114 @@ public static string PutCsvToUrl(this string url, object data,
return SendStringToUrl(url, method: "PUT", requestBody: data.ToCsv(), contentType: MimeTypes.Csv, accept: MimeTypes.Csv,
requestFilter: requestFilter, responseFilter: responseFilter);
}

public static WebResponse PostFileToUrl(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webReq.UploadFile(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "POST");
}

if (ResultsFilter != null)
return null;

return webReq.GetResponse();
}

public static async Task<WebResponse> PostFileToUrlAsync(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null, CancellationToken token=default)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

await webReq.UploadFileAsync(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "POST", token: token);
}

if (ResultsFilter != null)
return null;

return await webReq.GetResponseAsync();
}

public static WebResponse PutFileToUrl(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webReq.UploadFile(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "PUT");
}

if (ResultsFilter != null)
return null;

return webReq.GetResponse();
}

public static async Task<WebResponse> PutFileToUrlAsync(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null, CancellationToken token=default)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

await webReq.UploadFileAsync(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "PUT", token: token);
}

if (ResultsFilter != null)
return null;

return await webReq.GetResponseAsync();
}

public static WebResponse UploadFile(this WebRequest webRequest,
FileInfo uploadFileInfo, string uploadFileMimeType)
{
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webRequest.UploadFile(fileStream, fileName, uploadFileMimeType);
}

if (ResultsFilter != null)
return null;

return webRequest.GetResponse();
}

public static async Task<WebResponse> UploadFileAsync(this WebRequest webRequest,
FileInfo uploadFileInfo, string uploadFileMimeType)
{
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

await webRequest.UploadFileAsync(fileStream, fileName, uploadFileMimeType);
}

if (ResultsFilter != null)
return null;

return await webRequest.GetResponseAsync();
}
}

//Allow Exceptions to Customize HTTP StatusCode and StatusDescription returned
Expand Down
55 changes: 0 additions & 55 deletions src/ServiceStack.Text/PclExport.Net45.cs
Original file line number Diff line number Diff line change
Expand Up @@ -535,61 +535,6 @@ public static StringCollection ToStringCollection(List<string> items)

public static class PclExportExt
{
//HttpUtils
public static WebResponse PostFileToUrl(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webReq.UploadFile(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "POST");
}

if (HttpUtils.ResultsFilter != null)
return null;

return webReq.GetResponse();
}

public static WebResponse PutFileToUrl(this string url,
FileInfo uploadFileInfo, string uploadFileMimeType,
string accept = null,
Action<HttpWebRequest> requestFilter = null)
{
var webReq = (HttpWebRequest)WebRequest.Create(url);
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webReq.UploadFile(fileStream, fileName, uploadFileMimeType, accept: accept, requestFilter: requestFilter, method: "PUT");
}

if (HttpUtils.ResultsFilter != null)
return null;

return webReq.GetResponse();
}

public static WebResponse UploadFile(this WebRequest webRequest,
FileInfo uploadFileInfo, string uploadFileMimeType)
{
using (var fileStream = uploadFileInfo.OpenRead())
{
var fileName = uploadFileInfo.Name;

webRequest.UploadFile(fileStream, fileName, uploadFileMimeType);
}

if (HttpUtils.ResultsFilter != null)
return null;

return webRequest.GetResponse();
}

//XmlSerializer
public static void CompressToStream<TXmlDto>(TXmlDto from, Stream stream)
{
Expand Down

0 comments on commit 1e1e0ad

Please sign in to comment.