web api 如何通过接收文件流的方式,接收客户端及前端上传的文件
服务端接收文件流代码:
public async Task<HttpResponseMessage> ReceiveFileByStream()
{
var stream = HttpContext.Current.Request.InputStream;
if (stream.Length > )
{
var absolutePath = HttpContext.Current.Request.MapPath("/img/");
if (!Directory.Exists(absolutePath))
{
Directory.CreateDirectory(absolutePath);
}
var fileType = "";
var bytes = new byte[stream.Length];
stream.Read(bytes, , bytes.Length);
//前两个字节代表文件类型,这里以 JPG 类型为例
var bs = bytes[].ToString() + bytes[].ToString();
if (bs.Equals(""))
{
fileType = ".jpg";
}
var path = absolutePath + Guid.NewGuid() + fileType;
await Task.Run(() =>
{
using (FileStream fs = new FileStream(path, FileMode.Create, FileAccess.Write))
{
fs.Write(bytes, , bytes.Length);
}
});
return Request.CreateResponse(HttpStatusCode.OK, "上传成功!");
}
else
{
return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "没有文件耶,哥们!");
}
}
客户端上传文件流代码:
HttpClient
static string TestHttpClientUpload()
{
var resultStr = string.Empty;
HttpClient client = new HttpClient();
client.BaseAddress = new Uri("http://192.168.20.15:57895");
string apiUrl = "api/upload/ReceiveFileByStream";
string path = @"C:\Users\xxxx\Desktop\woman.jpg";
FileStream fs = new FileStream(path, FileMode.Open, FileAccess.Read);
HttpContent content = new StreamContent(fs);
var result = client.PostAsync(apiUrl, content).Result;
fs.Dispose();
resultStr = result.Content.ReadAsStringAsync().Result;
return resultStr;//上传成功
}
HttpWebRequest
static string TestHttpWebRequestUpload()
{
var resultStr = string.Empty;
string url = "http://192.168.20.15:57895/api/upload/ReceiveFileByStream";
HttpWebRequest request = WebRequest.CreateHttp(url);
request.Method = "post"; string path = @"C:\Users\xxxx\Desktop\woman.jpg";
FileStream fs = new FileStream(path, FileMode.Open, FileAccess.Read);
var requestStream = request.GetRequestStream();
fs.CopyTo(requestStream);
fs.Dispose();
requestStream.Dispose(); var result = request.GetResponseAsync().Result;
var responseStream = result.GetResponseStream();
using (StreamReader sm = new StreamReader(responseStream))
{
resultStr = sm.ReadToEnd();
}
return resultStr;//上传成功
}
前端上传文件:
<div>
<span>Form表单上传单个文件</span><br />
<form id="myForm1" enctype="multipart/form-data" method="post" action="http://192.168.20.15:57895/api/upload/ReceiveFileByStream">
<input type="file" name="myFile" />
<input type="submit" value="submit提交" />
</form>
</div>
上面三种方式,客户端没有问题,但是前端这样上传是有问题的,因为在文件流开头还有其他东西:
用一段代码测试:
//这里的 255 是 255216 里面的 255, 从 255 所在的位置开始才是文件的字节数据
var index = bytes.ToList().IndexOf();
var str = Encoding.UTF8.GetString(bytes, , index);
Trace.WriteLine(str);

这就是HTTP请求自带的,打开浏览器,F12,可以看到:

那么,如何成功的躲避这一段字节呢?
答案是 : 利用 Ajax 提交表单
<div>
<form id="myForm4">
<input type="file" id="myFile" />
<input type="button" value="AJAX提交图片" onclick="uploadFile()" />
</form>
</div>
function uploadFile() {
var url = "http://192.168.20.15:57895/api/upload/ReceiveFileByStream";
var data = $("#myFile")[0].files[0];
$.ajax({
url: url,
data: data,
type: "post",
processData: false,//表示提交的时候不会序列化 data,而是直接使用 data,默认为 true
contentType: false,//表示不要去设置Content-Type请求头
cache: false,//设置为 false 将不会从浏览器缓存中加载请求信息。
success: function () { }
});
}
但是,这样提交在跨域的时候,会有一次 OPTIONS 请求

