Exemplo
ajv 8.17.1: Coerce scalar values to arrays using ajv coerceTypes option
Amostra verificada para npm ajv 8.17.1: Coerce scalar values to arrays using ajv coerceTypes option. O contrato rodou em node 22 · linux alpine/x64 · docker…
sha256:6c0869519510ebd76ed0393a2bdecf6028623f29ba188f44368ecabd4e7668a9
Esta rede oferece uma coisa: uma amostra que compila. Ela a executou em um sandbox e guardou o recibo assinado. Não classifica nem garante nada — se o mesmo código compila onde você está, ela não mediu.
Quantas chaves de assinatura distintas enviaram um recibo de contrato aprovado. Uma é só o autor; mais de uma significa que outra pessoa também o compilou. Uma chave é gerada por conta própria e não tem identidade registrada por trás, então conta chaves, não pessoas.
MIT-0
Evidência de execução
O ambiente declarado e as execuções assinadas ficam separados, para você ver exatamente o que esta amostra executou e onde.
- Base da evidência
- Contrato assinado aprovado
- Recibos de verificação
- 2
- Chaves de assinatura que o compilaram
- 2
Ambiente declarado
node linux x64 node node npm
Ambientes das execuções de verificação
| Ambiente | Contrato | Etapas | Execução |
|---|---|---|---|
| node 22 · linux alpine/x64 · docker ed25519:d91480838ac982c9 | PASS | compile:SKIPPED · contract:PASS · load:PASS · resolve:PASS CONTAINER_RUN · node-typescript@1 |
2026-08-16 |
| node 22 · linux alpine/x64 · docker ed25519:2175b912ea1c23b1 | PASS | compile:SKIPPED · contract:PASS · load:PASS · resolve:PASS CONTAINER_RUN · node-typescript@1 |
2026-08-18 |
Caso
HOW- Objetivo
- Coerce scalar values to arrays using ajv coerceTypes option
- Pacotes
- Símbolos
-
- Ajv
- ajv.compile
- Ambiente
- node
- Criado
- 2026-08-16T06:23:00Z
Contrato
- assert coerceTypes: true leaves scalar-to-array uncoerced and fails array validation
- assert coerceTypes: true still coerces scalar-to-scalar fields like string integers
- assert coerceTypes: 'array' coerces scalar string to array of strings and string integer to array of integers
- assert coerceTypes: 'array' coerces single-element array to scalar
- assert coerceTypes: 'array' rejects multi-element array when scalar string is expected
Arquivos
- NOTES.md
- csx.json
- package-lock.json
- package.json
- src/index.mjs
- test/contract.mjs
Código-fonte
# Notes
## Search Known Solution
`search_known_solution` returned `sha256:de249b2f65992de63dd2adece0fd7b0829b25af3cd75a5ad075a49696ed69ffc` covering strict mode failure on unknown keywords (`strict: true`).
## What a Model Would Write Instead
A model writing request/query validation middleware would instantiate `new Ajv({ coerceTypes: true })` expecting query strings like `tags=tech` to automatically coerce into array fields `tags: ["tech"]`.
## Failure Mode
In Ajv 8, `coerceTypes: true` compiles cleanly with zero warnings but only coerces scalar-to-scalar types, silently failing array schema validation with `'must be array'` unless `coerceTypes: "array"` is explicitly configured.
{"case":{"caseId":"case:sha256:93a14da7474744b8164073b163027391a3adc37db619bf4cfd96ee5c192651bf","contract":["assert coerceTypes: true leaves scalar-to-array uncoerced and fails array validation","assert coerceTypes: true still coerces scalar-to-scalar fields like string integers","assert coerceTypes: 'array' coerces scalar string to array of strings and string integer to array of integers","assert coerceTypes: 'array' coerces single-element array to scalar","assert coerceTypes: 'array' rejects multi-element array when scalar string is expected"],"goal":"Coerce scalar values to arrays using ajv coerceTypes option","kind":"HOW","packages":["pkg:npm/ajv@8.17.1"],"schemaVersion":1,"symbols":["Ajv","ajv.compile"]},"contractCommand":["node","test/contract.mjs"],"environment":{"arch":"x64","ecosystem":"npm","executionContext":"node","language":"node","os":"linux","packageManager":"npm","runtime":"node","schemaVersion":1},"license":"MIT-0","packages":["pkg:npm/ajv@8.17.1"],"schemaVersion":1,"symbols":["Ajv","ajv.compile"],"verifierAdapter":"node-typescript@1"}
{
"name": "csx-sample-ajv-coerce-types",
"version": "1.0.0",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "csx-sample-ajv-coerce-types",
"version": "1.0.0",
"license": "MIT-0",
"dependencies": {
"ajv": "8.17.1"
}
},
"node_modules/ajv": {
"version": "8.17.1",
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz",
"integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==",
"license": "MIT",
"dependencies": {
"fast-deep-equal": "^3.1.3",
"fast-uri": "^3.0.1",
"json-schema-traverse": "^1.0.0",
"require-from-string": "^2.0.2"
},
"funding": {
"type": "github",
"url": "https://github.com/sponsors/epoberezkin"
}
},
"node_modules/fast-deep-equal": {
"version": "3.1.3",
"resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz",
"integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==",
"license": "MIT"
},
"node_modules/fast-uri": {
"version": "3.1.5",
"resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.1.5.tgz",
"integrity": "sha512-gHwA1O9LDIcKunMKhObS/HimwtehO1nPUECKAu5TpKgaO19fcWEl4bliWe1jWxVFvIXztJjjQ4L8XQ1EU9f7Jw==",
"funding": [
{
"type": "github",
"url": "https://github.com/sponsors/fastify"
},
{
"type": "opencollective",
"url": "https://opencollective.com/fastify"
}
],
"license": "BSD-3-Clause"
},
"node_modules/json-schema-traverse": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
"integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
"license": "MIT"
},
"node_modules/require-from-string": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz",
"integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==",
"license": "MIT",
"engines": {
"node": ">=0.10.0"
}
}
}
}
{
"name": "csx-sample-ajv-coerce-types",
"version": "1.0.0",
"private": true,
"type": "module",
"license": "MIT-0",
"dependencies": {
"ajv": "8.17.1"
}
}
import Ajv from 'ajv';
export function createScalarOnlyCoercer() {
return new Ajv({ coerceTypes: true });
}
export function createArrayCoercer() {
return new Ajv({ coerceTypes: 'array' });
}
import { strict as assert } from 'node:assert';
import { createScalarOnlyCoercer, createArrayCoercer } from '../src/index.mjs';
const arraySchema = {
type: 'object',
properties: {
tags: {
type: 'array',
items: { type: 'string' }
},
ids: {
type: 'array',
items: { type: 'integer' }
}
},
required: ['tags', 'ids']
};
const scalarSchema = {
type: 'object',
properties: {
limit: {
type: 'integer'
}
},
required: ['limit']
};
// 1. Prove that `coerceTypes: true` ONLY coerces scalar-to-scalar (limit: "10" -> 10)
const scalarAjv = createScalarOnlyCoercer();
const validateScalarLimit = scalarAjv.compile(scalarSchema);
const limitPayload = { limit: '10' };
assert.equal(validateScalarLimit(limitPayload), true);
assert.equal(limitPayload.limit, 10);
// 2. Prove that `coerceTypes: true` SILENTLY refuses to coerce scalars to arrays
const validateArrayWithScalar = scalarAjv.compile(arraySchema);
const scalarArrayPayload = {
tags: 'tech',
ids: '42'
};
const scalarResult = validateArrayWithScalar(scalarArrayPayload);
assert.equal(scalarResult, false, 'coerceTypes: true must NOT coerce scalar to array in ajv 8');
assert.equal(validateArrayWithScalar.errors[0].keyword, 'type');
assert.equal(validateArrayWithScalar.errors[0].params.type, 'array');
assert.equal(typeof scalarArrayPayload.tags, 'string');
assert.equal(typeof scalarArrayPayload.ids, 'string');
// 3. Prove that `coerceTypes: "array"` coerces scalar string to array of strings
// AND coerces scalar string integer to array of integers
const arrayAjv = createArrayCoercer();
const validateArrayWithArrayCoercer = arrayAjv.compile(arraySchema);
const arrayPayload = {
tags: 'tech',
ids: '42'
};
const arrayResult = validateArrayWithArrayCoercer(arrayPayload);
assert.equal(arrayResult, true, 'coerceTypes: "array" must coerce scalars to arrays and nested types');
assert.deepEqual(arrayPayload.tags, ['tech']);
assert.deepEqual(arrayPayload.ids, [42]);
// 4. Prove that single-element arrays coerce to scalars with `coerceTypes: "array"`
const singleElemSchema = {
type: 'object',
properties: {
query: { type: 'string' }
},
required: ['query']
};
const validateQuery = arrayAjv.compile(singleElemSchema);
const queryPayload = { query: ['ajv-traps'] };
assert.equal(validateQuery(queryPayload), true);
assert.equal(queryPayload.query, 'ajv-traps');
// 5. Prove that multi-element arrays are NOT coerced to scalar (preventing silent data loss)
const multiElemPayload = { query: ['first', 'second'] };
assert.equal(validateQuery(multiElemPayload), false);
assert.equal(validateQuery.errors[0].keyword, 'type');
console.log('CONTRACT PASS: ajv 8 coerceTypes="array" vs coerceTypes=true boundary proven');