{"record":{"id":"41e4d220b04667c3","repo":"docmirror/dev-sidecar","slug":"freeeye-runtime-config-is-required","errorCode":null,"errorMessage":"FreeEye runtime config is required.","messagePattern":"FreeEye runtime config is required\\.","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/core/src/modules/plugin/free-eye/client.js","lineNumber":96,"sourceCode":"    for (const testTag of testCls.getPrereqs()) {\n      if (!doneTests.includes(testTag)) {\n        allPrereqsDone = false\n        break\n      }\n    }\n    if (allPrereqsDone) {\n      return testCls\n    }\n  }\n  return null\n}\n\nasync function runTests (options = {}) {\n  const { testsDir, config } = options\n\n  const globalConfig = (config && typeof config === 'object') ? config : null\n  if (!globalConfig) {\n    throw new Error('FreeEye runtime config is required.')\n  }\n\n  const globalResults = {}\n  const summaries = []\n  const todoTests = await loadAllTests(testsDir, globalConfig)\n  console.log(\n    `Loaded ${todoTests.length} tests: ${\n      todoTests.map(t => t.getTestTag()).join(' ')}`,\n  )\n\n  const doneTests = []\n  while (todoTests.length > 0) {\n    const TestCls = getNextTest(todoTests, doneTests)\n    if (!TestCls) {\n      break\n    }\n\n    const testGroup = new TestCls(globalConfig, globalResults)","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/docmirror/dev-sidecar/blob/7710cd56cce760c708f30b01d2d4056eb8c402d5/packages/core/src/modules/plugin/free-eye/client.js#L78-L114","documentation":"`runTests` destructures `config` from its options and requires it to be a non-null object; otherwise it throws `FreeEye runtime config is required.` The free-eye test runner needs runtime settings (applied to every loaded test) and will not guess defaults. This is a fail-fast validation at the public entry point.","triggerScenarios":"Calling `runTests()` with no arguments, with `{ testsDir }` only, or with `config: null/undefined` (or a non-object such as a string), from packages/core/src/modules/plugin/free-eye/client.js:96.","commonSituations":"Migrating code that previously called an older zero-config test runner; a caller that loads config asynchronously and passes it before it resolves (undefined); spreading an options object where the config key was misspelled (`cfg` vs `config`).","solutions":["Always pass `config` as a plain object: `runTests({ testsDir, config: freeEyeConfig })`.","Load the plugin's config from `DevSidecar.config.get().plugin['free-eye']` and pass that object.","Fix the option key name if you passed the config under a different property.","Await any async config loader before invoking runTests so you do not pass undefined."],"exampleFix":"// before\nawait runTests({ testsDir })\n// after\nconst config = DevSidecar.config.get().plugin['free-eye']\nawait runTests({ testsDir, config })","handlingStrategy":"validation","validationCode":"const config = DevSidecar.config.get()?.plugin?.['free-eye']\nif (!config || typeof config !== 'object') {\n  throw new Error('free-eye config missing; cannot run tests')\n}\nawait runTests({ testsDir, config })","typeGuard":"function isFreeEyeConfig (v) {\n  return v !== null && typeof v === 'object' && !Array.isArray(v)\n}","tryCatchPattern":"try {\n  await runTests({ testsDir, config })\n} catch (err) {\n  if (err.message === 'FreeEye runtime config is required.') {\n    console.error('Pass { config } object from plugin settings')\n  } else { throw err }\n}","preventionTips":["Destructure config from DevSidecar.config.get() before calling","Await async config loaders before invoking runTests","Double-check option key spelling (`config`, not `cfg`)","Add a unit test asserting runTests throws without config"],"tags":["free-eye","missing-argument","validation"],"backgroundTag":"missing-required-option","analyzedSha":"7710cd56cce760c708f30b01d2d4056eb8c402d5","analyzedAt":"2026-08-31T22:07:07.234Z","schemaVersion":2},"datasetVersion":"2026-08-31T22:30:34.772Z"}