Skip to content

Nullables #256

@XenosEleatikos

Description

@XenosEleatikos

Hey there,

I think there is a bug in how "nullable" is handled during schema validation.

According to the OpenAPI 3.0.4 specification:

Field Name Type Description
nullable boolean This keyword only takes effect if type is explicitly defined within the same Schema Object. A true value indicates that both null values and values of the type specified by type are allowed. Other Schema Object constraints retain their defined behavior, and therefore may disallow the use of null as a value. The default value is false.

https://github.com/OAI/OpenAPI-Specification/blob/main/versions/3.0.4.md

Currently, in \League\OpenAPIValidation\Schema\SchemaValidator::validate, nullable is assumed to be true by default:

        (new Nullable($schema))->validate($data, $schema->nullable ?? true);

This contradicts the spec, which clearly states that the default must be false.

Moreover, there is a test that appears to rely on the incorrect behavior:
\League\OpenAPIValidation\Tests\FromCommunity\NullableSchemaTest::testNullableImplicitResult
— it implicitly assumes nullable = true, which shouldn't be the case.

However, simply changing the default to false will break another test cases:

\League\OpenAPIValidation\Tests\FromCommunity\IssueWithNullableMergeTest::testNullableMergeOneOf

That test uses a oneOf schema where one of the alternatives is nullable. But null is not accepted unless nullable is handled differently at that level. So this looks like a broader issue with how nullable and composed schemas like oneOf are validated.

As an initial workaround, I tried this:

        if (!$schema->oneOf) {
            (new Nullable($schema))->validate($data, $schema->nullable ?? false);
        }

…but I suspect the issue needs a more general solution in how nullability is resolved across composed schemas.

Let me know what you think — happy to help with a PR if needed!

Best regards,
Christoph

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions