2013-05-03 46 views
3

我必須寫一個程序使用此命令行:什麼方式,我必須指定argparse.FileType追加,保持 - 作爲默認

demo.py [-h] -f FILENAME [-o] 

的文件名是強制性的,意味着該文件中,我們可以追加至。 -o標誌表示該文件將被覆蓋。

這argparse代碼幾乎工作:

import argparse 

parser = argparse.ArgumentParser(description='A foo that bars') 

parser.add_argument("-f", 
        "--file", dest="filename", required=True, 
        type=argparse.FileType('a+'), 
        help="The output file (append mode, see --overwrite).") 

parser.add_argument("-o", 
        "--overwrite", dest="overwrite", 
        action='store_true', 
        help="Will overwrite the filename if it exists") 

args = parser.parse_args() 

if args.overwrite: 
    args.filename.truncate(0) 

print >> args.filename, 'Hello, World!' 

但是,如果我指定-(標準輸出)作爲文件名,我得到這個錯誤:

error: argument -f/--file: invalid FileType('a+') value: '-' 

我試圖ar+,我得到的同樣的錯誤。我在Windows上使用Python 2.7,但它也必須在Linux上工作。對於傳統支持,命令行不能更改。

我怎樣才能保持​​內置支持stdout速記,但支持覆蓋功能?

回答

3

argparse.FileType.__call__包含此代碼:

if string == '-': 
     if 'r' in self._mode: 
      return _sys.stdin 
     elif 'w' in self._mode: 
      return _sys.stdout 
     else: 
      msg = _('argument "-" with mode %r') % self._mode 
      raise ValueError(msg) 

所以,如果self._mode'a+',Python會引發一個ValueError。 你可以通過子分類argparse.FileType

import argparse 
import sys as _sys 

class MyFileType(argparse.FileType): 

    def __call__(self, string): 
     # the special argument "-" means sys.std{in,out} 
     if string == '-': 
      if 'r' in self._mode: 
       return _sys.stdin 
      elif any(m in self._mode for m in 'wa'): 
       return _sys.stdout 
      else: 
       msg = _('argument "-" with mode %r') % self._mode 
       raise ValueError(msg) 

     # all other arguments are used as file names 
     try: 
      return open(string, self._mode, self._bufsize) 
     except IOError as e: 
      message = _("can't open '%s': %s") 
      raise ArgumentTypeError(message % (string, e)) 


def parse_options(): 
    parser = argparse.ArgumentParser(description='A foo that bars') 

    parser.add_argument("-f", 
         "--file", dest="filename", required=True, 
         type=MyFileType('a+'), 
         help="The output file (append mode, see --overwrite).") 

    parser.add_argument("-o", 
         "--overwrite", dest="overwrite", 
         action='store_true', 
         help="Will overwrite the filename if it exists") 

    args = parser.parse_args() 

    if args.overwrite: 
     args.filename.truncate(0) 
    return args 

args = parse_options() 
print >> args.filename, 'Hello, World!' 
相關問題