GoogleChrome/lighthouse · error · Error

No timespan in progress

Error message

No timespan in progress

What it means

State-machine guard in UserFlow.endTimespan(). Requires currentTimespan to be set. Fires when endTimespan() is called without a prior startTimespan(), or when endTimespan() is called twice (the second call finds currentTimespan already cleared to undefined at line 213).

Solutions

  1. Ensure startTimespan() was called before endTimespan()
  2. Check flow.currentTimespan is set before calling endTimespan()
  3. Do not call endTimespan() twice — guard with a currentTimespan check

Example fix

// before — endTimespan without startTimespan
await flow.endTimespan(); // throws

// after — start timespan first
await flow.startTimespan();
// ... interactions ...
await flow.endTimespan();
Defensive patterns

Strategy: validation

Validate before calling

if (!flow.currentTimespan) {
  console.error('No timespan in progress — did you call startTimespan()?');
  return;
}
await flow.endTimespan();

Type guard

/** @param {UserFlow} flow @returns {boolean} */
function canEndTimespan(flow) {
  return flow.currentTimespan != null && flow.currentNavigation == null;
}

Prevention

When it happens

Trigger: Calling flow.endTimespan() when flow.currentTimespan is undefined. Happens when startTimespan() was never called, or after endTimespan() already completed and cleared the state.

Common situations: Forgot to call startTimespan() first. Double-calling endTimespan(). Calling endTimespan() by mistake instead of endNavigation(). Exception in a try/finally that caused endTimespan to run after it was already ended.

Related errors


AI-assisted analysis of GoogleChrome/lighthouse@9515cd4e58 (2026-08-13). Data as JSON: /api/errors/f41c66a6c263a7c1. Report an issue: GitHub.

Appendix: source

Thrown at core/user-flow.js:208

  /**
   * @param {LH.UserFlow.StepFlags} [flags]
   */
  async startTimespan(flags) {
    if (this.currentTimespan) throw new Error('Timespan already in progress');
    if (this.currentNavigation) throw new Error('Navigation already in progress');

    const nextFlags = this._getNextFlags(flags);

    const timespan = await startTimespanGather(this._page, {
      config: this._options?.config,
      flags: nextFlags,
    });
    this.currentTimespan = {timespan, flags: nextFlags};
  }

  async endTimespan() {
    if (!this.currentTimespan) throw new Error('No timespan in progress');
    if (this.currentNavigation) throw new Error('Navigation already in progress');

    const {timespan, flags} = this.currentTimespan;
    const gatherResult = await timespan.endTimespanGather();
    this.currentTimespan = undefined;

    this._addGatherStep(gatherResult, flags);
  }

  /**
   * @param {LH.UserFlow.StepFlags} [flags]
   */
  async snapshot(flags) {
    if (this.currentTimespan) throw new Error('Timespan already in progress');
    if (this.currentNavigation) throw new Error('Navigation already in progress');

    const nextFlags = this._getNextFlags(flags);

View on GitHub (pinned to 9515cd4e58)