Asp.net web api 葡萄藤的文件上传示例

Asp.net web api 葡萄藤的文件上传示例,asp.net-web-api,grapevine,Asp.net Web Api,Grapevine,我不熟悉Web API和REST服务,希望构建一个简单的REST服务器来接受文件上传。我找到了简单易懂的小道消息。我找不到任何文件上载示例 这是一个使用System.Web.Http的示例 var streamProvider = new MultipartFormDataStreamProvider(ServerUploadFolder); await Request.Content.ReadAsMultipartAsync(streamProvider); 但是grapevine请求

我不熟悉Web API和REST服务,希望构建一个简单的REST服务器来接受文件上传。我找到了简单易懂的小道消息。我找不到任何文件上载示例

这是一个使用System.Web.Http的示例

 var streamProvider = new MultipartFormDataStreamProvider(ServerUploadFolder);

 await Request.Content.ReadAsMultipartAsync(streamProvider);

但是grapevine请求属性没有任何方法可以做到这一点。有人能给我举个例子吗?

如果您试图将文件作为二进制负载上传,请参阅GitHub上的


如果您试图从表单提交上传一个文件,这将有点棘手,因为还没有添加多部分有效负载解析器,但这仍然是可能的

以下代码示例完全未经测试,我只是在脑海中写下了这一点,因此它可能不是最佳解决方案,但它是一个起点:

public static class RequestExtensions
{
    public static IDictionary<string, string> ParseFormUrlEncoded(this IHttpRequest request)
    {
        var data = new Dictionary<string, string>();

        foreach (var tuple in request.Payload.Split('='))
        {
            var parts = tuple.Split('&');
            var key = Uri.UnescapeDataString(parts[0]);
            var val = Uri.UnescapeDataString(parts[1]);
            if (!data.ContainsKey(key)) data.Add(key, val);
        }

        return data;
    }

    public static IDictionary<string, FormElement> ParseFormData(this IHttpRequest request)
    {
        var data = new Dictionary<string, FormElement>();
        var boundary = GetBoundary(request.Headers.Get("Content-Type"));

        if (boundary == null) return data;

        foreach (var part in request.Payload.Split(new[] { boundary }, StringSplitOptions.RemoveEmptyEntries))
        {
            var element = new FormElement(part);
            if (!data.ContainsKey(element.Name)) data.Add(element.Name, element);
        }

        return data;
    }

    private static string GetBoundary(string contenttype)
    {
        if (string.IsNullOrWhiteSpace(contenttype)) return null;

        return (from part in contenttype.Split(';', ',')
            select part.TrimStart().TrimEnd().Split('=')
            into parts
            where parts[0].Equals("boundary", StringComparison.CurrentCultureIgnoreCase)
            select parts[1]).FirstOrDefault();
    }
}

public class FormElement
{
    public string Name => _dispositionParams["name"];
    public string FileName => _dispositionParams["filename"];
    public Dictionary<string, string> Headers { get; private set; }
    public string Value { get; }

    private Dictionary<string, string> _dispositionParams;

    public FormElement(string data)
    {
        var parts = data.Split(new [] { "\r\n\r\n", "\n\n" }, StringSplitOptions.None);
        Value = parts[1];

        ParseHeaders(parts[0]);
        ParseParams(Headers["Content-Disposition"]);
    }

    private void ParseHeaders(string data)
    {
        Headers = data.TrimStart().TrimEnd().Split(new[] {"\r\n", "\n"}, StringSplitOptions.RemoveEmptyEntries).Select(header => header.Split(new[] {':'})).ToDictionary(parts => parts[0].TrimStart().TrimEnd(), parts => parts[1].TrimStart().TrimEnd());
    }

