Converting a file into stream - c#

I have a path which has a list of files.
foreach (var file in Directory.GetFiles(networkpath))
{
Stream s=file.
}
I want to convert the file into Stream.How to proceed further?

Is this what you need?
foreach (var file in Directory.GetFiles(networkpath))
{
using (FileStream fs = File.Open(file, FileMode.Open))
{
}
}

You can safely read file using FileStream in C#. To be sure the whole file is correctly read, you should call FileStream.Read method in a loop, even if in the most cases the whole file is read in a single call of FileStream.Read method.
First create FileStream to open a file for reading. Then call FileStream.Read in a loop until the whole file is read. Finally close the stream.
using System.IO;
public static byte[] ReadFile(string filePath)
{
byte[] buffer;
FileStream fileStream = new FileStream(filePath, FileMode.Open, FileAccess.Read);
try
{
int length = (int)fileStream.Length; // get file length
buffer = new byte[length]; // create buffer
int count; // actual number of bytes read
int sum = 0; // total number of bytes read
// read until Read method returns 0 (end of the stream has been reached)
while ((count = fileStream.Read(buffer, sum, length - sum)) > 0)
sum += count; // sum is a buffer offset for next reading
}
finally
{
fileStream.Close();
}
return buffer;
}

Change your file path to suit your code!Add this inside your loop!
FileStream fStream = new FileStream(#"c:\file.txt", FileMode.Open);
try
{
// read from file or write to file
}
finally
{
fStream.Close();
}

Related

How To Monitor Download Progress of Stream

From SharePoint, I get a "Stream" for a file. I want to copy this entire file from the internet to a local file on the PC, but I want to have status while this download is occurring. How? FileStream and StreamReader seem to have bytes vs char differences when not doing a full "CopyTo" which doesn't have progress updates. There has to be a cleaner way...
using (var sr = new StreamReader(fileData.Value))
{
using (FileStream fs = new FileStream(localFile + "_tmp", FileMode.Create))
{
byte[] block = new byte[1024];
// only guessing something like this is necessary...
int count = (int)Math.Min(sr.BaseStream.Length - sr.BaseStream.Position, block.Length);
while (sr.BaseStream.Position < sr.BaseStream.Length)
{
// read requires char[]
sr.Read(block, 0, count);
// write requires byte[]
fs.Write(block, 0, count);
Log("Percent complete: " + (sr.BaseStream.Position / sr.BaseStream.Length));
count = (int)Math.Min(sr.BaseStream.Length - sr.BaseStream.Position, block.Length);
}
}
}
Just had to use BinaryReader instead of StreamReader. Easy Peasy.

Corrupted file while compressing stream using dotnetzip library

The file is created and the size seems to be ok, but when I double click it is says its format is wrong or the file is damaged.
This is the code I'm using
public MemoryStream CompressFiles(Dictionary<string, MemoryStream> filesToBeCompressed)
{
var output = new MemoryStream();
using (var zip = new ZipFile())
{
foreach (var entry in filesToBeCompressed)
{
entry.Value.Seek(0, SeekOrigin.Begin); // <-- must do this after writing the stream (I've read this in a blog
zip.AddEntry(entry.Key.Substring(entry.Key.LastIndexOf('/') + 1, entry.Key.Length - entry.Key.LastIndexOf('/') - 1), entry.Value);
zip.Save(output);
}
}
return output;
}
Then in the calling method
SaveStreamToFile(documentCompressedName,getDocument());
getDocument() calls Compress internally
And that method finally
private static void SaveStreamToFile(string fileFullPath, Stream stream)
{
if (stream.Length == 0) return;
// Create a FileStream object to write a stream to a file
using (FileStream fileStream = System.IO.File.Create(fileFullPath, (int)stream.Length))
{
// Fill the bytes[] array with the stream data
var bytesInStream = new byte[stream.Length];
stream.Read(bytesInStream, 0, (int)bytesInStream.Length);
// Use FileStream object to write to the specified file
fileStream.Write(bytesInStream, 0, bytesInStream.Length);
}
}
Any ideas?
Thanks in advance! Guillermo.
I think the problem is in your function SaveStreamToFile. You have to set the position of the stream to the beginning before you write the archive to disk:
private static void SaveStreamToFile(string fileFullPath, Stream stream)
{
if (stream.Length == 0) return;
// Set the position within the stream to the beginning of the stream
stream.Seek(0, SeekOrigin.Begin);
// Create a FileStream object to write a stream to a file
using (FileStream fileStream = System.IO.File.Create(fileFullPath, (int)stream.Length))
{
// Fill the bytes[] array with the stream data
var bytesInStream = new byte[stream.Length];
stream.Read(bytesInStream, 0, (int)bytesInStream.Length);
// Use FileStream object to write to the specified file
fileStream.Write(bytesInStream, 0, bytesInStream.Length);
}
}
Hope, this helps.
From your code snippets, my guess here is that the MemoryStream's Position is at the end of the stream when you pass it to SaveStreamToFile, and as you never set the position back to the start of the stream, your stream.Read is actually reading no bytes at all. If you open your output zip file with a hex editor, you'll probably see that it's full of zeros.
You have a number of options here, but my suggestion would be to try:
private static void SaveStreamToFile(string fileFullPath, Stream stream)
{
if (stream.Length == 0) return;
// Create a FileStream object to write a stream to a file
using (FileStream fileStream = System.IO.File.Create(fileFullPath, (int)stream.Length))
{
// Use FileStream object to write to the specified file
fileStream.Write(stream.GetBuffer(), 0, stream.Length);
}
}
This approach avoids taking a copy of the internal memory buffer of the MemoryStream. Whilst I don't know how large your zip files are so it may not be an issue in terms of memory use, but storing the zip file in memory twice - once in the MemoryStream, and again in your original bytesInStream array seems unnecessary.

Create new FileStream out of a byte array

I am attempting to create a new FileStream object from a byte array. I'm sure that made no sense at all so I will try to explain in further detail below.
Tasks I am completing:
1) Reading the source file which was previously compressed
2) Decompressing the data using GZipStream
3) copying the decompressed data into a byte array.
What I would like to change:
1) I would like to be able to use File.ReadAllBytes to read the decompressed data.
2) I would then like to create a new filestream object usingg this byte array.
In short, I want to do this entire operating using byte arrays. One of the parameters for GZipStream is a stream of some sort, so I figured I was stuck using a filestream. But, if some method exists where I can create a new instance of a FileStream from a byte array - then I should be fine.
Here is what I have so far:
FolderBrowserDialog fbd = new FolderBrowserDialog(); // Shows a browser dialog
fbd.ShowDialog();
// Path to directory of files to compress and decompress.
string dirpath = fbd.SelectedPath;
DirectoryInfo di = new DirectoryInfo(dirpath);
foreach (FileInfo fi in di.GetFiles())
{
zip.Program.Decompress(fi);
}
// Get the stream of the source file.
using (FileStream inFile = fi.OpenRead())
{
//Create the decompressed file.
string outfile = #"C:\Decompressed.exe";
{
using (GZipStream Decompress = new GZipStream(inFile,
CompressionMode.Decompress))
{
byte[] b = new byte[blen.Length];
Decompress.Read(b,0,b.Length);
File.WriteAllBytes(outfile, b);
}
}
}
Thanks for any help!
Regards,
Evan
It sounds like you need to use a MemoryStream.
Since you don't know how many bytes you'll be reading from the GZipStream, you can't really allocate an array for it. You need to read it all into a byte array and then use a MemoryStream to decompress.
const int BufferSize = 65536;
byte[] compressedBytes = File.ReadAllBytes("compressedFilename");
// create memory stream
using (var mstrm = new MemoryStream(compressedBytes))
{
using(var inStream = new GzipStream(mstrm, CompressionMode.Decompress))
{
using (var outStream = File.Create("outputfilename"))
{
var buffer = new byte[BufferSize];
int bytesRead;
while ((bytesRead = inStream.Read(buffer, 0, BufferSize)) != 0)
{
outStream.Write(buffer, 0, bytesRead);
}
}
}
}
Here is what I ended up doing. I realize that I did not give sufficient information in my question - and I apologize for that - but I do know the size of the file I need to decompress as I am using it earlier in my program. This buffer is referred to as "blen".
string fi = #"C:\Path To Compressed File";
// Get the stream of the source file.
// using (FileStream inFile = fi.OpenRead())
using (MemoryStream infile1 = new MemoryStream(File.ReadAllBytes(fi)))
{
//Create the decompressed file.
string outfile = #"C:\Decompressed.exe";
{
using (GZipStream Decompress = new GZipStream(infile1,
CompressionMode.Decompress))
{
byte[] b = new byte[blen.Length];
Decompress.Read(b,0,b.Length);
File.WriteAllBytes(outfile, b);
}
}
}

