扫码阅读
手机扫码阅读

odoo框架源码研读一:前后端交互

448 2023-09-06

1 源码文件结构

odoo14.0源码结构如下:

.
|-- CONTRIBUTING.md
|-- COPYRIGHT
|-- LICENSE
|-- MANIFEST.in
|-- README.md
|-- SECURITY.md
|-- addons
|-- debian
|-- doc
|-- odoo
|-- odoo-bin
|-- requirements.txt
|-- setup
|-- setup.cfg
`-- setup.py

doc文件夹下是项目的帮助文档。

odoo-bin文件是odoo的启动脚本,配合自定义的odoo.conf配置文件用来启动项目。

odoo是odoo的底层模块,包含项目的基础父类,以及项目启动需要的基础类。

addons中包含了odoo的基础业务模块,包括CRM、Sales等模块。

2 框架结构

经历了六个月的odoo学习与实战,基于笔者对odoo前后端交互的理解。

2.1 前后端交互

odoo的前端基础框架以及和后台基础模块交互的API都封装在了addons下的web模块。

2.1.1 Controller控制器

odoo是通过controller控制器来控制前后台的交互,然后又根据功能的不同划分成了多个控制器,从下图中每个controller的命名中了解各自对应的功能模块。

这些controller继承了base模块中的Controller基类,并通过http.route装饰器的注解将controller中的方法标记为请求处理器,变成对外暴露的API接口,接收并处理http请求。关于http.route的详细介绍,源码中有详细的注释。此处以基础业务模块的controller控制器DataSet查询列表数据接口search_read为例:

http.route
type enum description
string/array
请求分发映射对应的方法
string http/json request类型
string user/public/none 认证方法类型
string GET/POST 请求类型
string
The Access-Control-Allow-Origin cors directive value
bool
是否启用CSRF防御

2.1.2 Dispatcher分发模块

通过调试代码,整理请求在到达controller之前的处理流程如下:

Root

Root是odoo的WSGI根应用,会在项目启动的时候创建。
请求到达odoo后,会被Root接收,并调用dispatch方法。


root在dispatch方法处理流程:

  1. 获取werkzeug中的原始request对象。

  2. 然后设置上下文环境,包括将状态绑定线程、设置session、数据库、语言等

root在设置db的时候会根据db_filter配置参数去获取匹配的数据库信息,如果唯一,那么进入系统登陆页面的时候session中会带有db,反之进入系统时session中不会带有db,并会进入数据库选择页面,选择之后才是登陆页面,登陆时会把选择的数据库信息设置到session中,以保证后面的请求都会通过IrHttp映射器分映射发请求到对应的方法。

然后通过get_request方法将request对象封装成HttpRequest或者JsonRequest

通过判断session是否带有db数据库名称,调用不同的分发逻辑,如果db值为空就会跳转到选择数据库的界面,否则会调用IrHttp请求映射器进行dispatch。

IrHttp

源码中对IrHttp的描述是"HTTP Routing"或者是"Routing map"。

请求在到了IrHttp._dispatch()后,做了如下操作:

  1. 根据请求中的path作为key去routeing_map中匹配对应的路由信息(方法、参数等)。

根据获取到的路由信息中的auth去进行权限校验

根据获取的路由信息以及校验信息封装requestHandler

调用request的dispatch方法

HttpRequest/JsonRequest

请求在到了HttpRequest/JsonRequest的dispatch方法后,都通过父类WebController的__call_function()方法根据在IrHttp时已经封装好的entpoint路由信息,路由到对应的controller中的接口方法。除此之外,HttpRequest在call_function之前还校验了csrf_token,而JsonHttp则是根据配置打印debug日志,以及返回结果封装json_response。

至此,请求就顺利的到达了Controller控制器。
关于HttpRequest和JsonRequest,两者都继承了同一个父类WebRequest,可以看出两者都具有处理异常、分发请求的功能,相比于JsonRequest,HttpRequest多了是否校验cors、渲染html和处理404请求的功能,而JsonRequest则多了封装json_response的功能。具体对比如下:


_request_type
参数类型
返回值
HttpRequest
http
请求路径参数pathParam;请求参数queryParm;form表单;
空内容;werkzeug Response 对象;字符串或者编码;
JsonRequest
json
JSON object
JSON-RPC

本篇就先讲到这里,下面一篇文章将会向大家介绍odoo的ORM。

原文链接: http://mp.weixin.qq.com/s?__biz=Mzg5MzUyOTgwMQ==&mid=2247486205&idx=1&sn=b97051051845907fbdb3375cb120c22f&chksm=c02c315bf75bb84db36beb9618ee3cc845691a219c315c5888c4cbdf1f1e9e243e8178199509#rd