    private void ParseParams(string data)
    {
        _dispositionParams = new Dictionary<string, string>();

        foreach (var part in data.Split(new[] {';'}))
        {
            if (part.IndexOf("=") == -1) continue;
            var parts = part.Split(new[] {'='});
            _dispositionParams.Add(parts[0].TrimStart(' '), parts[1].TrimEnd('"').TrimStart('"'));
        }
    }
}
公共静态类请求扩展
{
公共静态IDictionary ParseFormUrlEncoded(此IHttpRequest请求)
{
var data=newdictionary();
foreach(request.Payload.Split('=')中的变量元组)
{
var parts=tuple.Split('&');
var key=Uri.UnescapeDataString(部分[0]);
var val=Uri.UnescapeDataString(第[1]部分);
如果(!data.ContainsKey(key))data.Add(key,val);
}
返回数据;
}
公共静态IDictionary ParseFormData(此IHttpRequest请求)
{
var data=newdictionary();
var boundary=GetBoundary(request.Headers.Get(“内容类型”);
if(boundary==null)返回数据;
foreach(request.Payload.Split中的var部分(新[]{boundary},StringSplitOptions.RemoveEmptyEntries))
{
var元素=新FormElement(部分);
如果(!data.ContainsKey(element.Name))data.Add(element.Name,element);
}
返回数据;
}
私有静态字符串GetBoundary(字符串contenttype)
{
if(string.IsNullOrWhiteSpace(contenttype))返回null;
返回(来自contenttype.Split(“;”,“,”中的部分)
选择part.TrimStart().trimsend().Split('='))
分成几部分
其中部分[0]。等于(“边界”,StringComparison.CurrentCultureIgnoreCase)
选择零件[1])。FirstOrDefault();
}
}
公共类FormElement
{
公共字符串名称=>_dispositionParams[“Name”];
公共字符串FileName=>_dispositionParams[“FileName”];
公共字典头{get;private set;}
公共字符串值{get;}
私有字典_dispositionParams;
公共FormElement(字符串数据)
{
var parts=data.Split(新[]{“\r\n\r\n”,“\n\n”},StringSplitOptions.None);
值=零件[1];
(部分[0]);
ParseParams(标题[“内容处置”]);
}
私有void解析头(字符串数据)
{
Headers=data.TrimStart().TrimEnd().Split(新[]{“\r\n”,“\n”},StringSplitOptions.RemoveEmptyEntries)。选择(header=>header.Split(新[]{':'})).ToDictionary(parts=>parts[0]。TrimStart().TrimEnd(),parts=>parts[1]。TrimStart().TrimEnd();
}
私有void ParseParams(字符串数据)
{
_dispositionParams=新字典();
foreach(data.Split中的var部分(新[]{';'}))
{
如果(part.IndexOf(“=”)==-1)继续;
var parts=part.Split(新[]{'='});
_dispositionParams.Add(部分[0]。TrimStart(“”),部分[1]。TrimEnd(“”).TrimStart(“”);
}
}
}

如果您正在寻找可以立即使用的异步内容,您可以尝试实现的答案,我还没有测试过。

如果您试图将文件作为二进制负载上载,请参阅GitHub上的


如果您试图从表单提交上传一个文件,这将有点棘手,因为还没有添加多部分有效负载解析器,但这仍然是可能的

以下代码示例完全未经测试,我只是在脑海中写下了这一点,因此它可能不是最佳解决方案,但它是一个起点:

public static class RequestExtensions
{
    public static IDictionary<string, string> ParseFormUrlEncoded(this IHttpRequest request)
    {
        var data = new Dictionary<string, string>();

        foreach (var tuple in request.Payload.Split('='))
        {
            var parts = tuple.Split('&');
            var key = Uri.UnescapeDataString(parts[0]);
            var val = Uri.UnescapeDataString(parts[1]);
            if (!data.ContainsKey(key)) data.Add(key, val);
        }

        return data;
    }

    public static IDictionary<string, FormElement> ParseFormData(this IHttpRequest request)
    {
        var data = new Dictionary<string, FormElement>();
        var boundary = GetBoundary(request.Headers.Get("Content-Type"));

        if (boundary == null) return data;

        foreach (var part in request.Payload.Split(new[] { boundary }, StringSplitOptions.RemoveEmptyEntries))
        {
            var element = new FormElement(part);
            if (!data.ContainsKey(element.Name)) data.Add(element.Name, element);
        }

        return data;
    }

    private static string GetBoundary(string contenttype)
    {
        if (string.IsNullOrWhiteSpace(contenttype)) return null;

        return (from part in contenttype.Split(';', ',')
            select part.TrimStart().TrimEnd().Split('=')
            into parts
            where parts[0].Equals("boundary", StringComparison.CurrentCultureIgnoreCase)
            select parts[1]).FirstOrDefault();
    }
}

public class FormElement
{
    public string Name => _dispositionParams["name"];
    public string FileName => _dispositionParams["filename"];
    public Dictionary<string, string> Headers { get; private set; }
    public string Value { get; }

    private Dictionary<string, string> _dispositionParams;

    public FormElement(string data)
    {
        var parts = data.Split(new [] { "\r\n\r\n", "\n\n" }, StringSplitOptions.None);
        Value = parts[1];

        ParseHeaders(parts[0]);
        ParseParams(Headers["Content-Disposition"]);
    }

    private void ParseHeaders(string data)
    {
        Headers = data.TrimStart().TrimEnd().Split(new[] {"\r\n", "\n"}, StringSplitOptions.RemoveEmptyEntries).Select(header => header.Split(new[] {':'})).ToDictionary(parts => parts[0].TrimStart().TrimEnd(), parts => parts[1].TrimStart().TrimEnd());
    }

    private void ParseParams(string data)
    {
        _dispositionParams = new Dictionary<string, string>();

        foreach (var part in data.Split(new[] {';'}))
        {
            if (part.IndexOf("=") == -1) continue;
            var parts = part.Split(new[] {'='});
            _dispositionParams.Add(parts[0].TrimStart(' '), parts[1].TrimEnd('"').TrimStart('"'));
        }
    }
}
公共静态类请求扩展
{
公共静态IDictionary ParseFormUrlEncoded(此IHttpRequest请求)
{
var data=newdictionary();
foreach(request.Payload.Split('=')中的变量元组)
{
var parts=tuple.Split('&');
var key=Uri.UnescapeDataString(部分[0]);
var val=Uri.UnescapeDataString(第[1]部分);
如果(!data.ContainsKey(key))data.Add(key,val);
}
返回数据;
}
公共静态IDictionary ParseFormData(此IHttpRequest请求)
{
var data=newdictionary();
var boundary=GetBoundary(request.Headers.Get(“内容类型”);
if(boundary==null)返回数据;
foreach(request.Payload.Split中的var部分(新[]{boundary},StringSplitOptions.RemoveEmptyEntries))
{
var元素=新FormElement(部分);
如果(!data.ContainsKey(element.Name))data.Add(element.Name,element);
}
返回数据;
}
私有静态字符串GetBoundary(字符串contenttype)
{
if(string.IsNullOrWhiteSpace(contenttype))返回null;
返回(来自contenttype.Split(“;”,“,”中的部分)
选择part.TrimStart().trimsend().Split('='))
分成几部分
其中部分[0]。等于(“边界”,StringComparison.CurrentCultureIgnoreCase)
选择零件[1])。FirstOrDefault();
}
}
公共类FormElement
{
公共字符串名称=>_dispositionParams[“Name”];
公共字符串FileName=>_dispositionParams[“FileName”];
公共字典头{get;private set;}
公共字符串值{get;}
私有字典_dispositionParams;
公共FormElement(字符串数据)
{
var parts=data.Split(新[]{“\r\n\r\n”,“\n\n”},StringSplitOptions.None);
值=零件[1];
(部分[0]);
ParseParams(标题[“内容处置”]);
}
私有空解析头(