The attachment is found, but the file is not being saved. While debugging, it seems to be successfully saving, but the file is not in the test path.
private void button1_Click(object sender, RibbonControlEventArgs e)
{
Outlook.Inspector currInspector = null;
Outlook.MailItem mail = null;
Outlook.Attachments attachments = null;
//change to production paths when working, below are test paths
string path = #"H:\Customer Service";
string archivePath = #"H:\Customer Service\Helpers";
try
{
currInspector = Globals.ThisAddIn.Application.ActiveWindow();
mail = (Outlook.MailItem)currInspector.CurrentItem;
attachments = mail.Attachments;
for (int i = 1; i <= attachments.Count; i++)
{
Outlook.Attachment vendFile = attachments[i];
//save original in archive folder
vendFile.SaveAsFile(archivePath + vendFile);
//begin document modification and save to path
//StreamWriter streamWriter = new StreamWriter(new FileStream(path, FileMode.Create, FileAccess.ReadWrite));
//dispose of object
Marshal.ReleaseComObject(vendFile);
}
}
catch
{
MessageBox.Show("Unable to retrieve attachment");
}
finally
{
if (attachments != null) Marshal.ReleaseComObject(attachments);
if (mail != null) Marshal.ReleaseComObject(mail);
if (currInspector != null) Marshal.ReleaseComObject(currInspector);
}
}
}
You need to specify the fully qualified path and file name for the SaveAsFile method, not just a folder path:
string filename = Path.Combine(archivePath , vendFile.FileName);
vendFile.SaveAsFile(filename);
Related
public void button1_Click(object sender, EventArgs e)
{
//string item = ofd.FileName;
ofd.InitialDirectory = "c:\\";
ofd.Filter = "exe files (*.exe)|*.exe";
ofd.Multiselect = true;
ofd.RestoreDirectory = true;
if (ofd.ShowDialog() == DialogResult.OK)
{
listBox1.Items.Clear();
string tmp = Path.Combine(Path.GetDirectoryName(listBox2.GetItemText(listBox2.Items)), "\\inputdata.txt");
File.Create(tmp);
using (File.Open(tmp, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite))
{
;
foreach (string item in ofd.FileNames)
{
string date = Path.GetFileName(item.Substring(10, 16));
string ite = item.Substring(0, item.IndexOf(".h2"));
listBox1.Items.Add(item);
if (File.ReadAllText(tmp).Contains(Path.GetFileName(item).Substring(10, 16)))
{
File.AppendAllText(tmp, Environment.NewLine);
}
if (item.IndexOf("MOD10A") >= 0)
{
if (File.ReadAllText(tmp).IndexOf(date) < 0)
{
File.AppendAllText(tmp, ite.Replace("MOD10A1.A", "ter_"));
}
}//
if (item.IndexOf("MYD10A") >= 0)
{
if (File.ReadAllText(tmp).IndexOf(date) < 0)
{
File.AppendAllText(tmp, ite.Replace("MYD10A1.A", "Aqu_"));
}
}
File.AppendAllText(tmp, ", " + item);
}
}
}
}
listbox2 has filename which i get from openfiledialog. like C:\Program Files (x86)\Microsoft\file.exe
when i debug this program. error happens. message is that The process cannot access the "c:\inputdata.txt" because it is being used by another process.
I don't understand why inputdata.txt is located in c:\ and why error is happening.
What is the reason for this error?
You must close the FileStream after use it.
Look at this :
Closing a file after File.Create
https://msdn.microsoft.com/en-us/library/aa328800(v=vs.71).aspx
First read the text file then after update the file.
using (File.Open(tmp, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite))
{
/// Not right here a append txt logic
}
// Code File.AppendAllText
Then after right here appned or update logic here.bcz, If file is already open you can't write or update the file.
I met one problem when I tried to copy file.
Error description
I worked with DataGridView and PictureBox.
Deguber of VS 2015 stopped me at
FileStream fs = File.Open(file, FileMode.Open);
in function CopyFile. I cant understand what's wrong i did.
This is some code (C#, .NET 4.5.1) from main form:
static string CopyFile(string file, string to)
{
FileInfo fileInfo = new FileInfo(file);
byte tmp = 0;
string temp = to + "\\" + fileInfo.Name;
FileStream newFile = File.Open(temp, FileMode.Create);
try
{
FileStream fs = File.Open(file, FileMode.Open);
for (int i = 0; i < fileInfo.Length; i++)
{
tmp = (byte)fs.ReadByte();
newFile.WriteByte(tmp);
}
fs.Close();
}
catch (FileNotFoundException ex)
{
MessageBox.Show("Не вдалося найти файл.");
}
newFile.Close();
return temp;
}
private void WriteNewUserToFile(User item, string pathToFile)
{
StreamWriter sw = new StreamWriter(File.Open(#pathToFile, FileMode.Append, FileAccess.Write));
sw.WriteLine(string.Format("{0}, {1}, {2}, {3}, {4}, {5}",
item.Id,
item.Image,
item.FirstName,
item.LastName,
item.Email,
item.Phone));
sw.Close();
}
private void btnAddUser_Click(object sender, EventArgs e)
{
AddUserForm dlg = new AddUserForm();
if (dlg.ShowDialog() == DialogResult.OK)
{
User item = dlg.NewUser;
item.Image = CopyFile(item.Image, "images");
WriteNewUserToFile(item, "data/users.dat");
users.Add(item);
//this.AddNewDataGridRow(item);
}
}
And some code of AddNewUserForm:
public User NewUser
{
get { return newUser; }
set { newUser = value; }
}
private void btnImage_Click(object sender, EventArgs e)
{
OpenFileDialog dlg = new OpenFileDialog();
if (dlg.ShowDialog() == DialogResult.OK)
{
txtImage.Text = dlg.FileName;
try
{
picboxImage.Image = Image.FromFile(txtImage.Text);
}
catch
{
picboxImage.Image = Image.FromFile(#"images\NoImg.bmp");
}
}
}
private void btnApply_Click(object sender, EventArgs e)
{
NewUser = new User
{
Id = Convert.ToInt32(txtId.Text),
LastName = txtLastName.Text,
FirstName = txtFirstName.Text,
Email = txtEmail.Text,
Phone = txtPhone.Text,
Image = txtImage.Text
};
this.DialogResult = DialogResult.OK;
}
If somebody need all project/code, click here (download VS project).
When you set the Image for the PictureBox using the following code, the call keeps the file handle open. So when you try to open the file again you encounter the exception.
picboxImage.Image = Image.FromFile(txtImage.Text);
According to this accepted answer, when the file handle is closed is unpredictable, in some cases, the handle won't be closed even if you explicitly close the Image.
So you may use the technique in that answer like this, to ensure the file handle is closed properly.
picboxImage.Image = Image.FromStream(new MemoryStream(File.ReadAllBytes(txtImage.Text)));
This question already has an answer here:
System.IO.IOException: 'The process cannot access the file because it is being used by another process
(1 answer)
Closed 2 years ago.
I would like use C# to upload multiple files to google drive
this is my upload button function
private void bt_upload_Click(object sender, EventArgs e)
{
Filedialog_init();
DialogResult check_upload = MessageBox.Show("Want to upload these files ?", "Upload", MessageBoxButtons.OKCancel);
if (check_upload == DialogResult.OK)
{
for (int i = 0; i < result.Count; i++)
{
UploadFilesDrive(service, result[i], filePath[i], Datatype[i]);
tx_state.AppendText(result[i] + "Upload Done");
}
}
}
This is my Filedialog_init function
private static void Filedialog_init()
{
Stream myStream = null;
OpenFileDialog openFileDialog = new OpenFileDialog();
openFileDialog.InitialDirectory = "c:\\";
openFileDialog.Filter = "bin files (*.bin)|*.bin|All files (*.*)|*.*";
openFileDialog.FilterIndex = 1;
openFileDialog.RestoreDirectory = true;
openFileDialog.Multiselect = false;
if (openFileDialog.ShowDialog() == DialogResult.OK)
{
string filename = null;
string _datatype = null;
try
{
if ((myStream = openFileDialog.OpenFile()) != null)
{
foreach (String file in openFileDialog.FileNames)
{
filename = Path.GetFileName(file);
result.Add(filename);
// only show the name of file
Datatype.Add(_datatype);
}
filePath = openFileDialog.FileNames;
Datatype.ForEach(Console.WriteLine);
}
openFileDialog.Dispose();
}
catch (Exception ex)
{
MessageBox.Show("Error: Could not read file from disk. Original error: " + ex.Message);
}
}
else
MessageBox.Show("Upload Cancel");
}
I can upload the file successfully by assigning the filename and its datatype and path directly
But when I used openfiledialog,it went wrong with "my file is being used by another process"
How can I solve this problem?
Issue lies in your code here,
(myStream = openFileDialog.OpenFile()) This line is keeping lock on the file because your myStream does not get disposed. you need to dispose the stream as soon as you are done with it.
So try with using as it will dispose the stream as soon as your end using line gets executed. More details on using.
you can try as below,
using(Stream myStream = openFileDialog.OpenFile())
{
//Your code here...
}
My issue is that I keep seeing a recurring theme with trying to allow my Notepad clone to save a file. Whenever I try to save a file, regardless of the location on the hard disk, the UnauthorizedAccess Exception continues to be thrown. Below is my sample code for what I've done, and I have tried researching this since last night to no avail. Any help would be greatly appreciated.
//located at base class level
private const string fileFilter = "Text Files|*.txt|All Files|*.*";
private string currentPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
private void MenuFileSaveAs_Click(object sender, RoutedEventArgs e)
{
SaveFileDialog sfd = new SaveFileDialog();
sfd.DefaultExt = "*.txt";
sfd.Filter = fileFilter;
sfd.AddExtension = true;
sfd.InitialDirectory = currentPath;
sfd.RestoreDirectory = true;
sfd.OverwritePrompt = true;
sfd.ShowDialog();
try
{
System.IO.File.WriteAllText(currentPath,TxtBox.Text,Encoding.UTF8);
}
catch (ArgumentException)
{
// Do nothing
}
catch(UnauthorizedAccessException)
{
MessageBox.Show("Access Denied");
}
}
Change the following lines.
...
if (sfd.ShowDialog() != true)
return;
try
{
using (var stream = sfd.OpenFile())
using (var writer = new StreamWriter(stream, Encoding.UTF8))
{
writer.Write(TxtBox.Text);
}
}
...
I hope it helps you.
You need to get the correct path context and file object from the dialog box once the user has hit 'ok'. Namely verify the user actually hit ok and then use the OpenFile property to see what their file selection is:
if (sfd.ShowDialog.HasValue && sfd.ShowDialog)
{
if (sfd.OpenFile() != null)
{
// convert your text to byte and .write()
sfd.OpenFile.Close();
}
}
I am trying to Copy outlook email and paste it onto form. Whenever I perform paste operation outlook mail (MSG file) should get saved to some directory and I have implemented some code as shown below.
private void OutlookMailCopyPaste_KeyDown(object sender, KeyEventArgs e)
{
if (e.Control && e.KeyCode == Keys.V)
{
if (Clipboard.ContainsData("FileGroupDescriptor"))
{
if (Clipboard.ContainsData("FileGroupDescriptorW"))
{
Stream fileStream = (Stream)Clipboard.GetData("FileGroupDescriptor");
byte[] fileGroupDescriptor = new byte[fileStream.Length];
fileStream.Read(fileGroupDescriptor, 0, fileGroupDescriptor.Length);
fileStream.Close();
System.Text.StringBuilder fileName = new System.Text.StringBuilder("");
for (int i = 76; i < fileGroupDescriptor.Length; i++)
{
fileName.Append(Convert.ToChar(fileGroupDescriptor[i]));
}
//fileGroupDescriptor = Encoding.Convert(Encoding.GetEncoding("iso-8859-1"), Encoding.UTF8, fileGroupDescriptor);
//string tempString = Encoding.UTF8.GetString(fileGroupDescriptor, 0, fileGroupDescriptor.Length);
string tempString = fileName.ToString().Substring(fileName.ToString().IndexOf('.'));
if (tempString.ToUpper().StartsWith(".MSG"))
{
if (Clipboard.ContainsData("FileContents"))
{
MemoryStream[] filestreams = (MemoryStream[])Clipboard.GetData("FileContents");
if (filestreams != null && filestreams.Length > 0)
{
MemoryStream filestream = filestreams[0];
//save the file stream using its name to the application path
FileStream outputStream = File.Create(fileName.ToString());
filestream.WriteTo(outputStream);
outputStream.Close();
}
}
}
else
{
MessageBox.Show("Please copy and paste MSG file only.");
}
}
}
}
}
When ever I am reading clipboard data into memory stream I'm getting an exception like "Insufficient memory to continue the execution of the program." at line
MemoryStream[] filestreams =
(MemoryStream[])Clipboard.GetData("FileContents");
moreover Clipboard.GetData("FileContents") having null though i am checking whether it has some data or not prior to this line
if (Clipboard.ContainsData("FileContents"))
Thanks and Regards,
Ramesh Morasa