Description
Tapir version: 1.10.12
Scala version: 3.3.3
Given following model
implicit val cfg: Configuration = Configuration.default.withDiscriminator("pet")
sealed trait Pet derives tapir.Schema
case class Cat(
name: String,
) extends Pet
case class Dog(
name: String,
bites: Boolean,
) extends Pet
case class Rat(
name: String
) extends Pet
It will have the following OpenApi specification generated
openapi: 3.1.0
info:
title: Pet
version: Pet
paths: []
components:
schemas:
Cat:
title: Cat
type: object
required:
- name
- pet
properties:
name:
type: string
pet:
type: string
Dog:
title: Dog
type: object
required:
- name
- bites
- pet
properties:
name:
type: string
bites:
type: boolean
pet:
type: string
Pet:
title: Pet
oneOf:
- $ref: '#/components/schemas/Cat'
- $ref: '#/components/schemas/Dog'
- $ref: '#/components/schemas/Rat'
discriminator:
propertyName: pet
mapping:
Cat: '#/components/schemas/Cat'
Dog: '#/components/schemas/Dog'
Rat: '#/components/schemas/Rat'
Rat:
title: Rat
type: object
required:
- name
- pet
properties:
name:
type: string
pet:
type: string
Schemas for Cat
and Rat
are essentially the same and only can be distinguished by discriminator value pet
. However, it seems that OpenAPI specification does not require discriminator to actually be enforced when validating oneOf
type of Schema
definition.
This is answered in the discussion of OpenAPI specification OAI/OpenAPI-Specification#3608 where the suggestion is to use anyOf
instead of oneOf
to make validation work (a library I use does fail the validation of oneOf
because Rat
and Cat
are the similar schemas structurally).
One easy fix for a such problem is to add a validator of type enum
to each discriminator field pet
. So then the definition would become as follows. Such validation will make sure that type Cat
and Rat
are not subsets of each other.
Cat:
title: Cat
type: object
required:
- name
- pet
properties:
name:
type: string
pet:
type: string
enum: [ Cat ]
I would like to make a suggestion to extend sttp.tapir.generic.Configuration
by introducing a new flag as validateDiscriminatorValue: Boolean = false
and then add enum validator in method sttp.tapir.SchemaType.SCoproduct#addDiscriminatorField
.
I can submit a change request if this is accepted