Created
October 3, 2011 17:06
-
-
Save alexbeletsky/1259608 to your computer and use it in GitHub Desktop.
Running SSH under web application
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections.Generic; | |
using System.Linq; | |
using System.Web; | |
using System.Web.Mvc; | |
using System.Diagnostics; | |
using System.IO; | |
// Please try to run both: Cassini and IIS. | |
// For IIS select Application Pool with Process Identity == Your identity | |
// | |
// Expected output: | |
// Hi you_github_accout! You've successfully authenticated, but GitHub does not provide shell access. | |
// | |
// Actual output (Cassini): | |
// Hi you_github_accout! You've successfully authenticated, but GitHub does not provide shell access. | |
// | |
// Actual output (IIS): | |
// HANGS UP | |
namespace SshDiagnose.Controllers { | |
public class HomeController : Controller { | |
class CommandOutputReceiver { | |
private readonly TextWriter SynchronizedOutputWriter; | |
private readonly TextWriter SynchronizedErrorWriter; | |
private readonly TextWriter SynchronizedCombinedWriter; | |
private readonly StringWriter OutputWriter; | |
private readonly StringWriter ErrorWriter; | |
private readonly StringWriter CombinedWriter; | |
public CommandOutputReceiver() { | |
OutputWriter = new StringWriter(); | |
SynchronizedOutputWriter = TextWriter.Synchronized(OutputWriter); | |
ErrorWriter = new StringWriter(); | |
SynchronizedErrorWriter = TextWriter.Synchronized(ErrorWriter); | |
CombinedWriter = new StringWriter(); | |
SynchronizedCombinedWriter = TextWriter.Synchronized(CombinedWriter); | |
} | |
public void OutputDataReceived(object sender, DataReceivedEventArgs e) { | |
SynchronizedOutputWriter.WriteLine(e.Data); | |
SynchronizedCombinedWriter.WriteLine(e.Data); | |
} | |
public void ErrorDataReceived(object sender, DataReceivedEventArgs e) { | |
SynchronizedErrorWriter.WriteLine(e.Data); | |
SynchronizedCombinedWriter.WriteLine(e.Data); | |
} | |
public string Output { | |
get { | |
return OutputWriter.ToString(); | |
} | |
} | |
public string Error { | |
get { | |
return ErrorWriter.ToString(); | |
} | |
} | |
public string ErrorAndOutput { | |
get { | |
return CombinedWriter.ToString(); | |
} | |
} | |
} | |
public ActionResult Index() { | |
var output = new CommandOutputReceiver(); | |
var process = CreateProcess("cmd", "/C ssh -n -T git@github.com", output); | |
RunProcess(process); | |
return new ContentResult() { Content = output.ErrorAndOutput }; | |
} | |
private void RunProcess(Process p) { | |
ConsoleCancelEventHandler killOnCtrlC = (sender, cancelEvent) => p.Kill(); | |
p.Start(); | |
System.Console.CancelKeyPress += killOnCtrlC; | |
try { | |
p.BeginErrorReadLine(); | |
p.BeginOutputReadLine(); | |
p.WaitForExit(); | |
} | |
finally { | |
System.Console.CancelKeyPress -= killOnCtrlC; | |
} | |
} | |
private Process CreateProcess(string commandName, string commandArgumentsForLogging, CommandOutputReceiver output) { | |
var processInfo = new ProcessStartInfo(commandName, commandArgumentsForLogging); | |
processInfo.CreateNoWindow = true; | |
processInfo.RedirectStandardError = true; | |
processInfo.RedirectStandardOutput = true; | |
processInfo.UseShellExecute = false; | |
processInfo.ErrorDialog = false; | |
var p = new Process { StartInfo = processInfo }; | |
p.ErrorDataReceived += output.ErrorDataReceived; | |
p.OutputDataReceived += output.OutputDataReceived; | |
return p; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment