ComposioHQ/composio · error · ComposioInvalidModifierError
Invalid schema modifier. Not a function.
Error message
Invalid schema modifier. Not a function.
What it means
ComposioInvalidModifierError thrown in getRawComposioTools when a schema modifier is supplied to the tools listing call but is not a function. The SDK validates the modifier before mapping it over the returned tools.
Source
Thrown at ts/packages/core/src/models/Tools.ts:578
}
const caseTransformedTools = tools.items.map(tool => this.transformToolCases(tool));
let modifiedTools = await this.applyDefaultSchemaModifiers(caseTransformedTools);
// apply local modifiers if they are provided
if (options?.modifySchema) {
const modifier = options.modifySchema;
if (typeof modifier === 'function') {
const modifiedPromises = modifiedTools.map(tool =>
modifier({
toolSlug: tool.slug,
toolkitSlug: tool.toolkit?.slug ?? 'unknown',
schema: tool,
})
);
modifiedTools = await Promise.all(modifiedPromises);
} else {
throw new ComposioInvalidModifierError('Invalid schema modifier. Not a function.');
}
}
return modifiedTools;
}
/**
* Fetches tools exposed by a tool router session.
* This includes helper/meta tools plus any tools preloaded into the session.
* It provides access to the underlying tool data without provider-specific wrapping.
*
* @param sessionId {string} The session id to get tools for
* @param options {SchemaModifierOptions} Optional configuration for tool retrieval
* @param {TransformToolSchemaModifier} [options.modifySchema] - Function to transform the tool schema
* @returns {Promise<ToolList>} The list of session tools
*
* @example
* ```typescriptView on GitHub (pinned to 64b1b85502)
Solutions
- Ensure the second argument to tools.get is a function ({ toolSlug, toolkitSlug, schema }) => schema
- Check typeof modifier where you build the call
- Update to the current modifier callback signature
Example fix
// before
composio.tools.get({ toolkits: ['github'] }, { schemaModifier: 'stripDesc' })
// after
composio.tools.get({ toolkits: ['github'] }, ({ schema }) => schema) Defensive patterns
Strategy: validation
Validate before calling
if (modifier !== undefined && typeof modifier !== 'function') throw new TypeError('modifier must be a function'); Type guard
const isSchemaModifier = (m: unknown): m is TransformToolSchemaModifier => typeof m === 'function';
Try / catch
try { const tools = await composio.tools.get(q, modifier); } catch (e) { if (e instanceof ComposioInvalidModifierError) fixModifier(); else throw e; } Prevention
- Pass modifiers as arrow functions only
- Type the parameter as TransformToolSchemaModifier
When it happens
Trigger: Calling composio.tools.get(query, modifier) or wiring .with({ schemaModifier: ... }) where modifier is null, a string, or an object rather than ({ toolSlug, toolkitSlug, schema }) => schema.
Common situations: Passing modifier config objects from JSON, version mismatch in modifier signature shape, accidental double-wrapping of the modifier.
Related errors
- Invalid beforeExecute modifier. Not a function.
- Invalid afterExecute modifier. Not a function.
- experimental_subAgent() target must be "claude", "codex", or
- Invalid Composio CLI release tag: ${releaseTag}
- Invalid
AI-assisted analysis of ComposioHQ/composio@64b1b85502 (2026-08-28).
Data as JSON: /api/errors/e24eb948a75598ec.
Report an issue: GitHub.