Skip to content

Conversation

dmontagu
Copy link
Contributor

@dmontagu dmontagu commented Jul 10, 2023

Closes #6525

skip change file check

@cloudflare-workers-and-pages
Copy link

cloudflare-workers-and-pages bot commented Jul 10, 2023

Deploying with  Cloudflare Pages  Cloudflare Pages

Latest commit: 35e9586
Status: ✅  Deploy successful!
Preview URL: https://0629540d.pydantic-docs2.pages.dev
Branch Preview URL: https://discriminator-function-valid.pydantic-docs2.pages.dev

View logs

@adriangb
Copy link
Member

Sorry for never linking it to the original issue: #6541

Comment on lines +1253 to +1259
AllowedAnimal = Annotated[Union[CatModel, DogModel], Field(discriminator='name')]

class Model(BaseModel):
x: AllowedAnimal

m = Model(x={'name': 'kitty'})
assert m.x.name == 'cat'
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might be worth confirming a discriminated union was used, either via an error case or a json schema (or both)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was relying on the docs tests for that but I'll add it here too

Comment on lines +433 to +437
elif schema['type'] == 'function-after':
# After validators don't affect the discriminator values
return self._infer_discriminator_values_for_inner_schema(schema['schema'], source)

elif schema['type'] in {'function-before', 'function-wrap', 'function-plain'}:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not sure how you got around typing here but might be worth using _core_utils.is_function_with_inner_schema(

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note that it's not actually equivalent to that function call. We could do something like that, but this works because I'm not actually using any fields from inside schema to generate this error, so I don't need to do any type narrowing of schema.

The reason I did this was because each of those types of validator could affect what goes in, whereas function-after can't, so it's safe to rely on the input discriminator to select the union case to use for type-checking.

Model(x={'name': 'invalid'})
assert exc_info.value.errors(include_url=False) == [
{
'ctx': {'discriminator': "'name'", 'expected_tags': "'kitty', 'cat', 'puppy', 'dog'", 'tag': 'invalid'},
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These should be a list, it’s a 🐛

@dmontagu dmontagu merged commit 5b531d6 into main Jul 11, 2023
@dmontagu dmontagu deleted the discriminator-function-validators branch July 11, 2023 22:24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Discriminator needs literal error when validating literal field
2 participants