santifer/career-ops · error · Error

Apify actor ${actorId} finished with status ${run.status}${r

Error message

Apify actor ${actorId} finished with status ${run.status}${reason}

What it means

Thrown by `runActor` (plugins/apify/_apify.mjs:199) when the actor run reaches a terminal status other than SUCCEEDED — i.e. FAILED, ABORTED, or TIMED-OUT. The `waitForRun` loop returns the run object once status is in TERMINAL_STATUSES; runActor then checks `if (run.status !== 'SUCCEEDED')` and throws, appending `run.statusMessage` as `: <reason>` if present. The dataset is not fetched on failure.

Source

Thrown at plugins/apify/_apify.mjs:199

  if (!Array.isArray(items)) {
    throw new Error(`Apify run ${runId} returned non-array dataset payload`);
  }
  return items;
}

export async function runActor(actorId, input, { timeoutMs = DEFAULT_RUN_TIMEOUT_MS, token = process.env.APIFY_TOKEN } = {}) {
  if (!token) throw new Error('APIFY_TOKEN not set');
  if (!Number.isFinite(timeoutMs) || timeoutMs <= 0) {
    throw new Error(`apify: invalid timeoutMs ${JSON.stringify(timeoutMs)} (must be a positive finite number of milliseconds)`);
  }
  // Single deadline shared across startRun → waitForRun → fetchDatasetItems so
  // the caller's timeoutMs is the end-to-end ceiling, not just the wait loop.
  const deadline = Date.now() + timeoutMs;
  const runId = await startRun(actorId, input, token, deadline);
  const run = await waitForRun(runId, token, deadline, timeoutMs);
  if (run.status !== 'SUCCEEDED') {
    const reason = run.statusMessage ? `: ${run.statusMessage}` : '';
    throw new Error(`Apify actor ${actorId} finished with status ${run.status}${reason}`);
  }
  return await fetchDatasetItems(runId, token, deadline);
}

View on GitHub (pinned to 9b17a8ac97)

Solutions

  1. Read the statusMessage suffix — Apify usually states the failure cause.
  2. Open the run on the Apify console (runId is in the message) for full logs.
  3. Fix the actor input (field_map / input in portals.yml) to match the actor's expected schema.
  4. If the actor itself is broken, switch to an updated actor or contact its maintainer.
Defensive patterns

Strategy: try-catch

Try / catch

try {
  const items = await runActor(actorId, input, opts);
} catch (err) {
  if (/finished with status (FAILED|ABORTED|TIMED-OUT)/.test(err.message)) {
    console.error(`Apify actor ${actorId} did not succeed: ${err.message}`);
    // inspect the runId in the message on the Apify console for logs
  } else throw err;
}

Prevention

When it happens

Trigger: The actor finished but failed (input error, scraper bug), was aborted (manually or by Apify), or hit Apify's own run timeout. waitForRun returns the terminal run, and runActor rejects.

Common situations: Bad actor input (wrong field names, missing required input); the target site changed and the scraper broke; Apify aborted the run due to proxy/quota exhaustion; the actor timed out internally on Apify's side before your timeoutMs.

Related errors


AI-assisted analysis of santifer/career-ops@9b17a8ac97 (2026-08-13). Data as JSON: /api/errors/a434332173cc5c16. Report an issue: GitHub.