How to write contents of one file to another file?

I need to write contents of a file to another file using File.OpenRead and File.OpenWrite methods. I am unable to figure out how to do it.
How can i modify the following code to work for me.
using (FileStream stream = File.OpenRead("C:\\file1.txt"))
using (FileStream writeStream = File.OpenWrite("D:\\file2.txt"))
{
BinaryReader reader = new BinaryReader(stream);
BinaryWriter writer = new BinaryWriter(writeStream);
writer.Write(reader.ReadBytes(stream.Length));
}
using (FileStream stream = File.OpenRead("C:\\file1.txt"))
using (FileStream writeStream = File.OpenWrite("D:\\file2.txt"))
{
BinaryReader reader = new BinaryReader(stream);
BinaryWriter writer = new BinaryWriter(writeStream);
// create a buffer to hold the bytes
byte[] buffer = new Byte[1024];
int bytesRead;
// while the read method returns bytes
// keep writing them to the output stream
while ((bytesRead =
stream.Read(buffer, 0, 1024)) > 0)
{
writeStream.Write(buffer, 0, bytesRead);
}
}
Just wonder why not to use this:
File.Copy("C:\\file1.txt", "D:\\file2.txt");
You should be using File.Copy unless you want to append to the second file.
If you want to append you can still use the File class.
string content = File.ReadAllText("C:\\file1.txt");
File.AppendAllText("D:\\file2.txt",content);
This works for file with small size as entire file in loaded into the memory.
Try something along these lines:
using (FileStream input = File.OpenRead(pathToInputFile),
output = File.OpenWrite(pathToOutputFile))
{
int read = -1;
byte[] buffer = new byte[4096];
while (read != 0)
{
read = input.Read(buffer, 0, buffer.Length);
output.Write(buffer, 0, read);
}
}
Note that this is somewhat 'skeletal' and you should amend as required for your application of it.
Is it necessary to us FileStream? Because you can do this very easily with simple File Class like;
using System.IO;
string FileContent = File.ReadAllText(FilePathWhoseTextYouWantToCopy);
File.WriteAllText(FilePathToWhomYouWantToPasteTheText,FileContent);
using (var inputStream = File.OpenRead(#"C:\file1.txt"))
{
using (var outputStream = File.OpenWrite(#"D:\file2.txt"))
{
int bufferLength = 128;
byte[] buffer = new byte[bufferLength];
int bytesRead = 0;
do
{
bytesRead = inputStream.Read(buffer, 0, bufferLength);
outputStream.Write(buffer, 0, bytesRead);
}
while (bytesRead != 0);
}
}
Use FileStream class, from System.IO.
[ComVisibleAttribute(true)]
public class FileStream : Stream
Have you checked that the reader is reading all the data? This MSDN page has an example that checks all the data is read:
byte[] verifyArray = binReader.ReadBytes(arrayLength);
if(verifyArray.Length != arrayLength)
{
Console.WriteLine("Error reading the data.");
return;
}
The other alternative is that you probably need to Flush the output buffer:
writer.Flush();
If you are not keen at using Read/Write function of File , you can better try using Copy functionality
Easiest will be :
File.Copy(source_file_name, destination_file_name, true)
true--> for overwriting existing file,without "true" it will create a new file.But if the file already exists it will throw exception without "true" argument.

GZipStream not reading the whole file

I have some code that downloads gzipped files, and decompresses them. The problem is, I can't get it to decompress the whole file, it only reads the first 4096 bytes and then about 500 more.
Byte[] buffer = new Byte[4096];
int count = 0;
FileStream fileInput = new FileStream("input.gzip", FileMode.Open, FileAccess.Read, FileShare.Read);
FileStream fileOutput = new FileStream("output.dat", FileMode.Create, FileAccess.Write, FileShare.None);
GZipStream gzipStream = new GZipStream(fileInput, CompressionMode.Decompress, true);
// Read from gzip steam
while ((count = gzipStream.Read(buffer, 0, buffer.Length)) > 0)
{
// Write to output file
fileOutput.Write(buffer, 0, count);
}
// Close the streams
...
I've checked the downloaded file; it's 13MB when compressed, and contains one XML file. I've manually decompressed the XML file, and the content is all there. But when I do it with this code, it only outputs the very beginning of the XML file.
Anyone have any ideas why this might be happening?
EDIT
Try not leaving the GZipStream open:
GZipStream gzipStream = new GZipStream(fileInput, CompressionMode.Decompress,
false);
or
GZipStream gzipStream = new GZipStream(fileInput, CompressionMode.Decompress);
I ended up using a gzip executable to do the decompression instead of a GZipStream. It can't handle the file for some reason, but the executable can.
Same thing happened to me. In my case only reads up to 6 lines and then reached end of file. So I realized that although the extension is gz, it was compressed by another algorithm not supported by GZipStream. So I used SevenZipSharp library and it worked. This is my code
You can use SevenZipSharp library
using (var input = File.OpenRead(lstFiles[0]))
{
using (var ds = new SevenZipExtractor(input))
{
//ds.ExtractionFinished += DsOnExtractionFinished;
var mem = new MemoryStream();
ds.ExtractFile(0, mem);
using (var sr = new StreamReader(mem))
{
var iCount = 0;
String line;
mem.Position = 0;
while ((line = sr.ReadLine()) != null && iCount < 100)
{
iCount++;
LstOutput.Items.Add(line);
}
}
}
}
Are you calling Close or Flush on fileOutput? (Or just wrap it in a using, which is recommended practice.) If you don't the file might not be flushed to disk when your program ends.

Categories

Resources