[英]StreamReader.ReadLine() doesn't consume the stream
I am starting a new web application project where a user can upload a .csv
file so that I can process the file. 我正在启动一个新的Web应用程序项目,用户可以在其中上传
.csv
文件,以便我可以处理该文件。
Currently I am able to let the user upload the file but when I try to use the StreamReader
to read from the stream that generated from the file, it seems that the StreamReader
cannot read from the stream properly. 当前,我可以让用户上传文件,但是当我尝试使用
StreamReader
读取从文件生成的流时,似乎StreamReader
无法正确读取该流。
By the way, for the upload file part I followed the Microsoft tutorial here 顺便说一句,在上传文件部分,我跟着微软教程这里
Here is the code for the View. 这是视图的代码。
<form method="post" enctype="multipart/form-data" asp-controller="Upload" asp-action="Upload">
<div class="form-group">
<div class="col-md-10">
<p>Upload one or more files using this form:</p>
<input type="file" name="files" >
</div>
</div>
<div class="form-group">
<div class="col-md-10">
<input type="submit" value="Upload" />
</div>
</div>
Here is my code for the Controller 这是我的控制器代码
The len, len2 and p are variables for debugging purposes. len,len2和p是用于调试目的的变量。
[HttpPost]
public async Task<IActionResult> Upload(IFormFile file)
{
if (file != null && file.Length > 0)
{
var filePath = Path.GetTempFileName(); //Note: May throw excepetion when temporary file exceeds 65535 per server
var stream = new FileStream(filePath, FileMode.Create);
await file.CopyToAsync(stream);//
long len = stream.Length;// 412 bytes
StreamReader reader = new StreamReader(stream);//*
int p = reader.Peek();//currently the next character is EoF
var val = reader.ReadLine();
long len2 = stream.Length;// 412 bytes
bool end = reader.EndOfStream;// true
//do some stuff here
return RedirectToAction("Success");
}
else
{
return RedirectToAction("Upload_fail");//file not found
}
}
Any advice or help will be appreciated. 任何建议或帮助将不胜感激。
When reading from a Stream, the current position is updated accordingly. 从Stream读取时,当前位置会相应更新。 As an example, imagine the following steps:
例如,设想以下步骤:
If there were only two bytes in the stream, the position is now considered to be EOF - It is no longer possible to read additional bytes, as they've already been read. 如果流中只有两个字节,则该位置现在被认为是EOF-无法再读取其他字节,因为已经读取了它们。
Relating this to your example, the call to await file.CopyToAsync(stream)
advances the stream's position to EOF. 与您的示例相关,调用
await file.CopyToAsync(stream)
将流的位置前进到EOF。 As such, when you wrap a StreamReader
around it, there's nothing left to read. 这样,当您将
StreamReader
包裹起来时,就没什么可读取的了。 The process is the same for writing - The CopyToAsync
operation is advancing both the input and the output streams, resulting in both streams sitting at EOF once the operation completes. 写入的过程相同
CopyToAsync
操作同时推进输入流和输出流,一旦操作完成,两个流都位于EOF处。
To complicate things a little, Streams can be forward-only, meaning that it is not possible to go backwards once data has been read. 为了使事情复杂一点,Streams只能是前向的,这意味着一旦读取数据就不可能向后移动。 As you are working with a
FileStream
, I think you are able to go back to the beginning, like so: 在使用
FileStream
,我认为您可以回到开始,就像这样:
await file.CopyToAsync(stream);
stream.Position = 0;
You could also use stream.Seek(0, SeekOrigin.Begin)
, as mentioned in this answer: Stream.Seek(0, SeekOrigin.Begin) or Position = 0 您还可以使用
stream.Seek(0, SeekOrigin.Begin)
,如此答案中所述: Stream.Seek(0,SeekOrigin.Begin)或Position = 0
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.