簡體   English   中英

在 python 腳本中調用 IPtables 命令

[英]call IPtables command within python script

我正在嘗試在我的 python 腳本中調用以下命令。 我正在嘗試將規則插入到 IP 表中。 我正在使用子進程來調用它並在需要的地方插入變量,但是出現了一個大錯誤。 有什么建議么?

iptables = subprocess.call('iptables -I FORWARD -eth 0 -m '+protocol+' -t'+protocol+'--dport '+port+'-j DNAT --to-destination'+ipAddress)

錯誤:

Traceback (most recent call last):
  File "./port_forward.py", line 42, in <module>
    iptables = subprocess.call('iptables -I FORWARD -i eth0 -m '+protocol+' -t'+protocol+'--dport '+port+'-j DNAT --to-destination'+ipAddress)
  File "/usr/lib/python2.7/subprocess.py", line 493, in call
    return Popen(*popenargs, **kwargs).wait()
  File "/usr/lib/python2.7/subprocess.py", line 679, in __init__
    errread, errwrite)
  File "/usr/lib/python2.7/subprocess.py", line 1259, in _execute_child
    raise child_exception
OSError: [Errno 2] No such file or directory

您的問題對於 Python 初學者來說很常見。 您嘗試通過連接許多字符串和變量來構建復雜的字符串,而不是格式化字符串命令。 相反,使用字符串格式,它將允許您測試您的命令並使您的代碼更具可讀性和靈活性。

您的原始字符串在選項和參數之間缺少空格,例如--to-destination1.2.3.4

因此, 您應該格式化您的字符串(這也適用於 python 2.7):

opts = {'iptables': '/sbin/iptables', 'protocol': 'tcp', 'port': 80, 'ipAddress': '0.0.0.0'}
ipcmd = '{iptables} -I FORWARD -eth 0 -m {protocol} -t {protocol} \
--dport {port} -j DNAT --to-destination  {ipAddress}'.format(**opts)

if DEBUG:
   print ipcmd
iptables = subprocess.call(ipcmd)

這在以后修改起來要容易得多,而且,當您進行更多 Python 編程時,您會發現它更具可讀性。

此外,要調用 IPTables,您應該是 root,如評論中所述:在腳本的開頭添加:

   import sys
   import os
   if not os.getuid() == 0:
        print "You must be root to change IPTables."
        sys.exit(2)

看到錯誤跟蹤后更新:

您正在嘗試調用命令iptables但它不在您的路徑中。 您應該調用 iptables 的完整路徑,例如/sbin/iptables

我以同樣的方式編寫了一個簡單的防火牆並意識到,“為什么不直接用 bash 編寫它呢?”。 無論如何,我發現了 python-iptables 庫並使用它重寫了我的代碼。 我建議檢查一下。 我認為它會給你一種更健壯和結構化的方式來編寫 iptables 規則。

由於缺少空格,您的命令充滿了語法錯誤,如下所示:

iptables = subprocess.call(
     'iptables -I FORWARD -eth 0 -m '
   + protocol
   + ' -t'+protocol
         ^---here
   + '--dport '
      ^-- here
   + port
   + '-j DNAT --to-destination'
      ^--here
   + ipAddress)
     ^---here

生成后,您的 iptables 行將如下所示

-ttcp--dport 80-j DNAT  --to-destination1.2.3.4

-ttcp--dport被解析為單個參數, 80-j--to-destination1.2.3.4同上

只需將參數 shell=True 與命令一起傳遞即可。

iptables = subprocess.call('iptables -I FORWARD -eth 0 -m '+protocol+' -t'+protocol+'--dport '+port+'-j DNAT --to-destination'+ipAddress, shell=True)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM