Skip to main content
iVentureTeam

hr_leave_stats

Two lists on a time off request: what this employee has already taken this year, and who else in their department is away over the same dates.

Siddharth JambukiyaSiddharth JambukiyaOdoo Techno-Functional Consultant
August 27, 2026Updated August 31, 20264 min read
Technical namehr_leave_stats
Viewsform (view widget, <widget> element)
Modulehr_holidays, the Time Off app
Used in coreThe time off request form in hr_holidays
VersionsOdoo 20.0, Odoo 19.0, Odoo 18.0, Odoo 17.0, Odoo 16.0
No-code setupNo. It is set in view XML and depends on module-specific data
Alternativeshr_holidays_radio_image, web_ribbon, remaining_days

What the leave stats panel does

Approving a time off request is two judgments. Has this person already taken a lot this year, and will the team be covered while they are away. Neither is answerable from the request itself, so approvers historically opened two other screens.

This widget puts both on the request. One panel lists the employee's validated leave for the calendar year of the request. The other lists colleagues in the same department whose leave overlaps the requested dates.

Both refresh as the form is edited, so changing the dates immediately changes who shows up as a conflict.

What this means for your team

The coverage question is the one that gets skipped, and it is the one that causes the problem. An approver looking at a single request has no way to know that two other people in the same team already booked the same week.

Configuring departments to match how work is actually covered is what makes this panel useful. If a department is too broad, the list fills with irrelevant names; too narrow and real conflicts are invisible.

Supported options in Odoo 19

The widget takes the standard view widget props and declares no options. It requests four fields so it works regardless of what the form shows. The queries it runs are described below. Read from the leave stats source, Odoo 19.0.

OptionTypeWhat it does
employee_idrequested field dependencyDrives the employee panel, and is excluded from the department panel.
date_fromrequested field dependencyIts calendar year bounds the employee query; its value bounds the department overlap test.
date_torequested field dependencyBounds the department overlap test alongside the start date.
department_idrequested field dependencyDrives the department panel. Its display name path is trimmed to the last segment.

Only validated leave counts. Both queries filter on the validated state, so pending requests appear in neither list. That is deliberate: a pending request is not yet a fact about coverage.

Working examples

Placing it

<widget name="hr_leave_stats"/>

No attributes. It requests the four fields it needs.

The employee query window

# the whole calendar year of the request start
start of year  ..  end of year

Not the requested dates.

The department query window

# exactly the requested dates, overlapping
date_from <= to   and   date_to >= from

And excluding the requesting employee.

Two queries, two windows

The two queries use different windows, and that is the whole design. The employee list widens to the calendar year of the request's start date, because the question is about the year's pattern. The department list narrows to exactly the requested dates, because the question is about this week.

Both use an overlap test rather than containment, so a colleague whose leave merely touches the requested range still appears. That is correct for coverage: a partial overlap is still a day uncovered.

Reloading is driven by a record observer that compares the previous dates, employee and department against the new ones and only reruns the query whose inputs changed. Changing the dates reruns both; changing only the employee reruns only the employee list.

One small presentational detail: the department's display name arrives as a path, so the widget takes the last segment for display and keeps a flag recording that a parent existed, which lets the template show the hierarchy without printing the whole path.

Version compatibility

VersionStatusNotes
Odoo 20.0Partial / changedNot released. Substantially rewritten around newer conventions.
Odoo 19.0VerifiedVerified against the shipped source.
Odoo 18.0VerifiedSame two panels and query windows.
Odoo 17.0VerifiedSame two panels with older component conventions.
Odoo 16.0VerifiedSame two panels with older component conventions.

Upgrade note. Present since Odoo 16 in this form. The queries and the two-panel structure have been stable across those versions, so an upgrade needs no attention here.

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 this page after the release.

Substantially rewritten. The development branch reworks the component around the newer state and data conventions, with a large diff. The two panels and the two query windows are what to expect to survive; the details of how the data is loaded are being reshaped.

Common problems and fixes

SymptomCause and fix
The department panel is emptyNo employee or no department is set, or nobody else in that department overlaps. Check both fields are filled; an empty result is often correct.
A pending request does not appearBoth queries filter on the validated state. Expected. Validate it first if it should count.
The employee panel shows leave outside the requestThat panel covers the whole calendar year of the request's start date. Expected; it answers a different question from the department panel.
The requesting employee appears as a conflictThey should not; the department query excludes them. Check the employee field is actually set on the record.
The department name looks truncatedOnly the last segment of the hierarchy path is displayed. Expected. The full path is available on the department record.
Nothing reloads when I change datesThe observer compares the previous and new values before requerying. Check the date actually changed; identical values do not requery.

Leave stats panel vs the alternatives

WidgetBest forKey difference
hr_leave_statsGiving an approver the year pattern and the coverage picture on the request itselfTwo queries with different date windows, both limited to validated leave
hr_holidays_radio_imageChoosing a leave type visuallyA picker rather than a context panel
web_ribbonMarking a request's statusA label rather than context
remaining_daysShowing how soon a date fallsA single value rather than two lists

The time off calendar and the allocation report answer the same questions across the whole company, which is the right tool for planning. This widget exists for the moment of approval, where opening another screen is what actually gets skipped.

Frequently asked questions

Why do the two panels use different date ranges?+
They answer different questions. The employee panel widens to the whole calendar year to show a pattern; the department panel narrows to the requested dates to show coverage.
Why do not pending requests show?+
Both queries filter on the validated state, because a pending request is not yet a fact about coverage.
Does it save the record to refresh?+
No. A record observer watches the dates, employee and department in the browser and reruns only the query whose inputs changed.
Why is the department name shortened?+
The display name arrives as a hierarchy path, so the widget shows the last segment and records separately that a parent existed.
Which versions have it?+
Odoo 16 onwards with stable behavior. The development branch rewrites it substantially around newer conventions.

Time off approvals that do not create coverage gaps

Accrual rules, approval chains and team coverage all interact, and getting them wrong is only visible when someone is missing. We implement Odoo Time Off end to end, on versions 16 through 19.

Book a free consultation

How this page was produced

The two queries, their differing date windows, the validated state filter, the exclusion of the requesting employee, the selective reload driven by the record observer and the department name path handling were read from the leave stats source on the Odoo 19.0 branch. Version coverage comes from comparing the 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.