如何使用fabric模块在远端实现文件字符串替换功能?

高手请指导下,用fabric模块+fileinput实现远端文本字符串替换,好像不能用run函数,上代码

from fabric.api import run,local,env
import sys
import os,re,time,fileinput

path = r'/etc/test.conf'
old = 'yes'
new = 'no'
r = r'^[^#].*enable-cache.*'

if len(sys.argv) != 3:
    print len(sys.argv)
    print 'Usage:python change_conf_batch.py --host hn.txt'
    sys.exit(0)
if sys.argv[1].startswith('--host'):
    hn = sys.argv[2]

def readsn():

    with open(hn) as f:
        while True:
            line=f.readline()
            if not line:
                break
            desthost = line.strip().lstrip().rstrip()
            env.host_string = desthost
            run('cp %s %s' %(path,path+time.strftime(r'%Y%m%d%H%M%S', time.localtime())))
            run(change_conf(path, old, new))

def change_conf(path,old,new):
    f = fileinput.input(path,backup='.bak',inplace=True)
    for line in f:
        line = line.rstrip()
        match = re.match(r,line)
        if match:
            print line.replace(old, new)
        print line
    f.close()

if __name__ == '__main__':
    readsn()

报错如下,在本地run是没问题的

run: cp /etc/test.conf /etc/test.conf20161116085212
Traceback (most recent call last):
  File "change_conf_batch.py", line 45, in <module>
    readsn()
  File "change_conf_batch.py", line 32, in readsn
    run(change_conf(path, old, new))
  File "/root/.pythonbrew/venvs/Python-2.7.10/flask/lib/python2.7/site-packages/fabric/network.py", line 677, in host_prompting_wrapper
    return func(*args, **kwargs)
  File "/root/.pythonbrew/venvs/Python-2.7.10/flask/lib/python2.7/site-packages/fabric/operations.py", line 1088, in run
    shell_escape=shell_escape, capture_buffer_size=capture_buffer_size,
  File "/root/.pythonbrew/venvs/Python-2.7.10/flask/lib/python2.7/site-packages/fabric/operations.py", line 914, in _run_command
    _prefix_env_vars(_prefix_commands(command, 'remote')),
  File "/root/.pythonbrew/venvs/Python-2.7.10/flask/lib/python2.7/site-packages/fabric/operations.py", line 670, in _prefix_commands
    return prefix + command
TypeError: cannot concatenate 'str' and 'NoneType' objects
    
阅读 3.6k
1 个回答

run函数的参数是字符串(要在远端运行的命令)。
下面这句是要执行change_conf函数的返回的命令,但由于change_conf没有return默认返回None,所以会出问题。

run(change_conf(path, old, new))

简单点可以直接在run中执行sed命令来做替换,run('sed -i "s/xxx/yyy/g" filename')。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题