在config.py中提供全局配置变量的大多数Pythonic方法? [英] Most Pythonic way to provide global configuration variables in config.py?

查看:114
本文介绍了在config.py中提供全局配置变量的大多数Pythonic方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在对过于简单的东西的无尽追求中,我正在研究在Python egg软件包中典型的 config.py 中提供全局配置变量的'Pythonic'方法。
$ b 传统的方式(aah,good ol'#define !)如下所示:

  MYSQL_PORT = 3306 
MYSQL_DATABASE ='mydb'
MYSQL_DATABASE_TABLES = ['tb_users','tb_groups']

因此,可以通过以下方式之一导入全局变量:

  from config import * 
dbname = MYSQL_DATABASE
for MYSQL_DATABASE_TABLES:
print table

或:

$ p $ 导入配置
dbname = config.MYSQL_DATABASE
assert(isinstance(config.MYSQL_PORT,int))

它是有道理的,但有时可以是有点混乱,特别是当你试图记住某些变量的名字时。此外,提供一个'配置'对象变量作为属性可能更加灵活。所以,从 bpython config.py文件中领先,我想出了:

  class Struct (object):
$ b $ def __init __(self,* args):
self .__ header__ = str(args [0])如果其他参数无

def __repr__ (self):
if self .__ header__ is None:
return super(Struct,self).__ repr __()
return self .__ header__

def next(self ):
假迭代功能

提升StopIteration

def __iter __(self):
假迭代功能
我们跳过魔术属性和结构,然后返回其余的

ks = self .__ dict __。keys()
for k in ks:
如果不是k.startswith('__')而不是isinstance(k,Struct):
yield getattr(self,k)

def __len __(self):
不要统计魔术属性或结构。

ks = self .__ dict __。keys()
return len([k for k in ks if k.startswith('__')\
and not isinstance(k,Struct)])

和一个导入类的'config.py',内容如下:

  from _config导入Struct作为Section 
$ b $ mysql = Section(MySQL特定配置)
mysql.user = 'root'
mysql.pass ='secret'
mysql.host ='localhost'
mysql.port = 3306
mysql.database ='mydb'

mysql.tables = Section(mydb'的表)
mysql.tables.users ='tb_users'
mysql.tables.groups ='tb_groups'

并以这种方式使用:

 导入配置为CONFIG 

assert(isinstance(CONFIG.mysql.port,int))

mdata = MetaData
mysql://%s:%s @%s:%d /%s%(
CONFIG.mysql.user,
CONFIG.mysql.pass,
CONFIG.mysql.host,
CONFIG.mysql.port,
CONFIG.mysql.database,



tables = []
在CONFIG.mysql.tables中的名称:
tables.append(表(名称,mdata,autoload = True))



这似乎是一个更具可读性,表达性和灵活性的方式来存储和获取包中的全局变量。



有史以来最蠢的想法?应对这些情况的最佳做法是什么?什么是你的方式来存储和获取你的包中的全局名称和变量?

解决方案

那一次。最终,我发现我的简化 basicconfig.py 足以满足我的需求需要。如果需要,您可以传入其他对象的名称空间以供它参考。您也可以传入代码中的其他默认值。它还将属性和映射样式语法映射到相同的配置对象。

In my endless quest in over-complicating simple stuff, I am researching the most 'Pythonic' way to provide global configuration variables inside the typical 'config.py' found in Python egg packages.

The traditional way (aah, good ol' #define!) is as follows:

MYSQL_PORT = 3306
MYSQL_DATABASE = 'mydb'
MYSQL_DATABASE_TABLES = ['tb_users', 'tb_groups']

Therefore global variables are imported in one of the following ways:

from config import *
dbname = MYSQL_DATABASE
for table in MYSQL_DATABASE_TABLES:
    print table

or:

import config
dbname = config.MYSQL_DATABASE
assert(isinstance(config.MYSQL_PORT, int))

It makes sense, but sometimes can be a little messy, especially when you're trying to remember the names of certain variables. Besides, providing a 'configuration' object, with variables as attributes, might be more flexible. So, taking a lead from bpython config.py file, I came up with:

class Struct(object):

    def __init__(self, *args):
        self.__header__ = str(args[0]) if args else None

    def __repr__(self):
        if self.__header__ is None:
             return super(Struct, self).__repr__()
        return self.__header__

    def next(self):
        """ Fake iteration functionality.
        """
        raise StopIteration

    def __iter__(self):
        """ Fake iteration functionality.
        We skip magic attribues and Structs, and return the rest.
        """
        ks = self.__dict__.keys()
        for k in ks:
            if not k.startswith('__') and not isinstance(k, Struct):
                yield getattr(self, k)

    def __len__(self):
        """ Don't count magic attributes or Structs.
        """
        ks = self.__dict__.keys()
        return len([k for k in ks if not k.startswith('__')\
                    and not isinstance(k, Struct)])

and a 'config.py' that imports the class and reads as follows:

from _config import Struct as Section

mysql = Section("MySQL specific configuration")
mysql.user = 'root'
mysql.pass = 'secret'
mysql.host = 'localhost'
mysql.port = 3306
mysql.database = 'mydb'

mysql.tables = Section("Tables for 'mydb'")
mysql.tables.users = 'tb_users'
mysql.tables.groups =  'tb_groups'

and is used in this way:

from sqlalchemy import MetaData, Table
import config as CONFIG

assert(isinstance(CONFIG.mysql.port, int))

mdata = MetaData(
    "mysql://%s:%s@%s:%d/%s" % (
         CONFIG.mysql.user,
         CONFIG.mysql.pass,
         CONFIG.mysql.host,
         CONFIG.mysql.port,
         CONFIG.mysql.database,
     )
)

tables = []
for name in CONFIG.mysql.tables:
    tables.append(Table(name, mdata, autoload=True))

Which seems a more readable, expressive and flexible way of storing and fetching global variables inside a package.

Lamest idea ever? What is the best practice for coping with these situations? What is your way of storing and fetching global names and variables inside your package?

解决方案

I did that once. Ultimately I found my simplified basicconfig.py adequate for my needs. You can pass in a namespace with other objects for it to reference if you need to. You can also pass in additional defaults from your code. It also maps attribute and mapping style syntax to the same configuration object.

这篇关于在config.py中提供全局配置变量的大多数Pythonic方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