filterable_selection
One selection field, different choices per view: filterable_selection filters a selection's dropdown with a whitelist, a blacklist, or a list read live from another field on the record, without touching the model.
| Technical name | filterable_selection |
|---|---|
| Field types | selection, many2one (inherited from the selection field) |
| Views | form, list |
| Module | web, present in every Odoo database |
| Used in core | 5 occurrences across 4 modules, including hr, loyalty, hr_holidays_attendance, account_edi_ubl_cii |
| Versions | Odoo 20.0, Odoo 19.0, Odoo 18.0, Odoo 17.0, Odoo 16.0 |
| No-code setup | No: the filter options are XML only |
| Alternatives | selection, dynamic_selection, selection_badge |
What the Filterable Selection widget does
What this means for your team
Supported options in Odoo 19
| Option | Type | What it does |
|---|---|---|
whitelisted_values | list of selection keys | Only these values are offered in the dropdown, plus the record's current value if it falls outside the list. Ignored when whitelist_fname is set. |
blacklisted_values | list of selection keys | These values are removed from the dropdown; everything else stays. Lowest precedence: ignored when either whitelist option is set. |
whitelist_fname | field name | Names a field on the current record whose value is the list of allowed keys, letting the filter change per record. Highest precedence of the three. The field must be loaded in the view; an empty or missing value offers only the current value.(since Odoo 18.0) |
The three options do not combine. The source checks them in an if/else-if chain: if whitelist_fname is set the other two are ignored, and whitelisted_values shadows blacklisted_values. Pick exactly one strategy per view. And in every case the record's current value stays selectable-looking in the dropdown, by design.
Working examples
From loyalty hack to core widget
Version compatibility
| Version | Status | Notes |
|---|---|---|
| Odoo 20.0 | In development | Not released. Functionally unchanged on the development branch; internal props-schema rework only. |
| Odoo 19.0 | Verified | Verified against the shipped source; byte-identical to 18.0. |
| Odoo 18.0 | Verified | Adds whitelist_fname. |
| Odoo 17.0 | Partial / changed | In web core with whitelisted_values and blacklisted_values only. |
| Odoo 16.0 | Partial / changed | Exists inside the loyalty module only, with whitelist and blacklist; requires loyalty installed. |
Upgrade note. Views written for 16 must change the import context: the widget name is the same, but in 16 it only exists with the loyalty app installed, while 17+ ships it in web core. whitelist_fname in views deployed on 17 will be silently ignored, so gate that option on 18+.
What is changing in Odoo 20
Common problems and fixes
| Symptom | Cause and fix |
|---|---|
| A value you excluded still shows in the dropdown | It is the record's current value; the widget always keeps it visible so existing data renders. That is by design. Migrate the stored values if the choice should truly disappear. |
| Combining a whitelist and a blacklist only applies one of them | The options are checked in an if/else-if chain: whitelist_fname, then whitelisted_values, then blacklisted_values. Use a single strategy; express the combined rule as one whitelist. |
| whitelist_fname seems to be ignored | The referenced field is not loaded in the view, or you are on Odoo 17 where the option does not exist. Add the field to the view (invisible works) and confirm the version is 18 or later. |
| Excluded values keep appearing in the data anyway | The filter is UI-only; imports, RPC calls and other views can still write any selection value. Back the rule with a Python constraint or selection restriction on the model. |
| Changing the value on a kanban card saves the whole record instantly | Inherited from the base selection widget, which hardcodes autosave in kanban views. Expected behavior; edit from the form view when you want staged changes. |
Filterable Selection widget vs the alternatives
| Widget | Best for | Key difference |
|---|---|---|
filterable_selection | One selection field offering different choices per view or record | Filters the dropdown with whitelist, blacklist or a record-driven list; current value always survives |
| selection | The plain dropdown with every defined value | No filtering; the base widget this one extends |
| dynamic_selection | Choice lists maintained as data rather than code | Values come from records, not from filtering a static selection |
| selection_badge | Showing all values as clickable badges | Displays the full set for one-click switching instead of hiding any |
Frequently asked questions
How do I hide some selection values in one Odoo view only?+
Can the allowed values depend on the record?+
Why is the current value shown even though I blacklisted it?+
Does filterable_selection prevent bad values from being saved?+
Which option wins if I set several?+
Where does core Odoo use this widget?+
Same Odoo, different rules per team?
Operators who see three states, managers who see five, and a model that stays clean underneath: that is view engineering, and it is what keeps a shared Odoo usable as you grow. We design per-role views with filtered choices, computed guards and the Python constraints that back them up.
Design our role-based views