C# Windows Application File: have no access for File.Copy - c#

I have a project in ANN. To make it firstly i want to clone the picture to the local directory that can be accessed everytime in order to have indexing. The directory is
#"D:\assets\"
For the images, i'm using openfiledialog and multiselect is on.
For the container, i'm using this LOC:
> List<string[,]> path = new List<string[,]>();
The whole code is seperated. The first one is for browse and the second one is for copy the images to the directory that the first time i was mention.
For browse button:
List<string[,]> path = new List<string[,]>();
private void btnBrowse_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog();
ofd.Filter = "File Extention|*.jpg;*.jpeg;*.bmp";
ofd.Multiselect = true;
if(ofd.ShowDialog() == DialogResult.OK)
{
foreach (var filename in ofd.FileNames)
{
imageList.Images.Add(filename, new Bitmap(filename));
var saveFileName = Path.GetFileName(filename);
var saveFileDir = Path.GetDirectoryName(filename);
lvFruit.Items.Add(saveFileName, filename);
string[,] input = new string[,] { {saveFileDir, saveFileName } };
path.Add(input);
}
}
}
For saving picture
private void btnSubmit_Click(object sender, EventArgs e)
{
String fruitname = txtFruitName.Text;
string appPath = #"D:\assets\";
if (txtFruitName.Text == "")
{
MessageBox.Show("Fruit Name Should be Filled");
}
else
{
int newindex = 0;
foreach (var item in path)
{
newindex += 1;
string iName = item[newindex - 1, 1].Trim();
string iPath = item[newindex - 1, 0].Trim();
try
{
File.Copy(iPath, appPath + iName, true);
File.SetAttributes(appPath, FileAttributes.Normal);
}
catch (Exception err)
{
MessageBox.Show(err.ToString());
//MessageBox.Show("Permission error or picture is already exists");
}
path.Clear();
}
MessageBox.Show("All Picture Has Been Saved");
lvFruit.Clear();
txtFruitName.Text = "";
btnDone.Enabled = true;
}
}
The images file is located at D:\pic and should be copied to D:\assets
The error is:
System.UnauthorizedAccessException: Access to the path 'D:\pic is denied
at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
at System.IO.File.InternalCopy(String sourceFileName, String destFileName, Boolean overwrite, Boolean checkHost)
at System.IO.File.Copy(String sourceFileName, String destFileName,Boolean overwrite)
at Fruit_Dictionary.trainForm.btnSubmit_Click(Object sender EventArgs e) in D:\Fruit Dictionary\Fruit Dictionary\trainForm.cs:line 95
Do you know what the reason why it doesn't have any permited?
Actually i have run the program as administrator, and ofc i have check the permission in D:\pic and change it to do all permission.
I've been looking and surfing in internet for 2 days for just this reason, but i can't archieve anything. Any help will be helpful for me to accomplished this project.
Thank you :)

try to use a process to copy your files
foreach(String ImageOldPath in Paths)
{
try{
ProcessStartInfo info = new ProcessStartInfo();
info.FileName = "C:\\Windows\\system32\\xcopy.exe";
info.Arguments = $"{ImageOldPath LocalPath} "
Console.WriteLine(info.Arguments);
info.UseShellExecute = false;
info.CreateNoWindow = true;
info.WindowStyle = ProcessWindowStyle.Hidden;
Process proc = new Process();
proc.StartInfo = info;
proc.Start();
proc.Dispose();
}catch(Exception e){}
}
UPDATE
ImageOldPath is the image old path in your case its called filename located in your foreach statement
Local path is appPath

Related

C # ListBox how to export a file with the name I pass from the listbox

