mcp-ts-core version
0.11.4
Runtime
Bun
Runtime version
Bun 1.3.14
Transport
N/A — build-time linter
OS
macOS
Description
Related: #278
capped-list-no-truncation treats every depth-0 max_* input as a result cap. It correctly covers maxResults and max_rows, but also classifies value-bound filters such as max_depth_km, maxLat, and max_upload_mbps. A top-level array without truncated or totalCount then produces a truncation warning even though the input does not cap result count.
Reproduction
const definition = {
name: 'search',
input: z.object({
max_depth_km: z.number().describe('Maximum depth filter.'),
}),
output: z.object({
nodes: z.array(z.string()).describe('Matching nodes.'),
}),
};
Run bun run lint:mcp with the definition registered.
Actual behavior
The linter reports capped-list-no-truncation because max_depth_km matches the generic max_* arm.
Expected behavior
Value-bound filters should not trigger the rule. Count caps, including camelCase and snake_case forms, should still trigger when their normalized noun correlates with a top-level array output. For example, max_articles should match an articles array and max_result_count should match results.
Additional context
Keep the generic limit, *_limit, per_page, and page_size shapes. truncationAllowlist remains the escape hatch.
Acceptance criteria
- Value-bound inputs such as
max_depth_km, maxLat, max_date, and max_upload_mbps do not trigger the rule.
- Conventional count caps, including camelCase and snake_case forms, still trigger when their normalized noun matches a top-level array and no truncation disclosure exists.
max_result_count and equivalent explicit count suffixes match a results array.
totalCount and truncated remain recognized in enrichment and top-level output.
- Regression coverage covers matching and non-matching names.
Scope
- Correlate the
max_* arm with top-level array output names.
- Keep the existing disclosure and allowlist behavior.
Out of scope
- Matching bare
count, size, n, rows, or records.
- Changing array-output or disclosure conditions.
- A general English pluralizer; normalization only needs the bounded count-noun shapes covered by tests.
Touchpoints
src/linter/rules/enrichment-rules.ts
tests/unit/linter/enrichment-rules.test.ts
tests/unit/linter/validate.test.ts
skills/api-linter/SKILL.md
skills/add-tool/SKILL.md
CLAUDE.md and the per-version release changelog entry
mcp-ts-core version
0.11.4
Runtime
Bun
Runtime version
Bun 1.3.14
Transport
N/A — build-time linter
OS
macOS
Description
Related: #278
capped-list-no-truncationtreats every depth-0max_*input as a result cap. It correctly coversmaxResultsandmax_rows, but also classifies value-bound filters such asmax_depth_km,maxLat, andmax_upload_mbps. A top-level array withouttruncatedortotalCountthen produces a truncation warning even though the input does not cap result count.Reproduction
Run
bun run lint:mcpwith the definition registered.Actual behavior
The linter reports
capped-list-no-truncationbecausemax_depth_kmmatches the genericmax_*arm.Expected behavior
Value-bound filters should not trigger the rule. Count caps, including camelCase and snake_case forms, should still trigger when their normalized noun correlates with a top-level array output. For example,
max_articlesshould match anarticlesarray andmax_result_countshould matchresults.Additional context
Keep the generic
limit,*_limit,per_page, andpage_sizeshapes.truncationAllowlistremains the escape hatch.Acceptance criteria
max_depth_km,maxLat,max_date, andmax_upload_mbpsdo not trigger the rule.max_result_countand equivalent explicit count suffixes match aresultsarray.totalCountandtruncatedremain recognized inenrichmentand top-leveloutput.Scope
max_*arm with top-level array output names.Out of scope
count,size,n,rows, orrecords.Touchpoints
src/linter/rules/enrichment-rules.tstests/unit/linter/enrichment-rules.test.tstests/unit/linter/validate.test.tsskills/api-linter/SKILL.mdskills/add-tool/SKILL.mdCLAUDE.mdand the per-version release changelog entry