对如何写一个工业级的Python项目作一个top-down小结。
一、项目结构
顶层结构:
文件夹:
- model可以是项目中的自定义类;
- utils是一些工程工具,比如log,tracker
- log存放记录的日志
py文件:
- run:主文件,项目的顶层逻辑;
- settings:run文件中的常量(用作设置);
二、package(包)
__init__.py作用:
当文件夹下有__init__.py时,表示当前文件夹是一个package,其下的多个module统一构成一个整体。
模糊导入:
from Root.Pack1 import *
模糊导入中的*中的模块是由__all__来定义的,__init__.py的另外一个作用就是定义package中的__all__,用来模糊导入,如__init__.py:
__all__ = ["Pack1Class","Pack1Class1"]
或者
__all__ = ['file1','file2'] #package1下有file1.py,file2.py
借助__init__.py可以:将子文件中的类名导入到包名下
例如websocket包:websocket.WebSocketApp,外部在import的时候可以看到所有写在__init__.py文件中的类名
websocket包__init__.py文件内容:
websocket包_app.py中
三、类
如何写callback(回调函数):
1.在声明处,将用于挂接外部函数的形参写成带默认参数的形式,比如on_message=None:
def init(self, url, header=None, on_open=None, on_message=None, on_error=None, on_close=None, on_ping=None, on_pong=None, on_cont_message=None, keep_running=True, get_mask_key=None, cookie=None, subprotocols=None, on_data=None): """ url: websocket url. header: custom header for websocket handshake. on_open: callable object which is called at opening websocket. this function has one argument. The argument is this class object. on_message: callable object which is called when received data. on_message has 2 arguments. ... """
2. 类中需定义调用函数,检测外部函数能否正常使用:
def _callback(self, callback, *args): if callback: try: callback(self, *args) except Exception as e: _logging.error("error from callback {}: {}".format(callback, e)) if _logging.isEnabledForDebug(): _, _, tb = sys.exc_info() traceback.print_tb(tb)
3. 调用时,通过定义的_callback来调用外部函数API
self._callback(self.on_message, data)
给self绑定一个新属性:
Python由于是动态语言,可以自由地绑定新属性。但在类的方法中需要用hasattr检查是否已存在,防止多次绑定。
if not hasattr(self, 'flop_strategy'):
self.flop_strategy = FlopStrategy()