2013-03-11 77 views
0

我有一個bash片段,我想移植到Python。它發現SVN的位置以及它是否可執行。如何在Python中使用這個bash測試構造?

SVN=`which svn 2>&1` 
if [[ ! -x $SVN ]]; then 
    echo "A subversion binary could not be found ($SVN)"   
fi 

下面是一個使用子模塊在Python我當前的嘗試:

SVN = Popen('which svn 2>&1', shell=True, stdout=PIPE).communicate()[0] 
Popen("if [[ ! -x SVN ]]; then echo 'svn could not be found or executed'; fi", shell=True) 

這不,因爲雖然我有SVN的位置保存在Python的本地命名空間的工作,我可以」從Popen訪問它。

我也試圖組合成一個POPEN對象:

Popen("if [[ ! -x 'which svn 2>&1']]; then echo 'svn could not be found'; fi", shell=True) 

,但我得到這個錯誤(不用說,看起來很笨重)

/bin/sh: -c: line 0: syntax error near `;' 
/bin/sh: -c: line 0: `if [[ ! -x 'which svn 2>&1']]; then echo 'svn could not be found'; fi' 

有一個測試的Python版本構造「-x」?我認爲這將是理想的。其他解決方法也將受到讚賞。

由於

+1

[此網站](http://ubuntuforums.org/showthread.php?t=1457094)提供了一個代碼段,看起來像'commands.getoutput(「如果[-x MYFILE] \ n然後回聲真\ NFI「)'。然而,由於您仍在調用Bash,因此這很難「移植到Python」。 – Kos 2013-03-11 07:14:04

+1

'os.stat'可以給你關於給定文件的一些信息,比如它的權限,但是我認爲你仍然需要爲它建立一個「可執行的當前用戶」測試。 – Kos 2013-03-11 07:16:17

+1

您可以先將bash命令存儲爲字符串,以便您可以將它與變量SVN連接起來?然後將其傳遞給Popen()... – Jeff 2013-03-11 07:16:58

回答

1
SVN = Popen('which svn 2>&1', shell=True, stdout=PIPE).communicate()[0] 
str="if [[ ! -x " + SVN + " ]]; then echo 'svn could not be found or executed'; fi" 
Popen(str, shell=True) 
+1

這是非常低效的,它分叉了很多,並且讓殭屍進程四處流竄。 – LtWorf 2013-03-11 08:08:14

4

這是最簡單的解決方案:

path_to_svn = shutil.which('svn') 
is_executable = os.access(path_to_svn, os.X_OK) 

shutil.which是在Python 3.3新; this answer中有一個polyfill。如果你真的想要,你也可以從Popen中獲取路徑,但這不是必需的。

這裏是os.access的文檔。

+0

'os.access()'是多餘的。 'shutil.which()'默認已經檢查'X_OK'。 – jfs 2013-03-13 04:11:14

1

沒有必要使用哪一個,你可以嘗試運行svn而無需參數,如果它工作,這意味着它在那裏。

try: 
    SVN = subprocess.Popen('svn') 
    SVN.wait() 
    print "svn exists" 
except OSError: 
    print "svn does not exist"