Module Structure

Directories

Modules in Odoo have a predefined structure. Files of various categories must be kept in separate directories. Consequently, an Odoo module is organized into various directories. Those contain the business logic; looking at them should help you understand the module’s purpose.

1. controllers: includes the HTTP routes (python files).

2. data:  It contains the model data (XML file).

3. demo: Contains the module’s demo data (load if only the ‘load demo data’ is enabled).

4. doc: Contains the module documentation.

5. I18n: Contains the Translations.

6. models: It contains all models’ definitions and functions(python files)

7. report: Contains all report-related files(both python and XML files)

8. security: Contains files that specify record rules and CSV files for user permission.

9. static: contains the module’s web assets as well as subfolders for description, css/, js/, img/, lib/, etc.

10. tests: contains the files for the Python tests.

11. views: contains the definitions for the views and templates.

12. wizard:  contains the transient models and their views

14. __init__.py: To import the python directories (models, controllers, reports, ..,)

15. __manifest__.py: Core file of a module.

Not all directories are required. Depending on the module’s purpose, it might include the following. However, the outer “__init .py” and “__manifest .py” files are necessary in order to create a module. Place an empty outer “__init .py” file even if the module’s accompanying Python files are absent.

File Naming

In order to rapidly find information across all Odoo addons, file naming is crucial. This section covers how to name files in a normal Odoo module. We will use a school management application as an illustration. The school. class and school. students models are its two core models. As with models, divide the business logic into groups of models that are subsets of the same basic model. Each set is contained in a specific file with a name derived from its primary model. The model’s name is the same as the module name if there is just one model. To make it easier to comprehend how the inherited models are affected, each one should be in its own file.

While considering the security, three main files are included.

a) The first is an ir.model.access.csv file that defines access rights.

b) <module>_groups.xml contains definitions for user groups.

c) In <model>_security.xml, record rules are specified.

Backend views should be divided like models and prefixed with _views.xml when it comes to views. Templates (QWeb pages used notably for portal/website display) are specified as <model>_templates.xml.

Considering the data files, filenames will be the main model name suffixed by the _demo.xml and _data.xml. In terms of controllers, typically, every controller is a part of a single controller found in the file <module_name>.py. Odoo has a long-standing tradition of calling this file main.py, but this pattern is no longer followed.

If we need to inherit an existing controller from another module,  it can be done in <inherited_module_name>.py. For instance, using portal.py, a portal controller can be added to an application. While considering the static files, the Javascript files follow the same logic as the python models. Each component needs to be in its own file with a descriptive name. Additionally, subdirectories can be made to organize the “package”. The same reasoning ought to be used for the styles(scss files) and static XML file templates of JS widgets. Don’t link data (images, libraries) outside of Odoo: copy the data instead of using the URL to an image. The files in wizards are also named like the python models: <transient>.py and <transient>_views.xml. When it comes to Qweb reports, they may be divided into many categories, such as paper format and report actions.

The core file of an Odoo module is the __manifest .py file. It contains all information like a dictionary, including the name, version, author, dependencies, data, qweb, license, etc.

The ‘data’ key should be assigned to all view files in the module, and the ‘qweb’ key should include a list of all qweb views. Try to avoid empty keys while creating the manifest file. When adding a module’s version number, follow Odoo’s major version (16.0,15.0, etc.) with the module version numbers (1.0.0).

XML Files

There are many conventions to take into account while declaring a view or record in XML including the following:-

a) The record notation (using record>) should be used for all view records.

b) Place the id attribute before the model

c) Only non-updatable data with noupdate=1 is set using the tag “data.” The noupdate=1 attribute can be placed on the <odoo> tag, and there need not be a <data> tag if the file contains exclusively non-updatable data.

d) The name attribute comes first in the field declaration. The value should then be entered either in the field tag or using the eval attribute, followed by additional attributes (widget, options, etc.) in ascending order of significance.

Odoo supports custom tags that serve as syntactic sugar:

a) menu item: use this to quickly declare ir.ui.menu

b) template: to declare a QWeb View that only needs the view’s arch section.

These tags are preferred over the record notation.

XML IDs and naming

Security, View, and Action

In Odoo, we use the following patterns:-

a) For the menu: <model_name>_menu and <model_name>_menu_do_stuff for the submenus

b) <model_name>_view_<view_type> is the format for views, where view_type is a tree, kanban, form, search, etc.

c) The main action respects the <model_name> action for an action. Others are suffixed with _<detail>, where detail is a lowercase string that briefly describes the action. This is only used if the model has numerous actions declared.

d) For window actions, suffix the name of the action by the specific view information like <model_name>_action_view_<view_type>.

e) When considering a group <module_name>_group_<group_name> will be the format. Where a group_name is the name of the group like a user, manager, etc.

f) For a rule, use the format: “<model_name>_rule_<concerned_group>,” where the concerned group is the short name of the concerned group (e.g., “user” for the “model name group user,” “public” for users who may see the rule publicly, “company” for rules that apply on multi-company, etc.).

Dots should be used in place of underscores in the name to match the XML id. Action names should be real because they are displayed.

Inheriting XML

The original record’s ID should be used in the XML identifiers of inheriting views. It facilitates quickly locating every inheritance. There is no overlap because final XML Ids are prefixed by the module that generates them.

A .inherit.{details} suffix should be included in the name to make it easier to grasp the overriding goal from the name alone.

Source: Coding Guidelines in Odoo ERP