Reputation: 7864
I'm handling uploads in .NET Core, which are passed in as IFormFile
. I need to manipulate the stream to remove Exif data before I ultimately pass the file to be saved. I don't know how to handle this, however. I'm trying the code below, but it doesn't work because stream
is readonly inside a using
statement.
What is the correct way to do something like this?
public async Task<IActionResult> UploadImage(IFormFile image)
{
using (var stream = new MemoryStream())
{
// image is IFormFile
await image.CopyToAsync(stream);
// doesn't work, stream is readonly
stream = StripExif(stream);
// save stream
}
return Ok();
}
public static Stream StripExif(Stream stream)
{
stream.Seek(0, SeekOrigin.Begin);
// remove Exif data
return stream;
}
Upvotes: 2
Views: 900
Reputation: 2252
The using is only having a problem because you are trying to assign to the using variable. You could create a new MemoryStream
in StripExif
, and then assign the result of StripExif
to a new stream variable.
public async Task<IActionResult> UploadImage(IFormFile image)
{
using (var stream = new MemoryStream())
{
// image is IFormFile
await image.CopyToAsync(stream);
var strippedStream = StripExif(stream);
// save strippedStream, not stream.
}
return Ok();
}
public static MemoryStream StripExif(MemoryStream stream)
{
var result = new MemoryStream();
stream.Seek(0, SeekOrigin.Begin);
// remove Exif data from result
return result;
}
Updated :
public async Task<IActionResult> UploadImage(IFormFile image)
{
using (var stream = new MemoryStream())
using (var writer = new StreamWriter(new MemoryStream())
{
// image is IFormFile
await image.CopyToAsync(stream);
var strippedStream = StripExif(stream, writer);
// save strippedStream, not stream.
}
return Ok();
}
public static void StripExif(MemoryStream stream, StreamWriter writer)
{
// lets assume for sake of example that removing ExIf just removes the
// the first 10 characters of the stream
stream.Seek(10, SeekOrigin.Begin);
writer.Write(stream.ReadToEnd());
}
Upvotes: 2
Reputation: 203828
StripExif
is not actually creating a new Stream
, rather, it's mutating the Stream
passed to it, so it shouldn't be returning a Stream
at all. When the caller then modifies the call to reflect that it mutates the parameter, rather than creating a new stream, the problem goes away:
public async Task<IActionResult> UploadImage(IFormFile image)
{
using (var stream = new MemoryStream())
{
// image is IFormFile
await image.CopyToAsync(stream);
StripExif(stream);
// save stream
}
return Ok();
}
public static void StripExif(Stream stream)
{
stream.Seek(0, SeekOrigin.Begin);
// remove Exif data
}
Upvotes: 2