JElster
asked on
C# ProcessStart - How to automatically press the Y key
Hi.. I'm using ProcessStart to automatically run an external process. I need to press the Y key after about a second to continue the process. The process runs in DOS and I need to 'Accept' a message. How can I press the Y key automatically here is my existing code. thanks
ProcessStartInfo _psi = new ProcessStartInfo("pgp.exe" );
_psi.WorkingDirectory = "C:\";
_psi.RedirectStandardInput = true;
_psi.RedirectStandardOutpu t = true;
_psi.RedirectStandardError = true;
_psi.CreateNoWindow = false;
_psi.Arguments = " -e test.txt public.asc myEmail +force ";
System.Diagnostics.Process proc = System.Diagnostics.Process .Start(_ps i);
System.IO.StreamReader output = proc.StandardOutput;
// Attach the in for writing
System.IO.StreamWriter sIn = proc.StandardInput;
// Write each line of the batch file to standard input
while (output.Peek() != -1)
{
/// Need to press the enter key after the message in dos window
sIn.WriteLine(output.ReadL ine());
}
ProcessStartInfo _psi = new ProcessStartInfo("pgp.exe"
_psi.WorkingDirectory = "C:\";
_psi.RedirectStandardInput
_psi.RedirectStandardOutpu
_psi.RedirectStandardError
_psi.CreateNoWindow = false;
_psi.Arguments = " -e test.txt public.asc myEmail +force ";
System.Diagnostics.Process
System.IO.StreamReader output = proc.StandardOutput;
// Attach the in for writing
System.IO.StreamWriter sIn = proc.StandardInput;
// Write each line of the batch file to standard input
while (output.Peek() != -1)
{
/// Need to press the enter key after the message in dos window
sIn.WriteLine(output.ReadL
}
How about;
SendKeys.Send("{Y}");
SendKeys.Send("{Y}");
SendKeys only work with windows applications
You redirected stdin so your can write strings to a stream and the console
will read it from std in like normal
You redirected stdin so your can write strings to a stream and the console
will read it from std in like normal
ASKER
What?
something like this:
sIn.WriteLine("Y");
sIn.Flush();
If SendKeys.Send("{Y}") doesn't help you then try the InputSimulator.
The InputSimulator should also solve your problem.
The InputSimulator should also solve your problem.
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
You can also redirect StandardInput and not StandardOutput, wait for a second, and then write a "Y" to StandardInput - this is much simpler but has the downside that you might send the "Y" too early, and won't be able to know if something went wrong.
using System;
using System.Diagnostics;
using System.Text;
using System.Threading;
class Program
{
static void Main(string[] args)
{
Process proc = new Process();
// Run the command "del c:\temp" in a DOS window
// This will show a confirmation prompt requiring
// us to send a "Y" to continue
proc.StartInfo.FileName = "cmd.exe";
proc.StartInfo.Arguments = @"/c del c:\temp\*";
// Redirect standard input
proc.StartInfo.RedirectStandardInput = true;
// UseShellExecute must be false to redirect input
proc.StartInfo.UseShellExecute = false;
// Start the process
proc.Start();
// Wait a second
Thread.Sleep(1000);
// Write a "Y" to the process's input
proc.StandardInput.WriteLine("Y");
// Now that we've sent the confirmation "Y" wait for the process to exit
proc.WaitForExit();
Console.WriteLine("The process finished with ExitCode: {0}", proc.ExitCode);
Console.Write("Press any key to exit...");
Console.ReadKey();
}
}
ASKER
It appears I have to press ENTER after the Y.
How can I press ENTER.
thx again
How can I press ENTER.
thx again
ASKER
The following does not help
proc.StandardInput.WriteLi ne("Y");
proc.StandardInput.WriteLi ne();
proc.StandardInput.Flush() ;
Still requires a manual enter
????????
proc.StandardInput.WriteLi
proc.StandardInput.WriteLi
proc.StandardInput.Flush()
Still requires a manual enter
????????
Post your code.
ASKER
ProcessStartInfo _psi = new ProcessStartInfo("pgp.exe" );
_psi.WorkingDirectory = ConfigurationSettings.AppS ettings["U pLoadLocat ion"];
_psi.UseShellExecute = false;
_psi.RedirectStandardInput = true;
_psi.RedirectStandardOutpu t = true;
_psi.RedirectStandardError = true;
_psi.CreateNoWindow = false;
_psi.Arguments = " -e " + _zipFile + " MYKEY.asc MYEMAIL +force ";
System.Diagnostics.Process proc = System.Diagnostics.Process .Start(_ps i);
StringBuilder procOutput = new StringBuilder();
// Read the process's output until we see the
// "Are you sure?" prompt and then send a "Y"
while (!proc.StandardOutput.EndO fStream)
{
// Read up to 1024 characters into the char[] array "buffer"
char[] buffer = new char[1024];
proc.StandardOutput.Read(b uffer, 0, buffer.Length);
// Append the chars we just read to the procOutput StringBuilder
procOutput.Append(buffer);
// Check if procOutput ends with "Are you sure (Y/N)?"
if (procOutput.ToString().Con tains("(y/ N)?"))
{
// If so send "Y" and exit this loop
proc.StandardInput.WriteLi ne("Y");
proc.StandardInput.WriteLi ne();
proc.StandardInput.Flush() ;
break;
}
}
// Now that we've sent the confirmation "Y" wait for the process to exit
proc.WaitForExit();
_psi.WorkingDirectory = ConfigurationSettings.AppS
_psi.UseShellExecute = false;
_psi.RedirectStandardInput
_psi.RedirectStandardOutpu
_psi.RedirectStandardError
_psi.CreateNoWindow = false;
_psi.Arguments = " -e " + _zipFile + " MYKEY.asc MYEMAIL +force ";
System.Diagnostics.Process
StringBuilder procOutput = new StringBuilder();
// Read the process's output until we see the
// "Are you sure?" prompt and then send a "Y"
while (!proc.StandardOutput.EndO
{
// Read up to 1024 characters into the char[] array "buffer"
char[] buffer = new char[1024];
proc.StandardOutput.Read(b
// Append the chars we just read to the procOutput StringBuilder
procOutput.Append(buffer);
// Check if procOutput ends with "Are you sure (Y/N)?"
if (procOutput.ToString().Con
{
// If so send "Y" and exit this loop
proc.StandardInput.WriteLi
proc.StandardInput.WriteLi
proc.StandardInput.Flush()
break;
}
}
// Now that we've sent the confirmation "Y" wait for the process to exit
proc.WaitForExit();
Does pgp.exe not have a command line to suppress confirmation prompts? There should be a BATCHMODE option, intended specifically for this purpose...
ASKER
I think it does... checking now.......
thx!
thx!
Maybe --force?
ASKER
I'm doing a force and batchmode... get a Encryption error.......
Says it skipping the Y/N but get an encryption error...
Says it skipping the Y/N but get an encryption error...
I'm not particularly familiar with PGP - are you sure the rest of the command line is correct? Are you testing it in a cmd window by hand before trying to run it in your C# code?
ASKER
Yes.. that's exactly what I've been doing
thx
thx
Well, if that switch doesn't work out for you I've updated the code slightly to be more accurate:
Making that batch mode work is your best bet, though.
ProcessStartInfo _psi = new ProcessStartInfo("pgp.exe");
_psi.WorkingDirectory = ConfigurationSettings.AppSettings["UpLoadLocation"];
_psi.UseShellExecute = false;
_psi.RedirectStandardInput = true;
_psi.RedirectStandardOutput = true;
_psi.RedirectStandardError = true;
_psi.CreateNoWindow = false;
_psi.Arguments = " -e " + _zipFile + " MYKEY.asc MYEMAIL +force ";
System.Diagnostics.Process proc = System.Diagnostics.Process.Start(_psi);
StringBuilder procOutput = new StringBuilder();
// Read the process's output until we see the
// "Are you sure?" prompt and then send a "Y"
while (!proc.StandardOutput.EndOfStream)
{
// Read up to 1024 characters into the char[] array "buffer"
char[] buffer = new char[1024];
// Store the number of characters actually read
// (since it will undoubtedly be less than 1024)
int charsRead = proc.StandardOutput.Read(buffer, 0, buffer.Length);
// Append the chars we just read to the procOutput StringBuilder
// Use "charsRead" to only append the part of the buffer[] array
// that was filled, otherwise we'd end up appending a couple
// characters that Read() filled followed by a bunch of nulls
procOutput.Append(buffer, 0, charsRead);
// Check if procOutput ends with "Are you sure (Y/N)?"
if (procOutput.ToString().Contains("(y/N)?")) // Make sure this is actually "(y/N)?" and not "(y/N) ?"
{
// If so send "Y" and exit this loop
proc.StandardInput.WriteLine("Y");
proc.StandardInput.WriteLine();
proc.StandardInput.Flush();
break;
}
}
// Now that we've sent the confirmation "Y" wait for the process to exit
proc.WaitForExit();
Making that batch mode work is your best bet, though.
...You can also omit lnes 37 & 38 in that example (the WriteLine method automatically appends a CRLF).
ASKER
I think the issue is that I'm using an old PGP exe and the batchmode sucks...
Will try with a new PGP exe.. thanks for you help
Will try with a new PGP exe.. thanks for you help
http://inputsimulator.codeplex.com/