下面那次请求才是 POST 请求,至于为什么会有一次 OPTIONS 请求,大家可以自行百度,这里就不说了.
那么如何成功的避免这次 OPTIONS 请求呢?
答案就是 : Ajax 请求的时候, 不设置 contentType 属性!
function uploadFile() {
var url = "http://192.168.20.15:57895/api/upload/ReceiveFileByStream";
var data = $("#myFile")[0].files[0];
$.ajax({
url: url,
data: data,
type: "post",
processData: false,//表示提交的时候不会序列化 data,而是直接使用 data,默认为 true
cache: false,//设置为 false 将不会从浏览器缓存中加载请求信息。
success: function () { }
});
}
收工!
web api 如何通过接收文件流的方式,接收客户端及前端上传的文件的更多相关文章
- java客户端调用ftp上传下载文件
1:java客户端上传,下载文件. package com.li.utils; import java.io.File; import java.io.FileInputStream; import ...
- C# FormData 文件太大报错404 Form表单上传大文件,无法进入后台Action,页面提示404.
web.config中添加如下节点 <system.webServer> <security> <requestFiltering > &l ...
- File API 读取上传的文件
1, 在html 文档中,<input type="file"> 我们可以选择文件进行上传,但这时只能上传一个文件.如果加上multiple 属性,可以上传多个文件,上 ...
- 用百度webuploader分片上传大文件
一般在做文件上传的时候,都是通过客户端把要上传的文件上传到服务器,此时上传的文件都在服务器内存,如果上传的是视频等大文件,那么服务器内存就很紧张,而且一般我们都是用flash或者html5做异步上传, ...
- extjs实现简单的多文件上传(不借助任何插件),以及包含处理上传大文件的错误的各种处理办法
在extjs的学习过程中,有遇到过有关多文件上传的问题,但是网上的大多数都是专门的去实现多文件上传而去做的组件之类的,没有特别简单的方式,于是小白便做了下面的内容,只是通过动态的去添加extjs的自带 ...
- ASP.NET 使用 plupload 上传大文件时出现“blob”文件的Bug
最近在一个ASP.NET 项目中使用了plupload来上传文件,结果几天后客户发邮件说上传的文件不对,说是文件无法打开 在进入系统进行查看后发现上传的文件竟然没有后缀,经过一番测试发现如果文件上传的 ...
- 自实现input上传指定文件到服务器
遇到问题,解决问题,记录问题,成长就是一步一步走出来的. 一.添加 input 标签 我的工作中遇到了,需要上传pdf文件到服务器的需求,而且只能上传pdf文件,accept指定了 pdf 类型. & ...
- 用java 代码下载Samba服务器上的文件到本地目录以及上传本地文件到Samba服务器
引入: 在我们昨天架设好了Samba服务器上并且创建了一个 Samba 账户后,我们就迫不及待的想用JAVA去操作Samba服务器了,我们找到了一个框架叫 jcifs,可以高效的完成我们工作. 实践: ...
- QQ上传大文件为什么这么快
今天和同事在群里讨论“QQ上传大文件/QQ群发送大文件时,可以在极短的时间内完成”是如何做到的. 有时候我们通过QQ上传一个几百M的文件,竟然只用了几秒钟,从带宽上限制可以得出,实际上传文件是不可能的 ...
随机推荐
- react ( 二 )
ref属性 当我们在 react组件中要访问真实的DOM元素时,你可能需要用到ref属性,ref接收一个函数作为属性值,函数接收一个参数,这个参数就是真实的DOM元素.真实的DOM元素渲染到页面上之后 ...
- js常见算法(一)
1.每个单词手字母大写 var capitalizeEveryWord = str => str.replace(/\b[a-z]/g, char => char.toUpperCase( ...
- python写一个信息收集四大件的脚本
0x0前言: 带来一首小歌: 之前看了小迪老师讲的课,仔细做了些笔记 然后打算将其写成一个脚本. 0x01准备: requests模块 socket模块 optparser模块 time模块 0x02 ...
- 在windows8.1下安装ubuntu16.04
(一)首先来简要了解一些linux的概念! 1.发行版本和内核版本的区别与联系:linux发行版本是"内核版本+一系列挂载软件"的集合体,光是一个内核版本是无法当做操作系统运行的. ...
- MongoDB系列一(查询).
一.简述 MongoDB中使用find来进行查询.查询就是返回一个集合中文档的子集,子集合的范围从0个文档到整个集合.默认情况下,"_id"这个键总是被返回,即便是没有指定要返回这 ...
- bzoj3142 luogu3228 HNOI2013 数列
这题好没意思啊,怀疑拉不开区分度. 题意:求一个递增序列,每两个相邻数字之间的差值不超过m,最后一个值不能大于n. 分析:网上好多人用了差分,我没想到.然后YY了一发生成函数. 考虑构造生成函数G(x ...
- 元素化设计原理及规则v1.0
一.元素设计架构 元素设计架构展示在基于元素化设计的思想下,系统各元素之间如何相互协作,并完成整个系统搭建. 架构中以Entity(数据)为中心,由Entity产生数据库表结构,并且Entity作为业 ...
- Tomcat5.5.9+JSP经典配置实例
一.开发环境配置 第一步:下载j2sdk和tomcat:到sun官方站(http://java.sun.com/j2se/1.5.0/download.jsp)下载j2sdk,注意下载版本为Windo ...
- Python基础-week02
本节内容摘要:http://www.cnblogs.com/Jame-mei 0.xmind8破解及安装(想要破解版及资料请下方留言,这里不做具体说明) 1.模块初识 2.pyc是什么? 3.pyth ...
- Centos网口流量实时监控
iptraf方式 [root@kazihuo ~]# yum -y install iptraf [root@kazihuo ~]# iptraf-ng-ng 开启服务日志: 进入细节监控后提示日志路 ...