ajv: JSONSchemaType doesn't infer nullable types
What version of Ajv are you using? Does the issue happen if you use the latest version? 8.11.2 This issue is not present in 8.11.0
Your typescript code
import { JSONSchemaType } from "ajv";
const schema: JSONSchemaType<{ foo: string | null }> = {
type: "object",
properties: {
foo: { type: "string", nullable: true },
},
required: ["foo"],
};
void schema;
Typescript compiler error messages
Type '{ type: "object"; properties: { foo: { type: "string"; nullable: true; }; }; required: "foo"[]; }' is not assignable to type 'UncheckedJSONSchemaType<{ foo: string | null; }, false>'.
The types of 'properties.foo' are incompatible between these types.
Type '{ type: "string"; nullable: true; }' is not assignable to type '{ $ref: string; } | ({ anyOf: readonly UncheckedJSONSchemaType<string | null, false>[]; } & { [keyword: string]: any; $id?: string | undefined; $ref?: string | undefined; $defs?: Record<...> | undefined; definitions?: Record<...> | undefined; } & { ...; }) | ({ ...; } & ... 1 more ... & { ...; }) | ({ ...; } & ... 2...'.
Types of property 'nullable' are incompatible.
Type 'true' is not assignable to type 'false'.ts(2322)
Describe the change that should be made to address the issue? There should be no TypeScript errors. As mentioned, this does not give any compiler errors in version 8.11.0
Are you going to resolve the issue? I’m not familiar with the internals of ajv
About this issue
- Original URL
- State: open
- Created 2 years ago
- Reactions: 26
- Comments: 15
Seem’s that this is a bug introduced with the commit https://github.com/ajv-validator/ajv/commit/00b3939ba545e87f585b5ee5e93d26f025454fc6
IMO it’s against the JSON Schema specification.
JSON Schema imposes no restrictions on type: JSON Schema can describe any JSON value, including, for example, nullhttp://json-schema.org/draft/2020-12/json-schema-core.htmlAnd from the link @juliensnz posted
It’s important to remember that in JSON, null isn’t equivalent to something being absent.With this change, it became impossible to define a required field that has a null value.
While it should be perfectly fine.
By the way, from this commit message “nullable was enforced for optional parameters” - I think this is also wrong. I might want to have an optional, string field that can’t be null if it’s present. In this case only a string should be accepted or undefined value.
nullshouldn’t be accepted.Nullableandnon-requiredare different things similarly asnulland “absent” are different concepts in JSON.As a workaround I found that this works:
(though I’m not happy about it)
another solution (not prettier) could be to do:
I will top this all with this workaround:
Just see it as a Zen Koan
Hello everyone, who is encountered this issue! What helped me here to get rid of this issue at least temporary:
ajvversion8.11.0typescriptversion5.0.4: for exampletypescript 5.2.2proceeded reproduce this issue even with previously mentioned item.Overall, looks like issue connected not only with ajv, but with typescript dependency changes too, unfortunately, there is not enough time for taking deeper look into possible reasons. Hope, that it will help someone to resolve it locally in your projects and maybe found the root cause and fix it in the next update.
This probably doesn’t help but it appears if you make the field optional (e.g. add
?) then the schema works.e.g.
In my case ajv was coercing
nullvalues to0since the nullable field was an integer – by adding?I was able to addnullable: trueand ajv also stopped coercing.