nocobase/nocobase · error · FlowSurfaceBadRequestError

flowSurfaces fieldUse '${fieldUse}' is not allowed under '${

Error message

flowSurfaces fieldUse '${fieldUse}' is not allowed under '${input.containerUse}'

What it means

After resolving the effective fieldUse (requested or inferred), resolveSupportedFieldCapability (catalog.ts:3259-3273) validates it against the allowed set for the container: form allows editable uses, details/table allow display uses, filter-form allows filter uses (plus package-registered uses and, in fieldType mode, per-field component uses). A fieldUse outside that set is rejected even if it is a valid use elsewhere.

Source

Thrown at packages/plugins/@nocobase/plugin-flow-engine/src/server/flow-surfaces/catalog.ts:3270

    KNOWN_FIELD_NODE_USES.has(input.requestedFieldUse)
  ) {
    throw new FlowSurfaceBadRequestError(
      `flowSurfaces fieldUse '${input.requestedFieldUse}' does not match inferred fieldUse '${inferredFieldUse}' under '${input.containerUse}'`,
    );
  }

  const allowedFieldUses =
    input.requestedFieldUseMode === 'fieldType' && input.field
      ? getSupportedFieldComponentUseSet({
          containerUse: input.containerUse,
          field: input.field,
          enabledPackages: input.enabledPackages,
          dataSourceKey: input.dataSourceKey,
          getCollection: input.getCollection,
        })
      : getAllowedFieldUseSet(input.containerUse, input.enabledPackages);
  if (!allowedFieldUses?.has(fieldUse)) {
    throw new FlowSurfaceBadRequestError(
      `flowSurfaces fieldUse '${fieldUse}' is not allowed under '${input.containerUse}'`,
    );
  }

  return {
    wrapperUse,
    fieldUse,
    inferredFieldUse,
    standaloneUse: undefined,
    renderer: requestedRenderer,
  };
}

function isActionAllowedInContainer(item: FlowSurfaceCatalogItem, containerUse?: string) {
  if (!containerUse) {
    return true;
  }
  return Array.isArray(item.allowedContainerUses) && item.allowedContainerUses.includes(containerUse);

View on GitHub (pinned to fa42722fef)

Solutions

  1. Use a use from the container's allowed set: editable uses under form, display uses under details/table, filter uses under filter-form.
  2. Ensure the plugin that registers a custom field use is enabled and its use is included in enabledPackages passed to the call.
  3. Fix the use spelling against the current flow-engine catalog (EDITABLE/DISPLAY/FILTER_FIELD_USE_SET members).
  4. If the node was moved between containers, re-resolve its fieldUse for the new container instead of reusing the old value.

Example fix

// before
resolveSupportedFieldCapability({
  containerUse: 'details',
  field,
  requestedFieldUse: 'someEditableFieldModel', // editable-only use
});
// after
resolveSupportedFieldCapability({
  containerUse: 'details',
  field,
  requestedFieldUse: 'someDisplayFieldModel', // display use allowed under details
});
Defensive patterns

Strategy: validation

Validate before calling

const ALLOWED_BY_CONTAINER: Record<string, Set<string>> = {
  form: new Set(['TextInputFieldModel' /* ...all editable uses */]),
  details: new Set([/* display uses */]),
  table: new Set([/* display uses */]),
  'filter-form': new Set([/* filter uses */]),
};
function fieldUseAllowed(containerUse: string, fieldUse: string, registered: Iterable<string> = []) {
  const set = ALLOWED_BY_CONTAINER[containerUse];
  return Boolean(set && (set.has(fieldUse) || new Set(registered).has(fieldUse)));
}

Type guard

function isAllowedFieldUse(u: string, allowed: ReadonlySet<string>): boolean {
  return allowed.has(u);
}

Try / catch

try {
  const cap = resolveSupportedFieldCapability(input);
} catch (e) {
  if (e instanceof FlowSurfaceBadRequestError && /fieldUse .* is not allowed under/.test(e.message)) {
    // re-resolve a container-appropriate use before retrying
    const cap = resolveSupportedFieldCapability({ ...input, requestedFieldUse: undefined });
  } else throw e;
}

Prevention

When it happens

Trigger: Passing a fieldUse that belongs to a different container mode, e.g. an editable use like an input use under containerUse='table', a display use under 'form', or a filter-only use under 'details'; also a custom use from a disabled package (getRegisteredFieldUses filtered by enabledPackages).

Common situations: Moving/copying a field node between form, table, details, and filter-form containers without updating its use; enabling a plugin that registers field uses but not passing enabledPackages; typo in the use name so it matches no allowed set; requests built against an older catalog version.

Related errors


AI-assisted analysis of nocobase/nocobase@fa42722fef (2026-09-01). Data as JSON: /api/errors/ec506cb392416e72. Report an issue: GitHub.