**sorry for my english but i don't know very well in google translate i do translation.
I want from my listbox the file that I choose to be exported with the same name that it has in my listbox**
private void downloadFile(object sender, EventArgs e)
{
string ip = txt_ip.Text;
string user = txt_user.Text;
string pass = txt_pass.Text;
//string pathLocalFile = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Desktop), "download_sftp_file.txt");
try
{
SftpClient client = new SftpClient(ip, user, pass);
client.Connect();
string rmDer = dr_finder.Text;
var files = client.ListDirectory(rmDer);
if (rmDer == "")
{
client.Connect();
string rmDerNow = "/";
var filesName = client.ListDirectory(rmDerNow);
foreach (var file in filesName)
{
DirList.Items.Add(file.Name);
string result = Path.GetFileNameWithoutExtension(file.Name);
DirList.Items.Add(System.IO.Path.GetFileName(file.Name));
}
MessageBox.Show("List Directory Success!");
}
string pachRemFile = DirList.SelectedItem.ToString();
string pachlocalFile = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Desktop),"Server Ftp File.txt");
Stream Filestream = File.OpenWrite(pachlocalFile);
client.DownloadFile(pachRemFile,Filestream);
client.Disconnect();
}
catch (Exception error)
{
MessageBox.Show(error.Message);
}
}
this object is the solution I finally didn't find anyone to help me. so I helped myself.
and I thought he had good programmers on this site
SaveFileDialog savefile = new SaveFileDialog(); /* this here is my solution get a save as. */
if (savefile.ShowDialog() == DialogResult.OK)
{
string pachRemFile = DirList.SelectedItem.ToString();
Stream Filestream = File.Open(savefile.FileName, FileMode.CreateNew);
StreamWriter sw = new StreamWriter(Filestream);
client.DownloadFile(pachRemFile, Filestream);
client.Disconnect();
}

C# is crashing on an event

