Delivery forecast
The project in the screenshot has almost no completed history, so the card deliberately shows no precise date — a range, and a plain statement of why. A confident-looking date off a thin sample is the failure this design exists to avoid. Once a few sprints of estimates and logged time exist, the same card shows Likely (P50), Safe (P80) and — at high confidence only — Worst case (P90).
Route: /org/tasks?panel=risk → Delivery forecast · Permission: View risk radar (Manage risk radar to force a recompute)
Module: Task Management · Entry points: Risk Radar panel · milestone cards · Roadmap timeline markers · Portfolio Risk Radar
What this is. A simulated range of finish dates for a project and each of its milestones, with the odds of hitting the target. What it is for. Answering "when will this actually be done?" with a probability instead of a wish. The problem it solves. A plan date is one number that assumes everything goes as estimated. This runs two thousand versions of your project and shows you the spread.
1. What the forecast is
Every night — and whenever you open the panel — the platform simulates your project finishing, two thousand times over. Each run draws a realistic duration for every open task, schedules it against the right person's calendar, respects the dependencies, and records when the last task lands.
Sort those two thousand finish dates and you get:
| Figure | Means |
|---|---|
| P50 | Half the simulated runs finished by this date. The "likely" date. |
| P80 | Four in five finished by this date. The date to promise. |
| P90 | Nine in ten. Only shown at high confidence — see §4. |
| Buffer | The gap between P50 and P80, in days. How much slack the plan actually needs. |
| On-time chance | What share of runs landed on or before the milestone's target date. |
It costs no AI credits. No model is involved: this is arithmetic on your own history.
The simulation is seeded from a fingerprint of its own inputs. The same plan on the same day always produces the same P50 and P80. A number that moved because a random number moved would be worse than no number at all.
2. Where the numbers come from
| Input | Source | If it is missing |
|---|---|---|
| Remaining hours per task | remaining_hours, or estimate − actual | The project's median remaining hours is substituted, and it says so |
| How your estimates usually go | Tasks closed in the last 180 days that had both an estimate and logged time | A generic spread is used, and confidence drops to low |
| Who does what | Task assignee | Unassigned work is scheduled against the project's default capacity |
| How much they can do per day | Member capacity (hours per week ÷ 5) | The project's timesheet cap, else 8 hours |
| When they are not available | Weekends, organization holidays, approved leave | Weekends only |
| What must come first | Finish-to-start dependencies with their lag | Other link types are listed as not simulated |
The crucial one is the second row. The forecast is not guessing how long things take — it is learning how your team's estimates compare with reality, and applying that same optimism or pessimism to the work that is left.
3. How the simulation works
Two details that make it more than adding up estimates:
- One person does one thing at a time. Two twenty-hour tasks on the same person do not finish on the same day. This alone accounts for most of the difference between a plan date and reality.
- A wildly wrong historical figure is thrown away. A task recorded as taking twenty times its estimate is a data-entry mistake, not a signal, and is dropped before it can poison every future forecast.
4. Confidence — and why low confidence shows no dates
| Confidence | Means | What you see |
|---|---|---|
| High | 20+ closed tasks to learn from, and 60%+ of open work estimated | P50, P80, P90, the histogram, the drivers |
| Medium | At least 5 closed tasks to learn from | P50, P80, buffer, histogram. No P90 — a 90th percentile off a thin sample is noise with a decimal point |
| Low | Neither | No precise dates at all — a range, and a plain statement that there is not enough history |
A confident-looking date built on three closed tasks is worse than no date, because someone will plan around it. Log estimates and time for a few sprints and the forecast becomes meaningful. The caption always tells you how much of the project is estimated: "12 of 30 open tasks have estimates."
5. What it had to assume
Expand What this assumed under any forecast. It lists, every time:
- how many tasks had no estimate, and what was substituted
- how little history it had to learn from
- how much work has no assignee
- dependency link types it did not simulate (only finish-to-start is scheduled)
- whether the dependency graph contained a loop it had to work around
Nothing here is buried. A forecast built on substituted estimates should say so where you read it.
6. Forecast on the risk radar
A milestone whose simulated P80 lands after its target raises a Forecast miss signal, which flows through the same alerts, explanations and advisor as every other risk signal.
| The simulation says | Severity |
|---|---|
| Under a 20% chance of landing on time | Critical |
| The P50 is already past the target — the middle of the distribution misses | High |
| The P80 is past the target — a realistic bad run misses | Medium |
| The P80 lands on or before the target | Nothing. It agrees with the plan |
It stays silent at low confidence (a guess should not page anyone), on a milestone with no target date or no open work, and on one that is already overdue — Milestone overdue states that as a fact, and predicting it too is noise on top of an alarm that has already fired.
7. On the roadmap
The timeline draws a P50 and P80 marker on each sprint and phase bar, so the gap between the plan and the simulation is visible on the plan itself. Low-confidence forecasts are not drawn: a marker on a timeline reads as a commitment.
8. Administrator settings
Super Admin → System Configuration:
| Key | Default | What it does |
|---|---|---|
TASK_FORECAST_ENABLED | true | Turn the whole capability off, including the nightly step |
TASK_FORECAST_RUNS | 2000 | Simulation passes. Below about 500 the P80 becomes visibly noisy between runs |
The forecast runs inside Task Risk Radar Daily, after risk scoring and before the second scoring pass. If it fails, the risk result still stands — a simulation having a bad day must never stop delivery risk being scored.
9. Downstream
- Risk radar — the
forecast_misssignal, and a forecast card on each milestone - Portfolio Risk Radar — a P80 column beside the milestones about to slip
- Roadmap timeline — P50 / P80 markers
- Public API —
GET /api/v1/ext/task/forecast(scopetask:risk:read), and the same as an MCP tool
10. Don't confuse this with…
| This | That |
|---|---|
| Delivery forecast — when the work will finish, as a range | Risk radar — what is going wrong right now |
| P80 — a date four runs in five beat | A deadline, a commitment, or a promise to a customer |
| Milestone burn — the pace needed versus the pace achieved | Forecast miss — a simulated finish date past the target |
11. Troubleshooting
| Symptom | Cause | Fix |
|---|---|---|
| "Not enough history" on every project | Nobody logs time against estimates | Record both on a few closed tasks; five is enough for medium confidence |
| The forecast never changes | The plan has not changed — the stored result is served | Change an estimate or a date, or press Recompute |
| No forecast at all | TASK_FORECAST_ENABLED is false, or migration 001173 has not been applied | Check System Configuration, then the migration |
| The dates look impossibly far out | One task has an enormous remaining-hours figure, or a dependency chain is longer than it should be | Open the drivers list — it names the tasks shaping the spread |
| A milestone is missing | It has no open tasks | Correct: inventing a date for finished work would be worse than leaving it out |