2013-08-14 28 views
24

Linuxの語数ユーティリティwcを実行して、現在/ var/log/syslogにある行の数を調べたいので、それが増えていることを検出できます。私は様々なテストを試みましたが、結果をwcから取得している間は、行数とコマンド(var/log/syslogなど)の両方が含まれています。Python3のサブプロセス出力

だから、戻っています:1338年の/ var// syslogの を記録 をしかし、私は唯一の行数をしたいので、私はは/ var/log/syslogの部分を取り除きたい、とちょうどI 1338

を保ちますbytestringから文字列に変換しようとしましたが、結果をストリッピングしましたが、喜びはありませんでした。文字列とストリッピング、デコードなどに変換するための同じストーリーは、すべて私が探している出力を生成することができません。

  • b'1338は/ var/log/syslogのを\ n」の
  • 1338は/ var/log/syslogの

これらはsyslogに1338行で、私は何を得るのいくつかの例であります

は、ここで私がしようとすると、このナットをクラックするために書いたいくつかのテストコードですが、ない解決策:

import subprocess 

#check_output returns byte string 
stdoutdata = subprocess.check_output("wc --lines /var/log/syslog", shell=True) 
print("2A stdoutdata: " + str(stdoutdata)) 
stdoutdata = stdoutdata.decode("utf-8") 
print("2B stdoutdata: " + str(stdoutdata))  
stdoutdata=stdoutdata.strip() 
print("2C stdoutdata: " + str(stdoutdata))  

これからの出力は次のとおりです。

  • 2Aのstdoutdata:b'1338は/ var/log/syslogのを\ n」は

  • 2B stdoutdata:1338は/ var/log/syslogの

  • 2C stdoutdata:1338は/ var/log/syslogの

  • 2D stdoutdata:1338は/ var/log/syslogの

答えて

39

私がお勧めsubprocess.getoutput()を使用します。シェルでコマンドを実行し、string outputbyte stringの出力ではなく)を取得します。次に、split on whitespaceを返し、返された文字列のリストから最初の要素を取得します。

このお試しください:* nixの上('\0'を除く)任意のバイトシーケンスであるかもしれないシェルとデコードのファイル名を呼び出す避けるために

import subprocess 
stdoutdata = subprocess.getoutput("wc --lines /var/log/syslog") 
print("stdoutdata: " + stdoutdata.split()[0]) 
+0

ありがとう!それをテストし、それは働いた。多くの研究をして、それを見たことはありませんでした。ダン! – user2565677

+3

'subprocess.getoutput'は* Legacy Shell Invocation Functions *(http://docs.python.org/3/library/subprocess.html#subprocess.getoutput)のカテゴリに属していることに注意してください。 – pepr

+0

@peprしかし、「遺産」という表記は、実際には何を意味していますか? 3.5.0a0のように、私は削除のタイムラインが表示されません。 (別の場所で定義されていますか?) – belacqua

8

を、あなたは標準入力としてファイルを渡すことができます。

import subprocess 

with open(b'/var/log/syslog', 'rb') as file: 
    nlines = int(subprocess.check_output(['wc', '-l'], stdin=file)) 
print(nlines) 

それとも、任意のデコードエラーを無視することができます:

import subprocess 

stdoutdata = subprocess.check_output(['wc', '-l', '/var/log/syslog']) 
nlines = int(stdoutdata.decode('ascii', 'ignore').partition(' ')[0]) 
print(nlines) 
+0

この場合、 'sys.stdout.encoding'を得る方法はありますか?これを' ascii'の代わりにデコードするために渡しますか? stdoutを 'subprocess.PIPE'すればどうなるでしょうか? –

+1

@Mr_and_Mrs_Dこれは間違ったことです.1一般的なケースでは助けになりません(ファイル名は、答えに明示的に記載されているように、任意の文字エンコーディングで復号不可能なバイトシーケンスです)。PEP 383 )2- asciiはここで動作します(Pythonでサポートされているロケールでwcによって出力された数字をデコードするため) – jfs

関連する問題