I am trying to create a C# service as a console app.
The main code:
static void Main(string[] args)
{
var exitCode = HostFactory.Run(
x =>
{
x.Service<HeartBeat>(s =>
{
s.ConstructUsing(heartbeat => new HeartBeat());
s.WhenStarted(heartbeat => heartbeat.Start());
s.WhenStopped(heartbeat => heartbeat.Stop());
});
x.RunAsLocalSystem();
x.SetServiceName("UpgradeServices");
x.SetDisplayName("Service Upgrade");
x.SetDescription("Service is monitoring new version.");
});
int exitCodeValue = (int)Convert.ChangeType(exitCode, exitCode.GetTypeCode());
Environment.ExitCode = exitCodeValue;
}
Then I have code for deleting and copying files as per below:
public class MovingFiles
{
public string fileName;
public string destPath;
private DirectoryInfo directory;
private DirectoryInfo myFile;
public string sourcePath;
public string targetPath;
public MovingFiles(string sourceFolder, string targetFolder)
{
sourcePath = sourceFolder;
targetPath = targetFolder;
}
public void deleteFilesMethod()
{
System.Threading.Thread.Sleep(10000);
string deleteString;
//First we want to delete all files except for the JSON file as this has all of the important settings
if (System.IO.Directory.Exists(targetPath))
{
string[] files = System.IO.Directory.GetFiles(targetPath);
// Loop through each files and then delete these if they are not the JSON file
foreach (string s in files)
{
deleteString = targetPath;
// The file name which is returned will be deleted
fileName = System.IO.Path.GetFileName(s);
if (fileName != "appsettings.json")
{
deleteString = System.IO.Path.Combine(targetPath, fileName);
try
{
System.IO.File.Delete(deleteString);
}
catch (System.IO.IOException e)
{
Console.WriteLine(e.Message);
return;
}
}
}
}
else
{
Console.WriteLine("The loop didn't run, source path doesn't exist");
}
}
public void copyFilesMethod()
{
System.Threading.Thread.Sleep(10000);
if (System.IO.Directory.Exists(sourcePath))
{
// Searching for the latest directory created in the sourcePath folder
directory = new DirectoryInfo(sourcePath);
myFile = (from f in directory.GetDirectories()
orderby f.LastWriteTime descending
select f).First();
sourcePath = System.IO.Path.Combine(sourcePath, myFile.Name);
string[] files = System.IO.Directory.GetFiles(sourcePath);
// Copy the files and overwrite destination files if they already exist.
foreach (string s in files)
{
// Use static Path methods to extract only the file name from the path.
fileName = System.IO.Path.GetFileName(s);
if (fileName != "appsettings.json")
{
destPath = System.IO.Path.Combine(targetPath, fileName);
try
{
System.IO.File.Copy(s, destPath, true);
}
catch (System.IO.IOException e)
{
Console.WriteLine(e.Message);
return;
}
}
}
}
else
{
Console.WriteLine("The loop didn't run, source path doesn't exist");
}
// Keep console window open in debug mode.
Console.WriteLine("Procedure has been completed.");
}
This should be triggered once there is a new file, which I have written as this:
class FileMonitor
{
public FileSystemWatcher watcher = new FileSystemWatcher();
public string sourcePath;
public string targetPath;
public FileMonitor(string sourceFolder, string targetFolder)
{
sourcePath = sourceFolder;
targetPath = targetFolder;
}
public void watch()
{
watcher.Path = sourcePath;
watcher.NotifyFilter = NotifyFilters.LastWrite
| NotifyFilters.FileName | NotifyFilters.DirectoryName
| NotifyFilters.CreationTime;
//var one = NotifyFilters.FileName;
watcher.Filter = "*.*";
watcher.Created += new FileSystemEventHandler (OnChanged);
watcher.EnableRaisingEvents = true;
//System.Threading.Thread.Sleep(25000);
}
public void OnChanged(object source, FileSystemEventArgs e)
{
//Copies file to another directory.
MovingFiles FileMoveOne = new MovingFiles(sourcePath, targetPath);
FileMoveOne.deleteFilesMethod();
FileMoveOne.copyFilesMethod();
}
}
What I understand once I run the below it would look every 10 seconds if there is a new file and then trigger the OnChange method, am I right?
public class HeartBeat
{
private readonly Timer _timer;
public HeartBeat()
{
_timer = new Timer(10000)
{
AutoReset = true
};
_timer.Elapsed += TimerElapsed;
}
private void TimerElapsed(object sender, ElapsedEventArgs e)
{
//StringBuilder loggingLine = new StringBuilder();
/* Every 30 seconds it will write to the file */
string[] lines = new string[] {DateTime.Now.ToString() + ": Heartbeat is active. Service is monitoring SS and DS"};
//lines[1] = DateTime.Now.ToString() + " About to check if new files are placed on server";
//loggingLine.Append(lines[i]);
File.AppendAllLines(#"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor1\HeartBeat.log", lines);
//File.AppendAllLines(#"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor1\HeartBeat.log", lines);
FileMonitor versioOne = new FileMonitor(#"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor1", #"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor2");
versioOne.watch();
}
public void Start ()
{
_timer.Start();
}
public void Stop ()
{
_timer.Stop();
}
}
The issue I am having is inconsistency.
It should copy the files to the folder Monitor2 once a new folder is created, but it is not doing that on the first creation. It does delete and copy the files on the second time once create a folder in monitor1 folder.
On every second time it is trying to copy the files it crashes with the below error which I am not familiar with:
Topshelf.Hosts.ConsoleRunHost Critical: 0 : The service threw an unhandled exception, System.UnauthorizedAccessException: Access to the path 'C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor2\System.Net.Sockets.dll' is denied.
at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
at System.IO.File.InternalDelete(String path, Boolean checkHost)
at System.IO.File.Delete(String path)
at UpgradeServices.MovingFiles.deleteFilesMethod() in C:\Users\RLEBEDEVS\Desktop\C#\Service\UpgradeServices\MovingFIles.cs:line 48
at UpgradeServices.FileMonitor.OnChanged(Object source, FileSystemEventArgs e) in C:\Users\RLEBEDEVS\Desktop\C#\Service\UpgradeServices\FileMonitor.cs:line 43
at System.IO.FileSystemWatcher.OnCreated(FileSystemEventArgs e)
at System.IO.FileSystemWatcher.NotifyFileSystemEventArgs(Int32 action, String name)
at System.IO.FileSystemWatcher.CompletionStatusChanged(UInt32 errorCode, UInt32 numBytes, NativeOverlapped* overlappedPointer)
at System.Threading._IOCompletionCallback.PerformIOCompletionCallback(UInt32 errorCode, UInt32 numBytes, NativeOverlapped* pOVERLAP)
Topshelf.Hosts.ConsoleRunHost Information: 0 : Stopping the UpgradeServices service
Topshelf.Hosts.ConsoleRunHost Information: 0 : The UpgradeServices service has stopped.
The program '[497452] UpgradeServices.exe' has exited with code 1067 (0x42b).
Line 48 is this one, though it performed the tasks previously fine (on the first go).
System.IO.File.Delete(deleteString);
I see that the issue is with the way I am raising the event. Does anybody know what should I change in order to achieve the desired result which is when the service is started on every new folder created in the destiny it would perform the two methods moving and deleting files? The folder will always have only new folders created.
Regards,
It seems that in your heartbeat you starting new FileMonitor every 10 seconds, so after 20 seconds you will have 2 FileMonitor's watching and moving(deleting) the same files at the time. Just start FileMonitor once using hosted service for example. Or remove the timer handler part in your HeartBeat class and just create FileMonitor in constructor:
public HeartBeat()
{
FileMonitor versioOne = new
FileMonitor(#"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor1", #"C:\Users\RLEBEDEVS\Desktop\Monitor\Monitor2");
versioOne.watch();
// may be save it to instance field so it does not get garbage collected.
// Not sure how FileSystemWatcher behaves with subscription,
// it should prevent the "versionOne" from being collected via subscription.
}

Open a executable through filedialog this is getting errors - Why?

Does anyone know why the following will Open the Kool.exe however the Kool.exe cannot load all of its files unless i place the current projects debug/project.exe into the same folder as the Kool.exe it is trying to open?
private void button1_Click(object sender, EventArgs e)
{
OpenFileDialog openF1 = new OpenFileDialog();
openF1.InitialDirectory = #"C:\";
openF1.Title = "Browse for Kool.exe...";
openF1.CheckFileExists = true;
openF1.CheckPathExists = true;
openF1.DefaultExt = "exe";
openF1.FileName = "Kool";
openF1.Filter = "Kool (*.exe)|*.exe|All Files(*.*)|*.*";
openF1.FilterIndex = 2;
openF1.RestoreDirectory = true;
openF1.ReadOnlyChecked = true;
openF1.ShowReadOnly = true;
if (openF1.ShowDialog() == DialogResult.OK)
{
Process[] pname = Process.GetProcessesByName(openF1.FileName);
if (pname.Length == 0)
{
Process.Start(openF1.FileName);
this.Close();
}
else
{
MessageBox.Show("Kool is already running.", "Patch: Error", MessageBoxButtons.OK, MessageBoxIcon.Error, MessageBoxDefaultButton.Button1);
}
}
else
{
MessageBox.Show("Cannot find Kool install", "Patch: Error", MessageBoxButtons.OK, MessageBoxIcon.Error, MessageBoxDefaultButton.Button1);
}
}
Other: I am running the application as an administrator.
Firstly, I doubt that this has anything to do with the file open dialog.
I strongly suspect that the problem is that Kool.exe assumes that the files it needs are in the current working directory, instead of trying to find them relative to the executable file itself.
Ideally, you should fix Kool.exe to be more resilient - but if that's not possible, just set the new process's working directory when you start it.
string file = openF1.FileName;
string directory = new FileInfo(file).Directory;
Process.Start(new ProcessStartInfo {
FileName = file,
WorkingDirectory = directory
});

openfiledialog error for selecting used files

try
{
OpenFileDialog dialog = new OpenFileDialog();
String appData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
string tempPath = System.IO.Path.GetTempPath();
dialog.InitialDirectory = tempPath;
dialog.Multiselect = true;
dialog.Filter = "Temp files (*.tmp)|*.tmp";
dialog.ValidateNames = false;
if (dialog.ShowDialog() == DialogResult.OK)
{
string[] filePaths = dialog.SafeFileNames;
foreach (string s in filePaths)
richTextBox1.Text += s;
//MessageBox.Show("");
}
}
catch
{
MessageBox.Show("Error Occured");
}
when i selecting files (which already in use in another application) in openfiledialog I getting error but still I want their paths...
This is apparantly an issue with OpenFileDialog and MultiSelect "true." See this post for a discussion on the problem (and some possible solutions):
http://social.msdn.microsoft.com/forums/en-US/netfxbcl/thread/56fbbf9b-31d5-4e89-be85-83d9cb1d538c/
Setting openFileDialog.ValidateNames = false; worked for me.
try
String tempPath = System.IO.Path.GetDirectoryName(dialog.FileName) + #"\";

How to set Printer Settings while printing PDF

I'm trying to print a PDF file using Process object. And up to certain extent I could print it successfully. But now I want to set printer properties.. like no of copies, Paper size etc. But I don't see any property to set these values.
I'm using following code to print PDFs
string fileName = "";
string arguments = "";
string verbToUse = "";
int i = 0;
ProcessStartInfo startInfo = new ProcessStartInfo();
OpenFileDialog openFileDialog1 = new OpenFileDialog();
openFileDialog1.InitialDirectory = "c:\\";
openFileDialog1.Filter = "pdf files (*.pdf)|*.pdf|All files (*.*)|*.*";
openFileDialog1.FilterIndex = 2;
openFileDialog1.RestoreDirectory = true;
if (openFileDialog1.ShowDialog() == DialogResult.OK)
{
if ((fileName = openFileDialog1.FileName) != null)
{
startInfo = new ProcessStartInfo(fileName);
if (File.Exists(fileName))
{
i = 0;
foreach (String verb in startInfo.Verbs)
{
// Display the possible verbs.
MessageBox.Show(i.ToString() + ". " + verb);
i++;
}
}
}
//Console.WriteLine("Select the index of the verb.");
string index = "2";
if (Convert.ToInt32(index) < i)
verbToUse = startInfo.Verbs[Convert.ToInt32(index)];
else
return;
startInfo.Verb = verbToUse;
if (verbToUse.ToLower().IndexOf("printto") >= 0)
{
//Printer Name
arguments = #"\\hydfsvt02\HPLaserJ";
startInfo.Arguments = arguments;
}
Process newProcess = new Process();
newProcess.StartInfo = startInfo;
try
{
newProcess.Start();
MessageBox.Show(newProcess.ProcessName + " for file " + fileName + " started successfully with verb " + startInfo.Verb);
}
catch (System.ComponentModel.Win32Exception ex)
{
MessageBox.Show(" Win32Exception caught!");
MessageBox.Show(" Win32 error = " + ex.Message);
}
catch (System.InvalidOperationException)
{
MessageBox.Show("File " + fileName + " started with verb " + verbToUse);
}
}
I have written an application that does batch printing of PDF files.
It's not possible to specify the printer settings that you want to use. It's not even possible if you use the COM interface with the Adobe Standard/Pro versions.
Your options are to either:
Buy a license to a third-party PDF renderer that you can use to convert the PDF to Bitmaps and use the PrintDocument to control the PrinterSettings
Use something like GhostScript to convert the PDF files to BMP files and then use the PrintDocument class to print the BMP files. You can then control the PrinterSettings.
private void startPrintingButton_Click(object sender, EventArgs e)
{
OpenFileDialog ofd = new OpenFileDialog();
if (DialogResult.OK == ofd.ShowDialog(this))
{
PrintDocument pdoc = new PrintDocument();
pdoc.DefaultPageSettings.PrinterSettings.PrinterName = "ZDesigner GK420d";
pdoc.DefaultPageSettings.Landscape = true;
pdoc.DefaultPageSettings.PaperSize.Height = 140;
pdoc.DefaultPageSettings.PaperSize.Width = 104;
Print(pdoc.PrinterSettings.PrinterName, ofd.FileName);
}
}
private void Print(string printerName, string fileName)
{
try
{
ProcessStartInfo gsProcessInfo;
Process gsProcess;
gsProcessInfo = new ProcessStartInfo();
gsProcessInfo.Verb = "PrintTo";
gsProcessInfo.WindowStyle = ProcessWindowStyle.Hidden;
gsProcessInfo.FileName = fileName;
gsProcessInfo.Arguments = "\"" + printerName + "\"";
gsProcess = Process.Start(gsProcessInfo);
if (gsProcess.HasExited == false)
{
gsProcess.Kill();
}
gsProcess.EnableRaisingEvents = true;
gsProcess.Close();
}
catch (Exception)
{
}
}
This code will print PDF files as well as adjust the printing settings.

Categories