0

Popenでsshを介してコマンドを発行し、出力を返す関数を作成しようとしています。

def remote(cmd):
    escaped = escape(cmd)
    return subprocess.Popen(escaped, ...).communicate()[0]

私の問題は、escape関数の実装方法です。このためのヘルパーを備えたPythonモジュール(2.6)はありますか?グーグルはそこにあることを示していますがpipes.quotere.escapeそれらはローカルで実行されるコマンドに対してのみ機能するようです。コマンドがsshに渡されると、エスケープはより厳密にする必要があるようです。

たとえば、ローカルマシンでは、これは問題ありません。

echo $(hostname)

sshに渡すときは、次のようにする必要があります。

ssh server "echo \$(hostname)"

また、二重引用符は、コンテキストに応じてさまざまな方法で解釈できます。リテラル引用符の場合、次のものが必要です。

ssh a4ipe511 "echo \\\"hello\\\""

変数の拡張を行うために、二重引用符も使用されます。

ssh a4ipe511 "echo \"\$(hostname)\""

ご覧のとおり、SSHに入るコマンドをエスケープするためのルールはかなり複雑になる可能性があります。この関数は誰でも呼び出されるので、複雑なコマンドによっては関数が誤った出力を返すのではないかと心配しています。

これは組み込みのPythonモジュールで解決できるものですか、それとも自分でエスケープを実装する必要がありますか?

4

1 に答える 1

1

初め:

pipes.quoteローカルで実行されるコマンドとre.escapeは何の関係もありません。それらは単に文字列を変換します。その後あなたがそれで何をするかはあなたのビジネスです。したがって、どちらか(特にpipes.quote)は、必要なものに適しています。

2番:

echo $(hostname)を使用してリモートホストでコマンドを実行する場合、デフォルトではコマンドがシェルに渡されないsshため、シェルのエスケープについて心配する必要はありません。subprocess.Popenしたがって、たとえば、これは問題なく機能します。

>>> import subprocess
>>> subprocess.call([ 'ssh', 'localhost', 'echo $(hostname)'])
myhost.example.com
0

二重引用符も期待どおりに機能します。

>>> subprocess.call([ 'ssh', 'localhost', 'echo "one   two"; echo three'])
one   two
three
0

あなたが実際に問題を抱えているかどうかは私にはわかりません。

于 2013-03-18T19:47:31.040 に答える