larksuite/cli · error
schema must declare exactly one of required or optional
Error message
schema must declare exactly one of required or optional
What it means
Every field's schema tag must declare exactly one of `required` or `optional`. Declaring both, or neither, makes the input's nullability/optionality ambiguous, so parseSchemaTag rejects the tag at compile time.
Source
Thrown at shortcuts/common/typed_compile_args.go:495
result.maximum = &v
case "minItems":
v, err := parseNonnegativeInt(value)
if err != nil {
return result, fmt.Errorf("schema minItems: %w", err)
}
result.minItems = &v
case "maxItems":
v, err := parseNonnegativeInt(value)
if err != nil {
return result, fmt.Errorf("schema maxItems: %w", err)
}
result.maxItems = &v
default:
return result, fmt.Errorf("unknown schema token %q", key)
}
}
if result.required == result.optional {
return result, fmt.Errorf("schema must declare exactly one of required or optional")
}
if result.required && result.defaultValue.Set {
return result, fmt.Errorf("required input cannot declare default")
}
if result.nullable != nil && *result.nullable && !isNilCapable(valueType) {
return result, fmt.Errorf("nullable requires a nil-capable Go type")
}
if result.minLength != nil && result.maxLength != nil && *result.minLength > *result.maxLength {
return result, fmt.Errorf("minLength exceeds maxLength")
}
if result.minimum != nil && result.maximum != nil && *result.minimum > *result.maximum {
return result, fmt.Errorf("minimum exceeds maximum")
}
if result.minItems != nil && result.maxItems != nil && *result.minItems > *result.maxItems {
return result, fmt.Errorf("minItems exceeds maxItems")
}
return result, nil
}View on GitHub (pinned to 7fd6ef3c07)
Solutions
- Keep exactly one marker: either required or optional, not both.
- If the field has no schema tag constraints, decide its optionality explicitly.
- Delete the redundant token when converting a field between required and optional.
Example fix
// before Email string `schema:"required;optional;format=email"` // after Email string `schema:"required;format=email"`
Defensive patterns
Strategy: validation
Validate before calling
func exactlyOneRequiredOptional(tag string) bool {
n := 0
for _, tok := range strings.Split(tag, ";") {
if tok == "required" || tok == "optional" {
n++
}
}
return n == 1
} Prevention
- Always end each field's decision with exactly one of required/optional.
- When flipping optionality, delete the old token in the same edit.
- Grep for ';required;optional' or tags missing both before committing.
When it happens
Trigger: A field tagged schema:"required;optional" or a field with a schema tag containing only constraints, e.g. schema:"minLength=3", with no required/optional token.
Common situations: Copy-pasting a constraint-only tag onto a new field, merging two tags and keeping both markers, or refactoring a field from required to optional and forgetting to delete the old token.
Understand the failure class
Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.
Related errors
- schema minItems: %w
- schema maxItems: %w
- unknown schema token %q
- required input cannot declare default
- nullable requires a nil-capable Go type
AI-assisted analysis of larksuite/cli@7fd6ef3c07 (2026-09-04).
Data as JSON: /api/errors/ed54340e16fc43f3.
Report an issue: GitHub.