{"record":{"id":"f10ad63760858829","repo":"santifer/career-ops","slug":"apify-token-not-set-enable-apify-in-config-plugi","errorCode":null,"errorMessage":"APIFY_TOKEN not set — enable apify in config/plugins.yml and add the token to .env","messagePattern":"APIFY_TOKEN not set — enable apify in config/plugins\\.yml and add the token to \\.env","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"plugins/apify/index.mjs","lineNumber":182,"sourceCode":"  };\n  for (const [k, v] of Object.entries(defaults || {})) {\n    if (!ALLOWED_DEFAULT_KEYS.has(k)) continue;\n    if (!out[k]) out[k] = String(v);\n  }\n  return out;\n}\n\n/** The keyed provider hook. Reads APIFY_TOKEN from the plugin's scoped ctx.env. */\nexport default {\n  provider: {\n    id: 'apify',\n    // Keyed providers never auto-detect (the engine also forces this to null).\n    detect() { return null; },\n\n    async fetch(entry, ctx) {\n      const token = ctx?.env?.APIFY_TOKEN || process.env.APIFY_TOKEN;\n      if (!hasToken(token)) {\n        throw new Error('APIFY_TOKEN not set — enable apify in config/plugins.yml and add the token to .env');\n      }\n      if (!entry.actor) {\n        throw new Error(`apify: entry ${entry.name} missing 'actor' (e.g. misceres/indeed-scraper)`);\n      }\n      if (\n        !entry.field_map ||\n        !isFieldSpec(entry.field_map.title) ||\n        !isFieldSpec(entry.field_map.url) ||\n        (entry.field_map.company != null && !isFieldSpec(entry.field_map.company)) ||\n        (entry.field_map.location != null && !isFieldSpec(entry.field_map.location)) ||\n        (entry.field_map.description != null && !isFieldSpec(entry.field_map.description))\n      ) {\n        throw new Error(\n          `apify: entry ${entry.name} has invalid field_map. Each of title, url, company, ` +\n          `location, description must be a string or a non-empty array of strings. title and url are required.`\n        );\n      }\n","sourceCodeStart":164,"sourceCodeEnd":200,"githubUrl":"https://github.com/santifer/career-ops/blob/9b17a8ac97b398a496b38e423ae24e433b43254f/plugins/apify/index.mjs#L164-L200","documentation":"Thrown by the apify provider's `fetch` hook (plugins/apify/index.mjs:182) when neither `ctx.env.APIFY_TOKEN` (the plugin's scoped env) nor `process.env.APIFY_TOKEN` is set. This is the provider-level guard, richer than the transport-level one (error 112): it names both the config file (config/plugins.yml) and .env so the user knows exactly where to enable the plugin and add the token. It fires before any actor/field_map validation.","triggerScenarios":"The apify provider is referenced (portals.yml entry with `provider: apify`) and its fetch is invoked, but the plugin is not fully configured — either not enabled in config/plugins.yml or the token is absent from both the scoped ctx.env and process.env.","commonSituations":"Plugin added to portals.yml but never enabled via `node plugins.mjs enable apify`; .env missing APIFY_TOKEN; the plugin's scoped env did not receive the token (env loader scoping issue); running in CI without the secret injected.","solutions":["Enable the plugin: `node plugins.mjs enable apify` (or set it in config/plugins.yml).","Add `APIFY_TOKEN=apify_api_...` to .env and ensure the env loader populates the plugin's scoped ctx.env.","Run `node doctor.mjs` to confirm the apify plugin reports active with a valid token.","In CI, inject APIFY_TOKEN as a secret."],"exampleFix":"# before — config/plugins.yml missing apify, .env missing token\n# after\n# config/plugins.yml\napify:\n  enabled: true\n# .env\nAPIFY_TOKEN=apify_api_xxxxxxxxxxxxx","handlingStrategy":"validation","validationCode":"import { existsSync, readFileSync } from 'node:fs';\n// Ensure apify is enabled AND the token is present before scanning.\nfunction assertApifyReady(root) {\n  const cfg = readFileSync(`${root}/config/plugins.yml`, 'utf-8');\n  const enabled = /^apify:\\n(?:[ \\t]+enabled:[ \\t]*true|.{0})|apify:[ \\t]*true/m.test(cfg);\n  if (!enabled) throw new Error('apify plugin not enabled in config/plugins.yml');\n  if (!process.env.APIFY_TOKEN) throw new Error('APIFY_TOKEN missing from .env');\n}\nassertApifyReady(process.cwd());","typeGuard":null,"tryCatchPattern":"try {\n  await provider.fetch(entry, ctx);\n} catch (err) {\n  if (/APIFY_TOKEN not set — enable apify/.test(err.message)) {\n    console.error(`Setup required: ${err.message}`);\n    process.exitCode = 2;\n  } else throw err;\n}","preventionTips":["Run `node plugins.mjs enable apify` then add APIFY_TOKEN to .env.","Gate CI scans on `node doctor.mjs` reporting apify active."],"tags":["apify","configuration","environment","auth","secrets","plugin"],"backgroundTag":null,"analyzedSha":"9b17a8ac97b398a496b38e423ae24e433b43254f","analyzedAt":"2026-08-13T00:48:39.135Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}