Pythonconfiguration文件:任何文件格式build议? INI格式还合适吗? 看起来很老派
我需要为Python应用程序存储configuration(键/值),我正在寻找将这些configuration存储在文件中的最佳方法。
我遇到了Python的ConfigParser ,我想知道现在INI文件格式是否真的还适合? 是否存在更新的格式或INI仍然是推荐的方式? (XML,JSON,…)
请分享您的意见/build议…
考虑使用普通的Python文件作为configuration文件。
一个例子( example.conf
):
# use normal python comments value1 = 32 value2 = u"A unicode value" value3 = "A plain string value" value4 = ["lists", "are", "handy"] value5 = {"and": "so", "are": "dictionaries"}
在你的程序中,使用execfile
( 2.7 docs )加载configuration文件:
if __name__ == "__main__": config = {} execfile("example.conf", config) # python 3: exec(open("example.conf").read(), config) print config["value1"] print config["value5"]
我喜欢这种方法,原因如下:
- 在简单的情况下,格式和INI风格的configuration文件一样容易编写。 它也与INI文件共享一个重要的特性:它非常适合版本控制(对于XML而言也是如此,也可能是JSON)
- 我喜欢用实际编程语言来configuration文件的灵活性。
该方法被广泛使用,举几个例子:
- Django网站的设置位于settings.py中 。 Django不使用
execfile
,它使用import
来读取/执行settings.py
AFAIK,但最终结果是一样的:设置文件里的代码被执行。 - bash shell在启动时读取并执行
~/.bashrc
。 - Python解释器在启动时导入(并执行)
site.py
。
INI是完全可以的,正如其他人所说,你的configuration文件的格式真的取决于你将如何使用它。
我个人是YAML的粉丝:简洁,可读,灵活。
谷歌似乎分享我的热情,因为他们也在谷歌应用程序引擎中使用它。 Pythonparsing器在这里 。
字典也很受欢迎。 基本上是一个哈希表。
{"one": 1, "two": 2}
就是一个例子,看起来像json。
然后你可以把它mydict["one"]
,它会返回1。
然后你可以使用shelve将字典保存到一个文件中:
mydict = shelve.open(filename) # then you can call it from there, like mydict["one"]
所以,这比ini文件要容易一些。 你可以像列表一样添加东西,或者很容易地更改选项,然后一旦closures它就会将其写回。
下面是我的意思的简单例子:
import shelve def main(): mydict = shelve.open("testfile") mydict["newKey"] = value("some comment", 5) print(mydict["newKey"].value) print(mydict["newKey"].comment) mydict.close() class value(): def __init__(self, comment, value): self.comment = comment self.value = value if __name__ == '__main__': main()
这完全取决于你的要求。 如果(如你所说)所有你需要的是键/值对,ini文件(或其他“普通”configuration文件)将完全适合你。 不,他们还没有过时,因为他们仍在使用。
XML / JSON是完美的,如果你有层次结构,也想使用更复杂的方法(例如:XML文件validation,命名空间等)。
看看ConfigObj ,它到目前为止我发现的最尖端的方法,肯定比ConfigParser更灵活。 就我个人而言,我不是YAML的粉丝,因为它的“灵活性”使得像Augeas这样的工具很难使用。
这取决于如何使用configuration文件。
INI文件的优点之一是它们很容易阅读和理解。 如果您手动编辑configuration,则在JSON或XML文件中犯错很容易。 PHP仍然使用INI文件。
但是,如果你的configuration不是用手来编辑的,可以用你喜欢的任何格式,因为INI不是最容易parsing的。
为了完整性,您还可以在“shlex”模块的帮助下使用shell风格的configuration格式。 如果你有一套固定的configuration参数,那么你可以把它和“optparse”模块结合起来。
from optparse import OptionParser _o = OptionParser("%prog [options] configfiles...") _o.add_option("--hostname", metavar="HOSTNAME", default="10.0.0.1") _o.add_option("--username", metavar="USERNAME", default="admin") _o.add_option("--password", metavar="PASSWORD", default="admin") import shlex def parse(filename, defaults): opt, args = _o.parse_args(shlex.split(open(filename).read()), defaults) return opt if __name__ == "__main__": import sys values, args = _o.parse_args() for arg in args: values = parse(arg, values) values, args = _o.parse_args(values = values) for name in _o.defaults: print name, "=", getattr(values, name)
该示例显示了如何链接ini文件以获取默认的一组值和用户定义的重定义。 所以假设你有两个文件包含
file1.ini:
--hostname 10.2.3.4 --password admin-sc
file2.ini:
--username "foo bar" --password "special key"
然后你可以运行./configtest.py file1.ini file2.ini --password other
,结果值的主机./configtest.py file1.ini file2.ini --password other
,用户名为“foo bar”,密码为“other”。 如果你的程序参数已经有一个optparse-definition,那么这个configuration设置的变化就派上用场了 – 只要重新使用它,你就可以将命令行中的值与configuration文件中的值以及可能的全局configuration设置链接起来。
作为一种激励,你的configuration参数总是被logging下来,错误的configuration参数会很早出现,就像你可以使用optparse-instance预先检查你的默认设置文件(模式检查)一样。 作为缺点,ini中没有允许的注释,configuration元素不容易被子结构化。尽pipe如此,你的parsing器本质上是一个线性的。