{"record":{"id":"6970a9d36671bd25","repo":"medusajs/medusa","slug":"zone-property-at-the-j-index-of-the-forms-p","errorCode":null,"errorMessage":"'zone' property at the ${j} index of the 'forms' property is not a string literal. The 'zone' property must be a string literal, e.g. 'general' or 'attributes'.","messagePattern":"'zone' property at the (.+?) index of the 'forms' property is not a string literal\\. The 'zone' property must be a string literal, e\\.g\\. 'general' or 'attributes'\\.","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"packages/admin/admin-vite-plugin/src/custom-fields/generate-custom-field-forms.ts","lineNumber":302,"sourceCode":"  formArray.elements.forEach((element, j) => {\n    if (!isObjectExpression(element)) {\n      return\n    }\n\n    const zoneProperty = element.properties.find(\n      (p) => isObjectProperty(p) && isIdentifier(p.key, { name: \"zone\" })\n    ) as ObjectProperty | undefined\n\n    if (!zoneProperty) {\n      logger.warn(\n        `'zone' property is missing from the ${j} index of the 'forms' property. The 'zone' property is required to load a custom field form.`,\n        { file }\n      )\n      return\n    }\n\n    if (!isStringLiteral(zoneProperty.value)) {\n      logger.warn(\n        `'zone' property at the ${j} index of the 'forms' property is not a string literal. The 'zone' property must be a string literal, e.g. 'general' or 'attributes'.`,\n        { file }\n      )\n      return\n    }\n\n    const tabProperty = element.properties.find(\n      (p) => isObjectProperty(p) && isIdentifier(p.key, { name: \"tab\" })\n    ) as ObjectProperty | undefined\n\n    let tab: string | undefined\n\n    if (tabProperty) {\n      if (!isStringLiteral(tabProperty.value)) {\n        logger.warn(\n          `'tab' property at the ${j} index of the 'forms' property is not a string literal. The 'tab' property must be a string literal, e.g. 'general' or 'attributes'.`,\n          { file }\n        )","sourceCodeStart":284,"sourceCodeEnd":320,"githubUrl":"https://github.com/medusajs/medusa/blob/5e06e544a296b9033f20f71f11c559f81a0e5739/packages/admin/admin-vite-plugin/src/custom-fields/generate-custom-field-forms.ts#L284-L320","documentation":"The plugin requires 'zone' to be a string literal because it reads the value at build time via AST parsing; expressions like a variable, template literal, or concatenation cannot be resolved. If zoneProperty.value is not a StringLiteral node, this warning is emitted and the form entry is skipped.","triggerScenarios":"zone: ZONE constant, zone: `general` (template literal), zone: 'gen'+'eral', or zone: getZone() in a form entry.","commonSituations":"Extracting zone names into shared constants/imports, using template literals out of habit, or generating configs dynamically.","solutions":["Inline the literal string: zone: 'general'","Keep the literal directly in the config file rather than referencing a constant","If multiple forms share zones, repeat the literal per entry"],"exampleFix":"// before\nconst ZONE = 'general'\nforms: [{ zone: ZONE, fields: {...} }]\n// after\nforms: [{ zone: 'general', fields: {...} }]","handlingStrategy":"type-guard","validationCode":"for (const [i, f] of forms.entries()) {\n  if (typeof f.zone !== 'string') throw new Error(`forms[${i}].zone must be an inline string literal`)\n}","typeGuard":"const isStringLiteral = (v: unknown): v is string => typeof v === 'string'","tryCatchPattern":null,"preventionTips":["Never reference constants for zone/tab values; inline literals only","Add a unit test asserting every form entry's zone is a plain string"],"tags":["admin","custom-fields","string-literal","ast-parsing"],"backgroundTag":"admin-custom-field-form-validation","analyzedSha":"5e06e544a296b9033f20f71f11c559f81a0e5739","analyzedAt":"2026-08-27T07:24:39.599Z","schemaVersion":2},"datasetVersion":"2026-08-27T08:17:20.692Z"}