Part 3 · Projects, time and knowledge
Workload plan
Place what is actually left to do on weeks, against a declared capacity rather than a guessed one, and quantify what cannot be placed instead of hiding it.
A task backlog tells you how many hours are recorded. It does not tell you whether they fit, which weeks they land on, or which of them are real work. The Plan de charge (workload plan) application fills exactly those three gaps and nothing else. It is meant for the person carrying several engagements at once who wants to know, with figures rather than a feeling, whether they are taking on too much.
This module is published but absent from the Boréal demo: this chapter describes it from its documentation and its declared screens, without screenshots (module published, not illustrated).
Overview#
Three ideas govern everything else, and each answers a way of being wrong.
Capacity is declared, never inferred. Hours in a timesheet are not wall clock time. On a real database several days go past sixteen hours, sometimes far past: assisted work produces several hours within the same hour. Dividing a backlog by "the hours I log per week" therefore returns a wrong answer with two decimals. The module measures the candidates, shows them side by side, and lets a person choose.
A workload says where it came from. Odoo's allocated hours field has several sources: a human estimate, or a sold quantity converted by its unit of measure. A yearly subscription line sold in "Year" belongs to the working time category and becomes thousands of hours nobody estimated. Every task therefore carries its source, and an hour derived from a sale unit that is not the hour is set aside from the plan, visibly, with its reason.
The unplaceable pile is not hidden. A task with no date lands on no week. A calendar that only shows what it can place lies by omission. The plan therefore always shows, next to the weeks, the total hours it could not place and how many tasks that is. It is often that number, not the calendar, that answers the question being asked.
The application lives off two others, which it only reads. The last logged dates come from Timesheets, and a task's start date, where it exists, from Schedule. It modifies neither.
Configuration#
Access and rights#
The application ships a single group, Workload plan: management. A person's capacity is sensitive data: it is not offered to every internal user, and the menu only appears for whoever holds the group.
| Level | What it opens |
|---|---|
| Without the group | Nothing. The menu does not appear and the models are refused. |
| Workload plan: management | Declare the capacity, build plans, read the lines, weeks, signals and readings. |
The group is deliberately narrow. The module therefore reads timesheet lines and sale units with elevated rights on its own behalf, and each read is bounded to its own company in the domain rather than relying on a record rule that elevation bypasses.
System parameters#
Two settings, both in the system parameters.
| Parameter | Default | Effect |
|---|---|---|
bf_charge.template_tag |
Gabarit |
The project tags marking a template. Several, comma separated. |
bf_charge.dormant_days |
90 |
Days without a logged hour past which a project is called dormant. |
The template tag#
A template project is a pattern to clone, not work waiting. Its hours never enter a plan. Mark it by adding the Gabarit tag in the Tags field of its record.
The weekly reading#
The module ships a scheduled action, Workload plan: weekly reading, which takes a reading and keeps it. It ships disabled, on purpose: a reading taken before a capacity is declared archives zeros that will later look like a measurement. Enable it once the contract is filled in.
Declaring the capacity#
Everything starts with a capacity contract. Without one, the plan places the hours but cannot say whether they fit, and three of the five signals stay "not declared".
The contract is about a person, not a team, and three numbers are enough.
| Field | What it declares |
|---|---|
| Hours per week | The hours genuinely available to deliver. |
| Meeting hours per week | The meeting load subtracted from capacity. |
| Ceiling on concurrent customers | How many distinct customers you accept to carry at once. 0 means no ceiling declared, hence no signal. |
| Target customer share | The share of delivered hours that should go to customer engagements. |
| Stop criteria | What must happen for you to stop taking more on. Numeric if possible, and written before it is needed. |
The net capacity is the difference between the first two: that is what the plan uses.
The measured candidates#
Beside the fields to fill in, the form shows five numbers the module measured on the database. It chooses none of them.
| Candidate | What it is worth |
|---|---|
| Weekly median (12 months) | The middle of the weeks logged over a year. |
| Weekly mean (12 months) | The mean of the same weeks, pulled up by the peaks. |
| Declared working calendar | What the employee record says, often forty hours. |
| 90 day median, capped to wall clock | The last three months, each day capped at twelve hours. |
| Meetings per week (90 day median) | The appointment load of the last three months. |
The Take the measured meeting median button carries the last one into the matching field.
A contract comes into force with the Put in force button, which automatically closes the previous one for the same person. A contract with no hours per week is refused: that is its whole point.
A task's workload#
Every task carries, in its form, what the plan retains of it.
| Field | What it says |
|---|---|
| Retained workload | The hours the plan counts. |
| Workload source | Where they come from. |
| Reason for setting aside | Why they were set aside, where applicable. |
| Corrected workload | A workload set by hand, which wins over everything else. |
| Retained start, Retained end | The window the workload spreads over. |
| Placeable | False when the task carries no date. |
Five sources, in priority order.
| Source | When |
|---|---|
| Corrected by hand | A workload was entered in the dedicated field. It always wins. |
| Estimated | The allocated hours come from a human entry. |
| Sold quantity | They come from a sale line whose unit is the hour. |
| Sold quantity, set aside | They come from a sale line whose unit is another unit of time. The workload is then zero and the reason says so. |
| None | The task carries no estimate. That is a fact, not a zero, and it is counted separately. |
The sale unit that writes thousands of hours#
The fourth case deserves its paragraph, because it is invisible and expensive. A service product that creates a task on sale, sold in the Year unit, writes into the allocated hours the conversion of that year into working hours, meaning several thousand. Nothing flags the anomaly: the number is exact, what it describes is not. A sold duration is not an estimated effort.
The plan therefore sets those hours aside, totals them separately, and its summary says how many. If the figure surprises you, a product in your catalogue deserves a different unit of measure.
Placement, and what cannot be placed#
To put an hour on a week you need a date. The module looks for two, in this order.
- The task's start date, if the Schedule application is installed and the date is filled in.
- Its deadline, failing that.
A task carrying both has its workload spread pro rata over the days of each week covered. A task carrying only one falls entirely on the matching week. A task carrying neither is not placeable: it is counted separately, in hours and in number.
Three special cases.
| Case | What the plan does with it |
|---|---|
| Deadline already past | The workload is pulled onto the first week of the horizon and counted as overdue. |
| Start beyond the horizon | The workload is counted separately, occupying no week. |
| Window running past the horizon | The visible workload is spread over the weeks covered. |
Projects classify themselves#
The module files every project under one of three kinds, without reading a single message.
| Kind | Rule |
|---|---|
| Template | The project carries the template tag. Its hours never enter a plan. |
| Dormant | The project is archived, or no hour has been logged on it within the configured window. |
| Live | An hour was logged on it recently. |
That classification does most of the work. On a real database, the great majority of open budgeted hours live in a handful of projects that no longer move, or in templates. Removing them from the plan hides nothing: their totals stay displayed, separately, on the plan itself.
Building a plan#
A workload plan is created with a start date and a horizon in weeks, then computed with the Compute the plan button. The computation can be replayed as often as you like: it erases and rebuilds its weeks, lines and signals.
The form then gives, in three blocks, what it found.
| Block | What it carries |
|---|---|
| Placed | The hours placed on the horizon and the backlog in weeks of capacity. |
| What the plan could not place | Not placeable hours, the tasks concerned, tasks with no workload, hours beyond the horizon and overdue hours. |
| Out of plan, by construction | Template hours, dormant project hours and hours set aside for their sale unit. |
A prose summary repeats the essentials, including the share the unplaceable pile represents in the backlog. It is often the most useful sentence on the screen.
The Weeks tab gives one row per week, with its hours, the declared capacity, the load percentage and a coloured verdict: green under eighty per cent, amber above, red when the week exceeds capacity.
The five signals#
The Signals tab answers the question "am I taking on too much". Each signal shows its measure, not just its colour, and stays "not declared" until its benchmark is in the contract.
| Signal | Measure | Benchmark |
|---|---|---|
| Concurrent customers | Distinct customers touched over thirty days | The declared ceiling |
| Customer share of delivered hours | Customer hours against internal hours over thirty days | The target share |
| Hour banks below zero | How many banks are negative, and which | None |
| Arrivals against closures | Tasks opened against tasks closed over thirty days | The backlog must not grow two months in a row |
| Backlog in weeks of capacity | The backlog divided by the declared net capacity | Eight weeks, then sixteen |
The third stays silent if the Hour bank application is not installed: it says so rather than showing a misleading green.
Slicing the workload#
Every computation writes a fact table: one row per task and per week its workload lands on, carrying its project, its customer, its source, its dates and where it lands. A task straddling two weeks produces two rows whose shares sum to one.
The Lines button at the top of the plan opens that table straight onto the chart. Five native views apply to it.
| View | What it shows |
|---|---|
| Chart | Stacked bars per week, one stack per outcome. Placed and not placed read side by side. |
| Cross table | Projects in rows, weeks in columns. |
| List | The detail, task by task, with the hours total. |
| Calendar | The plan's weeks over a month, with their hours and their capacity. |
| Trend | The successive readings, to see whether it is getting worse. |
The filters shipped by default separate placed hours, not placeable ones, what is out of plan and what has no workload, as well as customer work from internal work. The groupings cover the week, the outcome, the project, the customer, the source and the project kind.
The reading, and the trend#
A workload reading is the same count, repeated and kept. A plan answers "where we are"; it does not answer "is it getting worse". The reading keeps the few numbers that carry the answer: open, dated and placeable tasks, live, dormant, template, placeable and not placeable hours, customers touched, customer and internal hours, tasks opened and closed over thirty days.
It never copies the detail: that is always re-read from the tasks. The trend chart and the readings cross table then read over several months.
What the module does not do#
- It does not compute a capacity. It asks for one.
- It does not ask you to date your tasks. It quantifies what is not dated.
- It estimates nothing on your behalf: a task with no estimate stays without one, and that is counted.
- It assigns nobody to anything. This is not a resource booking tool.
Troubleshooting#
The menu does not appear. The Workload plan: management group has not been granted. It is granted to nobody at installation.
Every signal says "not declared". No capacity contract is in force, or the one in force carries neither a customer ceiling nor a target customer share.
The plan places far fewer hours than the backlog announces. That is the expected behaviour, and the form's three blocks say where the others went: templates, dormant projects, set aside sale units, and above all the hours that cannot be placed for want of a date.
A week shows a "not declared" verdict. The declared capacity is zero: with no denominator, no percentage means anything.
A project shows as live when it no longer is. An hour was logged on it within the configured window. Lower bf_charge.dormant_days, or archive the project: an archived project is dormant whatever happens.