siyuan-note/siyuan · error

config.inputSchema is required

Error message

config.inputSchema is required

What it means

The config object did not include an inputSchema property (it was missing, undefined, or null). inputSchema is required because it defines the JSON Schema of the arguments the agent will pass to the capability handler; without it the kernel cannot validate or describe the tool's inputs.

Solutions

  1. Add an inputSchema JSON-Schema object describing the handler's arguments (e.g. { type: "object", properties: {...} })
  2. Use a minimal { type: "object" } schema if the tool takes no arguments
  3. Check that inputSchema is not set to null

Example fix

// before
plugin.registerCapability("search", { description: "Search notes" }, handler);
// after
plugin.registerCapability("search", { description: "Search notes", inputSchema: { type: "object", properties: { query: { type: "string" } }, required: ["query"] } }, handler);
Defensive patterns

Strategy: validation

Validate before calling

if (!config?.inputSchema || config.inputSchema === null) { throw new Error("config.inputSchema is required"); }

Type guard

const hasInputSchema = (c) => c != null && c.inputSchema != null && typeof c.inputSchema === "object";

Try / catch

try { plugin.registerCapability(name, config, handler); } catch (e) { if (String(e).includes("config.inputSchema is required")) { config.inputSchema = { type: "object" }; return plugin.registerCapability(name, config, handler); } throw e; }

Prevention

When it happens

Trigger: registerCapability(name, { description: "..." }, handler) with inputSchema omitted, or inputSchema explicitly set to null.

Common situations: Migrating from an older registration API that had no schema requirement; configs shared between plugins where the schema section was dropped; assuming inputSchema is optional like outputSchema.

Understand the failure class

Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.

Related errors


AI-assisted analysis of siyuan-note/siyuan@9f775e8a12 (2026-09-19). Data as JSON: /api/errors/6de4ac942c643e0e. Report an issue: GitHub.

Appendix: source

Thrown at kernel/plugin/api_agent.go:105

						if titleValue := configObj.Get("title"); goja.IsString(titleValue) {
							title = titleValue.String()
						}
						if descriptionValue := configObj.Get("description"); goja.IsString(descriptionValue) {
							description = strings.TrimSpace(descriptionValue.String())
							if description == "" {
								err = fmt.Errorf("config.description must not be empty")
								return
							}
						} else {
							err = fmt.Errorf("config.description is required and must be a string")
							return
						}
						if inputSchemaValue := configObj.Get("inputSchema"); isJsValueNotNull(inputSchemaValue) {
							if inputSchema, err = jsCapabilitySchemaToGoSchema(rt, inputSchemaValue); err != nil {
								return
							}
						} else {
							err = fmt.Errorf("config.inputSchema is required")
							return
						}
						if outputSchemaValue := configObj.Get("outputSchema"); isJsValueNotNull(outputSchemaValue) {
							if outputSchema, err = jsCapabilitySchemaToGoSchema(rt, outputSchemaValue); err != nil {
								return
							}
						}
						if effectsValue := configObj.Get("effects"); isJsValueNotNull(effectsValue) {
							if effects, err = jsCapabilityEffectsToGoEffects(rt, effectsValue); err != nil {
								return
							}
						}
						if actionEffectsValue := configObj.Get("actionEffects"); isJsValueNotNull(actionEffectsValue) {
							if actionEffects, err = jsCapabilityActionEffectsToGoEffects(rt, actionEffectsValue); err != nil {
								return
							}
						}
					}

View on GitHub (pinned to 9f775e8a12)