Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for re.Pattern #4366

Merged
merged 1 commit into from Aug 12, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions changes/4366-hramezani.md
@@ -0,0 +1 @@
Add support for `re.Pattern`
3 changes: 2 additions & 1 deletion pydantic/fields.py
@@ -1,4 +1,5 @@
import copy
import re
from collections import Counter as CollectionCounter, defaultdict, deque
from collections.abc import Callable, Hashable as CollectionsHashable, Iterable as CollectionsIterable
from typing import (
Expand Down Expand Up @@ -595,7 +596,7 @@ def _type_analysis(self) -> None: # noqa: C901 (ignore complexity)
self.required = False
self.allow_none = True
return
elif self.type_ is Pattern:
elif self.type_ is Pattern or self.type_ is re.Pattern:
# python 3.7 only, Pattern is a typing object but without sub fields
return
elif is_literal_type(self.type_):
Expand Down
2 changes: 1 addition & 1 deletion pydantic/schema.py
Expand Up @@ -803,7 +803,7 @@ def add_field_type_to_schema(field_type: Any, schema_: Dict[str, Any]) -> None:
and then modifies the given `schema` with the information from that type.
"""
for type_, t_schema in field_class_to_schema:
# Fallback for `typing.Pattern` as it is not a valid class
# Fallback for `typing.Pattern` and `re.Pattern` as they are not a valid class
if lenient_issubclass(field_type, type_) or field_type is type_ is Pattern:
schema_.update(t_schema)
break
Expand Down
2 changes: 1 addition & 1 deletion pydantic/validators.py
Expand Up @@ -684,7 +684,7 @@ def find_validators( # noqa: C901 (ignore complexity)
if is_none_type(type_):
yield none_validator
return
if type_ is Pattern:
if type_ is Pattern or type_ is re.Pattern:
yield pattern_validator
return
if type_ is Hashable or type_ is CollectionsHashable:
Expand Down
10 changes: 6 additions & 4 deletions tests/test_types.py
Expand Up @@ -2540,9 +2540,10 @@ class JsonRequired(BaseModel):
assert JsonRequired().dict() == {'json_obj': None}


def test_pattern():
@pytest.mark.parametrize('pattern_type', [re.Pattern, Pattern])
def test_pattern(pattern_type):
class Foobar(BaseModel):
pattern: Pattern
pattern: pattern_type

f = Foobar(pattern=r'^whatev.r\d$')
assert f.pattern.__class__.__name__ == 'Pattern'
Expand All @@ -2563,9 +2564,10 @@ class Foobar(BaseModel):
}


def test_pattern_error():
@pytest.mark.parametrize('pattern_type', [re.Pattern, Pattern])
def test_pattern_error(pattern_type):
class Foobar(BaseModel):
pattern: Pattern
pattern: pattern_type

with pytest.raises(ValidationError) as exc_info:
Foobar(pattern='[xx')
Expand Down