Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
The
Generic-derived schema for polymorphic datatypes is incorrect. The schema for a datatype likedata X a = X{ field :: a }hasfieldas a required property. This means that the schema forX (Maybe something)also hasfieldmarked as a required field. The optionality of theMaybeis forgotten. A service relying on the erroneous schema would expect a non-nullable value, but a service sendingX (Maybe something)values can sendnullin thefieldpropety, but a service relying on the erroneous schema will expect nonullinfield, leading to a runtime error.Given
data X a = X{ field :: a }, theGeneric-derived schema must markfieldas required, because it needs to work for alla. Therefore,instance ToSchema a => ToSchema (Maybe a)has to generate anullableschema to be correct. Then the schema forX (Maybe something)will have required propertyfieldwith anullableschema forsomething.This change changes the
ToSchemainstance forMaybe a. The schema forMaybe ais prefixed withMaybe_to distinguish it from the schema fora. Without this,declareSchemaRefwill generate the same reference for anaor aMaybe a. When an API uses anaand aMaybe a, only one of the two schemas will make it into thecomponents.schemassection (because of the name conflict). This can lead to a schema that says it produces non-nullable values, but may actually produce nulls.This problem could also be solved by changing
declareSchemaRefto strip thenullableproperty from the declared schema and return the nullability value alongside theReferenced Schema. This would increase sharing (you wouldn't have near duplicate schemasXandMaybe_X), and I think it would be cleaner, but at the cost of forcing downstream libraries (such asservant-openapi3) to explicitly handle that nullability information. I chose the solution that's compatible with current downstream code.I think this supercedes the previous attempts at fixing
Maybe:Maybe aschemas #103