Skip to main content
iVentureTeam

lead_days_widget

The lead time breakdown on a reordering rule: supplier delay, purchase security, warehouse handling, all added up. It is a server-computed JSON payload rendered by a five line widget.

Siddharth JambukiyaSiddharth JambukiyaOdoo Techno-Functional Consultant
August 27, 2026Updated September 7, 20265 min read
Technical namelead_days_widget
Field typeschar
Viewsform
Modulestock, the Inventory app
Used in core1 occurrence, the replenishment information dialog in stock
VersionsOdoo 20.0, Odoo 19.0, Odoo 18.0, Odoo 17.0, Odoo 16.0
No-code setupNo. The payload has to be computed server side
Alternativesreplenishment_graph_widget, popover_widget, html, forecast_widget

What the lead days panel does

When Odoo decides when to reorder a product, it adds up several delays: how long the supplier takes, the security days you add on top, the time the warehouse needs to receive and put away, and any purchase lead time configured globally. The result is a single number that drives the reordering date, and on its own it explains nothing.

The replenishment information dialog breaks that number down, and this widget renders the breakdown. The server computes the components and their total into a JSON payload, stores it in a text field, and the widget parses it and hands it to a template.

That is genuinely all it does. The widget is five lines: a template name and a shared base that parses the field. Everything a user sees, the labels, which components are present and how they add up, is decided in Python.

What this means for your team

Reordering rules are trusted only when people can see why they fire when they do. A buyer who thinks the system orders too early, or too late, is usually reacting to a lead time component they did not know was configured, most often the security days or a warehouse handling delay.

Putting the breakdown in front of them turns that from an argument into a configuration conversation. It is also the fastest way to audit a supplier setup: if the supplier delay is wrong, it shows here rather than in a report nobody runs.

For anyone building similar explanations, the pattern is worth copying. Computing a small JSON payload server side and rendering it with a minimal widget keeps all the business logic in Python, where it can be tested, and keeps the browser side trivial.

Working examples

The core usage

<field name="json_lead_days" nolabel="1"
       colspan="2" widget="lead_days_widget"/>

No options. The field holds the JSON the server computed for that replenishment rule.

What the field has to contain

{
  "lead_days_date": "2026-09-14",
  "lead_days_description": "...",
  "...": "whatever the template reads"
}

The exact keys are the template's contract with the server-side computation, not something the widget imposes.

Its sibling in the same file

<field name="json_replenishment_graph"
       widget="replenishment_graph_widget"/>

Built on the same base, rendering a chart instead of a panel.

Five lines on a very thin base

The shared base is worth describing because two widgets depend on it and neither adds much. It is a component with the standard field props, an empty template name, and a single getter that parses the field's value as JSON. The descriptor gives it a display name and declares a single supported type.

Each concrete widget then supplies its own template name and, in the graph's case, a lot of chart code. This one supplies only a template name, which is why the file's Lead Days section is five lines long.

Two consequences follow from the base being this thin. There is no error handling: an empty field, a null, or a malformed string all raise from the parse, so the calling view has to guarantee the payload. And the getter re-parses on every access, so the panel does follow a recomputed value, unlike several other JSON-driven widgets in Odoo that parse once at setup.

The registration style is the only thing that has moved across versions. Odoo 16 registered the component class directly, which meant the declared type and display name were attached to the class; Odoo 17 introduced the descriptor object still used today. Neither change affects views.

Version compatibility

VersionStatusNotes
Odoo 20.0In developmentNot released. The Lead Days part of the file is unchanged on the development branch.
Odoo 19.0VerifiedVerified against the shipped source.
Odoo 18.0VerifiedIdentical behavior.
Odoo 17.0VerifiedIdentical behavior. This is where the descriptor registration was introduced.
Odoo 16.0VerifiedSame behavior, with the component class registered directly.

Upgrade note. Nothing to do. The widget has existed since Odoo 16 and the only change is the registration style introduced in Odoo 17. What did change around it is its sibling: the replenishment history widget in Odoo 16 through 18 was replaced by a graph widget in Odoo 19.

What is changing in Odoo 20

Odoo 20 is expected at Odoo Experience in Brussels, 24 to 26 September 2026. The development branch is unstable and this may still change; we re-verify the page after release.

Unchanged. The Lead Days part of the file is identical on the development branch. The changes in that file all belong to the graph widget, which moves to a shared chart hook.

Common problems and fixes

SymptomCause and fix
An error about parsing JSONThe field is empty or malformed, and the base parses it without a guard. Make sure the server computes the payload before the view renders the field.
The panel is emptyThe payload parsed but contains none of the keys the template reads. Check the server-side computation; the widget imposes no keys of its own.
Options are ignoredThe descriptor has no extractor, so nothing in the options dictionary is read. Nothing to configure here.
The widget will not attach to my fieldIt declares a single supported type. Store the payload in a character field, as core does.
Missing widget errorThe inventory module is not installed in that database. Install Inventory.

Lead days panel vs the alternatives

WidgetBest forKey difference
lead_days_widgetExplaining a computed lead time as a breakdown of its partsA five line widget over a shared JSON base, with all the content decided server side
replenishment_graph_widgetThe stock curve in the same dialogBuilt on the same base, renders a chart instead of a panel
popover_widgetA JSON-driven note behind an iconConfigurable icon, color and template from the payload itself
htmlA breakdown computed as markupNo JavaScript at all, at the cost of client-side structure
forecast_widgetWhether a demand will be metA verdict rather than an explanation

For a JSON payload that should render as an icon and a popover rather than a panel, the inventory popover widget is the more configurable choice, since its whole appearance comes from the payload. For a breakdown you want to reuse across models, computing an HTML field server side needs no JavaScript at all.

Frequently asked questions

What does the lead days panel show?+
The components of the replenishment lead time and their total: supplier delay, security days, warehouse handling and any configured purchase lead time. All of it is computed on the server and rendered from a JSON payload.
Can I configure what it shows?+
No. The descriptor has no options and no extractor. The content comes entirely from the server-side computation and the template.
Why does it error on an empty field?+
The shared base parses the field's value with no guard, so an empty or malformed string raises. The core dialog always computes the payload first.
Does the panel follow a recomputed value?+
Yes. The parse happens in a getter, so it is re-read on each access, unlike several other JSON-driven widgets that parse once at setup.
Which versions have it?+
Odoo 16 onwards, with only the registration style changing in Odoo 17. It is unchanged on the Odoo 20 development branch.

Reordering rules your buyers actually trust

Lead times, security days and routes decide when Odoo orders, and a rule nobody understands gets overridden by hand. We configure and explain replenishment on Odoo 16 through 19.

Book a free consultation

How this page was produced

The shared base, its declared type and display name, the unguarded parse and the per-access parsing were read from json_widget.js on the Odoo 19.0 branch, with the usage taken from stock/wizard/stock_replenishment_info.xml. Version coverage comes from comparing the registrations in the same file across the 16.0, 17.0 and 18.0 branches, and against the public development branch. Spotted an error? Tell us and we will correct the page.