BottleneckIQ

Your Jira plugin is blaming the team for weekends and external waits

· 4-minute read · by Desveladisimo

A 3-minute read on two drifts in your flow numbers — both fixable, both invisible until you know to look. Extracted from the foundational mechanism map at your-time-in-status-plugin-is-lying-to-you.


A retrospective pattern I've watched repeat across teams and across companies: cycle time keeps inflating, the action item is "speed up the stage with the highest number," the next sprint comes back with the same number, and nobody can figure out why the fix didn't take. The team works harder. The dashboard reports the same drift. The retrospective happens again.

The two most common causes I've seen for this unchangeable-cycle-time pattern share a single property: the plugin doesn't understand the context in which your team actually works. Not workflow context (different drift, different post). Business context. Working hours, holidays, customer dependencies, the team's actual agency over the time being measured.

A ticket sitting in "In Review" from Friday 17:00 to Monday 09:00 reports 64 hours of "review time" the team couldn't have spent reviewing because they weren't there. A ticket waiting on a customer for eight days for procurement approval gets attributed to the team's cycle time as if the team were sitting on their hands. Both failures are routine. Most plugins commit them. Both have the same root cause and the same fix.

Two 60-second checks — run either one against your own data

60-second check

For weekend drift

Find a ticket whose status duration spans a weekend or a holiday. They're easy to find with a Jira filter for "resolved on Monday, created Friday or earlier." Compare your plugin's reported duration against business-hours-only math (Mon–Fri, working hours, weekends and holidays excluded). If the plugin reports the full wall-clock duration with weekends and off-hours fully counted, every cycle-time number you've shown a stakeholder is inflated by non-working hours — and the inflation is asymmetric across statuses, distorting the bottleneck signal toward statuses where tickets sit passively.

60-second check

For external-wait drift

Look at your last three months of data and pick the longest-duration status. If it's a status where work is paused on a third party (Waiting for Customer, Blocked: Vendor Response, In External Review, Awaiting Approval), check whether the plugin's bottleneck card and cycle-time aggregate exclude that time from the team's attribution. If the plugin has no per-project configuration for "external-blocking" or "pause" statuses, every retrospective in which throughput was named the action item was working from numbers that mixed team-controllable time with time the team couldn't influence.

If either check surfaces drift, what follows is why.

Drift 1: Calendar time treated as working time

A ticket sits in "In Progress" from Friday 17:00 to Monday 09:00. Wall-clock duration: 64 hours. Working-time duration: zero. The plugin reports 64.

This is the most-universal drift in Jira analytics tools — present in almost every time-in-status plugin and most of the lightweight flow-metrics plugins — and the easiest one to verify against your own data.

The inflation isn't symmetric across stages, and that's the part most teams don't catch even when they notice the calendar issue. Statuses that tickets sit in passively (Blocked, Waiting, In Review when nobody's looking) accumulate weekend and off-hour time disproportionately to statuses tickets sit in actively (In Progress when someone's typing). So the bottleneck card's time signal gets distorted toward passive statuses, and the action item lands on the wrong stage. A team gets told to speed up Code Review when Code Review actually had two business hours of attention that week and forty-eight non-working hours bolted to the same metric.

The fix is mechanical: every duration computation has to go through a single helper that honors a per-tenant work schedule — timezone, working days, work hours, holidays. Cycle time, time-in-status, alert thresholds, the bottleneck card's time signal all read from the same computation. Most plugins either don't have work-schedule configuration, or have it for one chart but not the alerts — which is arguably the worse failure mode because the alert fires at a different threshold than the chart shows.

And when the schedule changes? Most plugins leave old slices computed under the old rules and new slices computed under the new rules in the same chart. The honest engineering is to async-recompute every historical slice on settings change, with a visible progress banner during the few minutes it takes. The lie is the silent blend.

Drift 2: External waits attributed to the team

A ticket sits in "Waiting for Customer" for eight days. The customer is sitting on a question your team asked — a contract review, a procurement approval, a clarification request. Your team has nothing they can do.

A plugin that scores every status uniformly will see "Waiting for Customer" as a high-time-in-status outlier and either name it as the bottleneck (technically correct, operationally useless — the team cannot fix it) or, in plugins that don't surface a single answer, simply attribute those eight days to the team's cycle time. The dashboard reads median cycle time: 13 days. It does not read median cycle time: 5 days plus 8 days waiting on the customer. The team gets the throughput question in retrospective. The team has nothing to say about it.

This pattern is universal anywhere a team has external dependencies — customer approvals, vendor responses, legal reviews, security reviews, procurement, third-party integrations. It compounds particularly hard on B2B teams whose work is gated by counterparty timelines. The team gets blamed in standup for time waiting on the world.

The fix isn't to delete the external-blocking slices — the data is still legitimate (yes, this ticket waited eight days; the per-issue history should reflect it). The right shape is to preserve the slice everywhere it's a fact (per-issue history, charts, CSV export) and skip it only from the attribution step. The question "where is the team's controllable bottleneck?" deserves an honest answer that ignores statuses the team can't act on, while the question "how long did this ticket actually spend waiting?" gets answered honestly elsewhere.

Why both matter more than they look

Both drifts share a property that makes them quietly dangerous: they don't break the dashboard. The numbers look reasonable. The chart renders without errors. Stakeholders accept the cycle-time figure without questioning it. The team accepts the bottleneck-card name without challenging it. And every decision built on those numbers — throughput retrospectives, sprint planning estimates, performance conversations — calcifies the wrong action items.

The cost compounds quietly across quarters. A team told for two quarters that "we need to speed up Review" has been triaging on inflated numbers that don't reflect actual review time. A team told that "customer-facing tickets are our throughput problem" has been blamed for procurement delays they couldn't accelerate. The dashboard never showed any of it because the dashboard was the thing producing the error.

The plugin I built handles both

I built BottleneckIQ because I'd watched both of these drifts produce wrong action items across multiple teams across multiple companies over the years.

Every metric derives from the Jira issue changelog (so the math is correct on the foundation). A per-tenant work schedule applies to every duration (so weekends, off-hours, and holidays don't inflate). Per-project external-blocking statuses let you mark Waiting for Customer / Blocked: Vendor / In External Review as paused (so the bottleneck card stops naming the team for time it can't control). When you enable or edit the work schedule, the historical data is asynchronously recomputed with a visible progress banner — so charts never blend old calendar-time numbers with new working-time numbers.

30-day free trial. From $10/month for teams up to 10 users, $3/user beyond. One-click install on any Jira Cloud project.

This is one of three articles on drift mechanisms in Jira flow analytics. Calendar drift and external-wait drift are what's here. The other two drift families:

  • Workflow drift — status renames and workflow restructures distorting historical comparisons.
  • Edit-and-toggle drift — manual transition reversals and fast-succession status changes that the plugin's "last changed" pointer never sees.

The full six-mechanism map and the architectural alternative live in the foundational post. If you'd rather skip the reading and try the plugin against your own data, the install is one click from the Marketplace link above.

If you ran either of the 60-second checks above and found drift, I'd be glad to hear what you found — francisco@bottleneckiq.com. Real installs from teams who recognize their situation in these articles is the loop that makes the next version sharper.

Built by Desveladisimo — a lifetime developer launching his first independent product.