OD217 parent-store-without-path¶
A model sets _parent_store without an indexed parent_path field.
| Category | Severity | Series | Needs the index |
|---|---|---|---|
| Correctness | Error | all | yes |
What it reports¶
A class that sets _parent_store = True on a model with no parent_path field, or whose
parent_path field is not indexed: it gives no index, or index=False. Any other literal
index, such as "btree", counts as an index. A model is reported once per module, at the first
of its classes that sets _parent_store.
Why it matters¶
With _parent_store, Odoo keeps the path of each record's ancestors in the parent_path column and
answers child_of and parent_of searches with a prefix match on it. When it creates or updates
the model's table, it adds the column if needed and logs an error when the model has no
parent_path field, or when the field has no index. Without the field, the ORM cannot read or
search the paths it stores; without the index, each hierarchy search scans the whole table. Before
saas~11.3, Odoo keeps the hierarchy in parent_left and parent_right instead, and the rule stays
silent on such a series. A module of unknown series is checked all the same, except a model that
holds a parent_left field, taken as a sign of such a series. So a leftover parent_left on a
later series hides a true finding, and a model on an earlier series without the field gets a false
one: pass --odoo-version to settle both.
A model without a table of its own is left alone: an abstract model, or one with a class that sets
_auto = False. So is a model with a class that sets _parent_store to anything but True, or
an index that is not a literal. The field takes its index from the last definitions that set
it, and is unknown when those disagree, as two definitions in different files of one module may:
files load in the order of the imports, which is not indexed.
The rule does not run for a module when the module or one of its dependencies depends on a module
that is not indexed. A model is skipped when the class that introduces it, with _name or as a
class Odoo names, is in a module outside the dependencies, or when a class of it, or of a model it
inherits or delegates to, has a plain Python base class or an _inherit element that is not a
literal, a parent whose fields the scan cannot see. A module that Odoo always installs with base,
such as web, counts as in depends.
Example¶
class ParcelZone(models.Model):
_name = "parcel.zone"
_description = "Parcel zone"
_parent_store = True
name = fields.Char()
parent_id = fields.Many2one("parcel.zone", ondelete="cascade")
class ParcelZone(models.Model):
_name = "parcel.zone"
_description = "Parcel zone"
_parent_store = True
name = fields.Char()
parent_id = fields.Many2one("parcel.zone", ondelete="cascade")
parent_path = fields.Char(index=True)