简体   繁体   English

如何通过 sudo 运行命令并通过 ssh .net c# 输入密码

[英]How to run commands by sudo and enter password by ssh .net c#

I want to run command and get the result on remote computer which has Linux operating system.我想在具有 Linux 操作系统的远程计算机上运行命令并获取结果。 I am using ssh .net library to connect by C# code.我正在使用 ssh .net 库通过 C# 代码进行连接。 I can connect and run some commands that it doesn't need to use "sudo" before.我可以连接并运行一些以前不需要使用“sudo”的命令 but I don't know How to run commands which need to be run by sudo, because after run -for instance- "sudo iptables -L -n" I should enter password and I don't know How to enter password after execute this command.但我不知道如何运行需要由 sudo 运行的命令,因为在运行后-例如-“sudo iptables -L -n”我应该输入密码,但我不知道执行此操作后如何输入密码命令。

This is my code :这是我的代码:

private void connectingToLinuxHost(string ip, string username, string password, int port)
{
    SshCommandLineRunner ssh = new SshCommandLineRunner(ip, username, password, port);
    ssh.Connect();
    string output1 = ssh.ExecuteCommand("ls");

    ssh.ExecuteCommand("sudo iptables -L -n");
    Thread.Sleep(1000);
    string output2 = ssh.ExecuteCommand(password);

    ssh.ExecuteCommand("sudo iptables -L -n \n");
    Thread.Sleep(1000);
    string output3 = ssh.ExecuteCommand(password);
}

when this function run, I can connect to remote pc successfully, output1 has correct value, but output2 and output3 are empty.当这个函数运行时,我可以成功连接到远程电脑,输出1有正确的值,但输出2和输出3为空。 actually it is obvious that after sudo command it is needed to enter password.实际上很明显,在 sudo 命令之后需要输入密码。 I have read most question about ssh .net.我已经阅读了有关 ssh .net 的大多数问题。 some similar question has retain unanswered.一些类似的问题仍未得到解答。

SSH .NET : freeze upon sudo su - user2 ( he or she didnt know the password but I know I dont know how to enter it via code) SSH .NET:冻结 sudo su - user2 (他或她不知道密码,但我知道我不知道如何通过代码输入)

How to su with SSH.Net? 如何使用 SSH.Net su? (I used create shell method but i couldn't understand what is for and like this question I got "Last login: ..." output.) (我使用了 create shell 方法,但我无法理解这个问题的目的是什么,我得到了“上次登录:...”输出。)

The most secure way to do it, as already mentioned by a comment, is to use CreateShellStream and just write the password directly to the stream after running the sudo command.正如评论中已经提到的,最安全的方法是使用 CreateShellStream 并在运行 sudo 命令后直接将密码写入流。 The password gets sent just as if you had been using an interactive terminal.发送密码就像您使用交互式终端一样。 This might not be a convenient solution, though, if you don't want to be locked into using an endless stream for the rest of what you want to do.但是,这可能不是一个方便的解决方案,如果您不想被锁定为使用无休止的流来完成您想做的其余事情。 Example:例子:

var promptRegex = new Regex(@"\][#$>]"); // regular expression for matching terminal prompt
var modes = new Dictionary<Renci.SshNet.Common.TerminalModes, uint>();
using (var stream = ssh.CreateShellStream("xterm", 255, 50, 800, 600, 1024, modes))
{
    stream.Write("sudo iptables -L -n\n");
    stream.Expect("password");
    stream.Write("mypassword\n");
    var output = stream.Expect(promptRegex);
}

The downside is that your output will include junk you don't really want: control characters, prompts, and everything else that gets sent over the stream.缺点是您的输出将包含您并不真正想要的垃圾:控制字符、提示以及通过流发送的所有其他内容。

If you want to avoid using a shell stream then you may be able to (depending on security settings) provide a password via stdin.如果您想避免使用 shell 流,那么您可以(取决于安全设置)通过 stdin 提供密码。 THIS IS INSECURE because commands get logged in various places and you might be revealing your password to other users with root access.这是不安全的,因为命令会记录在不同的地方,并且您可能会将您的密码泄露给其他具有 root 访问权限的用户。 If you're the only user, or if you don't care that everybody else can see your password, then this might be more convenient for you.如果您是唯一的用户,或者您不关心其他人是否可以看到您的密码,那么这对您来说可能更方便。

Example:例子:

using (var cmd = ssh.RunCommand("echo -e 'mypassword\n' | sudo -S iptables -L -n"))
{
    if (cmd.ExitStatus == 0)
        Console.WriteLine(cmd.Result);
    else
        Console.WriteLine(cmd.Error);
}

Finally, it's also possible to have a script print your password to stdin.最后,还可以让脚本将您的密码打印到标准输入。 This way your password won't get logged along with the rest of the command line;这样您的密码就不会与命令行的其余部分一起记录; but this still isn't much more secure since anyone with root access could potentially read the script and see the password:但这仍然不是更安全,因为任何具有 root 访问权限的人都可能读取脚本并查看密码:

using (var cmd = ssh.RunCommand("~/printpasswd.sh | sudo -S iptables -L -n"))
{
    if (cmd.ExitStatus == 0)
        Console.WriteLine(cmd.Result);
    else
        Console.WriteLine(cmd.Error);
}

and inside printpasswd.sh:在 printpasswd.sh 中:

#!/bin/bash
echo -e 'mypassword\n'

You can use the same bash command with Renci library and install in the server "sshpass" package.您可以对 Renci 库使用相同的 bash 命令并安装在服务器“sshpass”包中。 In this case you can use:在这种情况下,您可以使用:

SshClient client = new SsClient(IP_server, username, password);
client.Connect();
var commandToSend = client.CreateCommand("sshpass -p \"password\" sudo iptables -L");
commandToSend.Execute();
string response = commandToSend:Result.ToString();
Console.WriteLine("Response: " + response);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM