We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
underscore_attrs_are_private and validate_all not compatible with validate_arguments
Output of `python -c "import pydantic.utils; print(pydantic.utils.version_info())"`:
```
             pydantic version: 1.8.2
            pydantic compiled: True
                 install path: /home/xxx/.conda/envs/py38/lib/python3.8/site-packages/pydantic
               python version: 3.8.5 (default, Sep  4 2020, 07:30:14)  [GCC 7.3.0]
                     platform: Linux-4.18.0-80.el8.x86_64-x86_64-with-glibc2.10
     optional deps. installed: ['typing-extensions']
```
`underscore_attrs_are_private` not work with `validate_arguments` just like it not work with `create_model`  #3134 .

When I define a function decorated by `validate_arguments` with `validate_all` been set `True`, It will raise `ValidationError`:

```py
from datetime import datetime
from pydantic import validate_arguments, Field


@validate_arguments(config={'validate_all': True})
def foo(dt: datetime = Field(default_factory=lambda : 42)):
    print(type(dt))

foo()
```
```
---------------------------------------------------------------------------
ValidationError                           Traceback (most recent call last)
<ipython-input-4-6c97ede6fd47> in <module>
      7     print(type(dt))
      8 
----> 9 foo()

~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.validate_arguments.validate.wrapper_function()

~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.ValidatedFunction.call()

~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.ValidatedFunction.init_model_instance()

~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/main.cpython-38-x86_64-linux-gnu.so in pydantic.main.BaseModel.__init__()

ValidationError: 3 validation errors for Foo
v__duplicate_kwargs
  object of type 'NoneType' has no len() (type=type_error)
args
  object of type 'NoneType' has no len() (type=type_error)
kwargs
  object of type 'NoneType' has no len() (type=type_error)
```


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `pydantic/decorator.py`
Content:
```
1 from functools import wraps
2 from typing import TYPE_CHECKING, Any, Callable, Dict, List, Mapping, Optional, Tuple, Type, TypeVar, Union, overload
3 
4 from . import validator
5 from .config import Extra
6 from .errors import ConfigError
7 from .main import BaseModel, create_model
8 from .typing import get_all_type_hints
9 from .utils import to_camel
10 
11 __all__ = ('validate_arguments',)
12 
13 if TYPE_CHECKING:
14     from .typing import AnyCallable
15 
16     AnyCallableT = TypeVar('AnyCallableT', bound=AnyCallable)
17     ConfigType = Union[None, Type[Any], Dict[str, Any]]
18 
19 
20 @overload
21 def validate_arguments(func: None = None, *, config: 'ConfigType' = None) -> Callable[['AnyCallableT'], 'AnyCallableT']:
22     ...
23 
24 
25 @overload
26 def validate_arguments(func: 'AnyCallableT') -> 'AnyCallableT':
27     ...
28 
29 
30 def validate_arguments(func: Optional['AnyCallableT'] = None, *, config: 'ConfigType' = None) -> Any:
31     """
32     Decorator to validate the arguments passed to a function.
33     """
34 
35     def validate(_func: 'AnyCallable') -> 'AnyCallable':
36         vd = ValidatedFunction(_func, config)
37 
38         @wraps(_func)
39         def wrapper_function(*args: Any, **kwargs: Any) -> Any:
40             return vd.call(*args, **kwargs)
41 
42         wrapper_function.vd = vd  # type: ignore
43         wrapper_function.validate = vd.init_model_instance  # type: ignore
44         wrapper_function.raw_function = vd.raw_function  # type: ignore
45         wrapper_function.model = vd.model  # type: ignore
46         return wrapper_function
47 
48     if func:
49         return validate(func)
50     else:
51         return validate
52 
53 
54 ALT_V_ARGS = 'v__args'
55 ALT_V_KWARGS = 'v__kwargs'
56 V_POSITIONAL_ONLY_NAME = 'v__positional_only'
57 V_DUPLICATE_KWARGS = 'v__duplicate_kwargs'
58 
59 
60 class ValidatedFunction:
61     def __init__(self, function: 'AnyCallableT', config: 'ConfigType'):  # noqa C901
62         from inspect import Parameter, signature
63 
64         parameters: Mapping[str, Parameter] = signature(function).parameters
65 
66         if parameters.keys() & {ALT_V_ARGS, ALT_V_KWARGS, V_POSITIONAL_ONLY_NAME, V_DUPLICATE_KWARGS}:
67             raise ConfigError(
68                 f'"{ALT_V_ARGS}", "{ALT_V_KWARGS}", "{V_POSITIONAL_ONLY_NAME}" and "{V_DUPLICATE_KWARGS}" '
69                 f'are not permitted as argument names when using the "{validate_arguments.__name__}" decorator'
70             )
71 
72         self.raw_function = function
73         self.arg_mapping: Dict[int, str] = {}
74         self.positional_only_args = set()
75         self.v_args_name = 'args'
76         self.v_kwargs_name = 'kwargs'
77 
78         type_hints = get_all_type_hints(function)
79         takes_args = False
80         takes_kwargs = False
81         fields: Dict[str, Tuple[Any, Any]] = {}
82         for i, (name, p) in enumerate(parameters.items()):
83             if p.annotation is p.empty:
84                 annotation = Any
85             else:
86                 annotation = type_hints[name]
87 
88             default = ... if p.default is p.empty else p.default
89             if p.kind == Parameter.POSITIONAL_ONLY:
90                 self.arg_mapping[i] = name
91                 fields[name] = annotation, default
92                 fields[V_POSITIONAL_ONLY_NAME] = List[str], None
93                 self.positional_only_args.add(name)
94             elif p.kind == Parameter.POSITIONAL_OR_KEYWORD:
95                 self.arg_mapping[i] = name
96                 fields[name] = annotation, default
97                 fields[V_DUPLICATE_KWARGS] = List[str], None
98             elif p.kind == Parameter.KEYWORD_ONLY:
99                 fields[name] = annotation, default
100             elif p.kind == Parameter.VAR_POSITIONAL:
101                 self.v_args_name = name
102                 fields[name] = Tuple[annotation, ...], None
103                 takes_args = True
104             else:
105                 assert p.kind == Parameter.VAR_KEYWORD, p.kind
106                 self.v_kwargs_name = name
107                 fields[name] = Dict[str, annotation], None  # type: ignore
108                 takes_kwargs = True
109 
110         # these checks avoid a clash between "args" and a field with that name
111         if not takes_args and self.v_args_name in fields:
112             self.v_args_name = ALT_V_ARGS
113 
114         # same with "kwargs"
115         if not takes_kwargs and self.v_kwargs_name in fields:
116             self.v_kwargs_name = ALT_V_KWARGS
117 
118         if not takes_args:
119             # we add the field so validation below can raise the correct exception
120             fields[self.v_args_name] = List[Any], None
121 
122         if not takes_kwargs:
123             # same with kwargs
124             fields[self.v_kwargs_name] = Dict[Any, Any], None
125 
126         self.create_model(fields, takes_args, takes_kwargs, config)
127 
128     def init_model_instance(self, *args: Any, **kwargs: Any) -> BaseModel:
129         values = self.build_values(args, kwargs)
130         return self.model(**values)
131 
132     def call(self, *args: Any, **kwargs: Any) -> Any:
133         m = self.init_model_instance(*args, **kwargs)
134         return self.execute(m)
135 
136     def build_values(self, args: Tuple[Any, ...], kwargs: Dict[str, Any]) -> Dict[str, Any]:
137         values: Dict[str, Any] = {}
138         if args:
139             arg_iter = enumerate(args)
140             while True:
141                 try:
142                     i, a = next(arg_iter)
143                 except StopIteration:
144                     break
145                 arg_name = self.arg_mapping.get(i)
146                 if arg_name is not None:
147                     values[arg_name] = a
148                 else:
149                     values[self.v_args_name] = [a] + [a for _, a in arg_iter]
150                     break
151 
152         var_kwargs = {}
153         wrong_positional_args = []
154         duplicate_kwargs = []
155         non_var_fields = set(self.model.__fields__) - {self.v_args_name, self.v_kwargs_name}
156         for k, v in kwargs.items():
157             if k in non_var_fields:
158                 if k in self.positional_only_args:
159                     wrong_positional_args.append(k)
160                 if k in values:
161                     duplicate_kwargs.append(k)
162                 values[k] = v
163             else:
164                 var_kwargs[k] = v
165 
166         if var_kwargs:
167             values[self.v_kwargs_name] = var_kwargs
168         if wrong_positional_args:
169             values[V_POSITIONAL_ONLY_NAME] = wrong_positional_args
170         if duplicate_kwargs:
171             values[V_DUPLICATE_KWARGS] = duplicate_kwargs
172         return values
173 
174     def execute(self, m: BaseModel) -> Any:
175         d = {k: v for k, v in m._iter() if k in m.__fields_set__ or m.__fields__[k].default_factory}
176         var_kwargs = d.pop(self.v_kwargs_name, {})
177 
178         if self.v_args_name in d:
179             args_: List[Any] = []
180             in_kwargs = False
181             kwargs = {}
182             for name, value in d.items():
183                 if in_kwargs:
184                     kwargs[name] = value
185                 elif name == self.v_args_name:
186                     args_ += value
187                     in_kwargs = True
188                 else:
189                     args_.append(value)
190             return self.raw_function(*args_, **kwargs, **var_kwargs)
191         elif self.positional_only_args:
192             args_ = []
193             kwargs = {}
194             for name, value in d.items():
195                 if name in self.positional_only_args:
196                     args_.append(value)
197                 else:
198                     kwargs[name] = value
199             return self.raw_function(*args_, **kwargs, **var_kwargs)
200         else:
201             return self.raw_function(**d, **var_kwargs)
202 
203     def create_model(self, fields: Dict[str, Any], takes_args: bool, takes_kwargs: bool, config: 'ConfigType') -> None:
204         pos_args = len(self.arg_mapping)
205 
206         class CustomConfig:
207             pass
208 
209         if not TYPE_CHECKING:  # pragma: no branch
210             if isinstance(config, dict):
211                 CustomConfig = type('Config', (), config)  # noqa: F811
212             elif config is not None:
213                 CustomConfig = config  # noqa: F811
214 
215         if hasattr(CustomConfig, 'fields') or hasattr(CustomConfig, 'alias_generator'):
216             raise ConfigError(
217                 'Setting the "fields" and "alias_generator" property on custom Config for '
218                 '@validate_arguments is not yet supported, please remove.'
219             )
220 
221         class DecoratorBaseModel(BaseModel):
222             @validator(self.v_args_name, check_fields=False, allow_reuse=True)
223             def check_args(cls, v: List[Any]) -> List[Any]:
224                 if takes_args:
225                     return v
226 
227                 raise TypeError(f'{pos_args} positional arguments expected but {pos_args + len(v)} given')
228 
229             @validator(self.v_kwargs_name, check_fields=False, allow_reuse=True)
230             def check_kwargs(cls, v: Dict[str, Any]) -> Dict[str, Any]:
231                 if takes_kwargs:
232                     return v
233 
234                 plural = '' if len(v) == 1 else 's'
235                 keys = ', '.join(map(repr, v.keys()))
236                 raise TypeError(f'unexpected keyword argument{plural}: {keys}')
237 
238             @validator(V_POSITIONAL_ONLY_NAME, check_fields=False, allow_reuse=True)
239             def check_positional_only(cls, v: List[str]) -> None:
240                 plural = '' if len(v) == 1 else 's'
241                 keys = ', '.join(map(repr, v))
242                 raise TypeError(f'positional-only argument{plural} passed as keyword argument{plural}: {keys}')
243 
244             @validator(V_DUPLICATE_KWARGS, check_fields=False, allow_reuse=True)
245             def check_duplicate_kwargs(cls, v: List[str]) -> None:
246                 plural = '' if len(v) == 1 else 's'
247                 keys = ', '.join(map(repr, v))
248                 raise TypeError(f'multiple values for argument{plural}: {keys}')
249 
250             class Config(CustomConfig):
251                 extra = Extra.forbid
252 
253         self.model = create_model(to_camel(self.raw_function.__name__), __base__=DecoratorBaseModel, **fields)
254
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/pydantic/decorator.py b/pydantic/decorator.py
--- a/pydantic/decorator.py
+++ b/pydantic/decorator.py
@@ -220,15 +220,15 @@
 
         class DecoratorBaseModel(BaseModel):
             @validator(self.v_args_name, check_fields=False, allow_reuse=True)
-            def check_args(cls, v: List[Any]) -> List[Any]:
-                if takes_args:
+            def check_args(cls, v: Optional[List[Any]]) -> Optional[List[Any]]:
+                if takes_args or v is None:
                     return v
 
                 raise TypeError(f'{pos_args} positional arguments expected but {pos_args + len(v)} given')
 
             @validator(self.v_kwargs_name, check_fields=False, allow_reuse=True)
-            def check_kwargs(cls, v: Dict[str, Any]) -> Dict[str, Any]:
-                if takes_kwargs:
+            def check_kwargs(cls, v: Optional[Dict[str, Any]]) -> Optional[Dict[str, Any]]:
+                if takes_kwargs or v is None:
                     return v
 
                 plural = '' if len(v) == 1 else 's'
@@ -236,13 +236,19 @@
                 raise TypeError(f'unexpected keyword argument{plural}: {keys}')
 
             @validator(V_POSITIONAL_ONLY_NAME, check_fields=False, allow_reuse=True)
-            def check_positional_only(cls, v: List[str]) -> None:
+            def check_positional_only(cls, v: Optional[List[str]]) -> None:
+                if v is None:
+                    return
+
                 plural = '' if len(v) == 1 else 's'
                 keys = ', '.join(map(repr, v))
                 raise TypeError(f'positional-only argument{plural} passed as keyword argument{plural}: {keys}')
 
             @validator(V_DUPLICATE_KWARGS, check_fields=False, allow_reuse=True)
-            def check_duplicate_kwargs(cls, v: List[str]) -> None:
+            def check_duplicate_kwargs(cls, v: Optional[List[str]]) -> None:
+                if v is None:
+                    return
+
                 plural = '' if len(v) == 1 else 's'
                 keys = ', '.join(map(repr, v))
                 raise TypeError(f'multiple values for argument{plural}: {keys}')

{"golden_diff": "diff --git a/pydantic/decorator.py b/pydantic/decorator.py\n--- a/pydantic/decorator.py\n+++ b/pydantic/decorator.py\n@@ -220,15 +220,15 @@\n \n         class DecoratorBaseModel(BaseModel):\n             @validator(self.v_args_name, check_fields=False, allow_reuse=True)\n-            def check_args(cls, v: List[Any]) -> List[Any]:\n-                if takes_args:\n+            def check_args(cls, v: Optional[List[Any]]) -> Optional[List[Any]]:\n+                if takes_args or v is None:\n                     return v\n \n                 raise TypeError(f'{pos_args} positional arguments expected but {pos_args + len(v)} given')\n \n             @validator(self.v_kwargs_name, check_fields=False, allow_reuse=True)\n-            def check_kwargs(cls, v: Dict[str, Any]) -> Dict[str, Any]:\n-                if takes_kwargs:\n+            def check_kwargs(cls, v: Optional[Dict[str, Any]]) -> Optional[Dict[str, Any]]:\n+                if takes_kwargs or v is None:\n                     return v\n \n                 plural = '' if len(v) == 1 else 's'\n@@ -236,13 +236,19 @@\n                 raise TypeError(f'unexpected keyword argument{plural}: {keys}')\n \n             @validator(V_POSITIONAL_ONLY_NAME, check_fields=False, allow_reuse=True)\n-            def check_positional_only(cls, v: List[str]) -> None:\n+            def check_positional_only(cls, v: Optional[List[str]]) -> None:\n+                if v is None:\n+                    return\n+\n                 plural = '' if len(v) == 1 else 's'\n                 keys = ', '.join(map(repr, v))\n                 raise TypeError(f'positional-only argument{plural} passed as keyword argument{plural}: {keys}')\n \n             @validator(V_DUPLICATE_KWARGS, check_fields=False, allow_reuse=True)\n-            def check_duplicate_kwargs(cls, v: List[str]) -> None:\n+            def check_duplicate_kwargs(cls, v: Optional[List[str]]) -> None:\n+                if v is None:\n+                    return\n+\n                 plural = '' if len(v) == 1 else 's'\n                 keys = ', '.join(map(repr, v))\n                 raise TypeError(f'multiple values for argument{plural}: {keys}')\n", "issue": "underscore_attrs_are_private and validate_all not compatible with validate_arguments\nOutput of `python -c \"import pydantic.utils; print(pydantic.utils.version_info())\"`:\r\n```\r\n             pydantic version: 1.8.2\r\n            pydantic compiled: True\r\n                 install path: /home/xxx/.conda/envs/py38/lib/python3.8/site-packages/pydantic\r\n               python version: 3.8.5 (default, Sep  4 2020, 07:30:14)  [GCC 7.3.0]\r\n                     platform: Linux-4.18.0-80.el8.x86_64-x86_64-with-glibc2.10\r\n     optional deps. installed: ['typing-extensions']\r\n```\r\n`underscore_attrs_are_private` not work with `validate_arguments` just like it not work with `create_model`  #3134 .\r\n\r\nWhen I define a function decorated by `validate_arguments` with `validate_all` been set `True`, It will raise `ValidationError`:\r\n\r\n```py\r\nfrom datetime import datetime\r\nfrom pydantic import validate_arguments, Field\r\n\r\n\r\n@validate_arguments(config={'validate_all': True})\r\ndef foo(dt: datetime = Field(default_factory=lambda : 42)):\r\n    print(type(dt))\r\n\r\nfoo()\r\n```\r\n```\r\n---------------------------------------------------------------------------\r\nValidationError                           Traceback (most recent call last)\r\n<ipython-input-4-6c97ede6fd47> in <module>\r\n      7     print(type(dt))\r\n      8 \r\n----> 9 foo()\r\n\r\n~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.validate_arguments.validate.wrapper_function()\r\n\r\n~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.ValidatedFunction.call()\r\n\r\n~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/decorator.cpython-38-x86_64-linux-gnu.so in pydantic.decorator.ValidatedFunction.init_model_instance()\r\n\r\n~/.conda/envs/py38/lib/python3.8/site-packages/pydantic/main.cpython-38-x86_64-linux-gnu.so in pydantic.main.BaseModel.__init__()\r\n\r\nValidationError: 3 validation errors for Foo\r\nv__duplicate_kwargs\r\n  object of type 'NoneType' has no len() (type=type_error)\r\nargs\r\n  object of type 'NoneType' has no len() (type=type_error)\r\nkwargs\r\n  object of type 'NoneType' has no len() (type=type_error)\r\n```\r\n\n", "before_files": [{"content": "from functools import wraps\nfrom typing import TYPE_CHECKING, Any, Callable, Dict, List, Mapping, Optional, Tuple, Type, TypeVar, Union, overload\n\nfrom . import validator\nfrom .config import Extra\nfrom .errors import ConfigError\nfrom .main import BaseModel, create_model\nfrom .typing import get_all_type_hints\nfrom .utils import to_camel\n\n__all__ = ('validate_arguments',)\n\nif TYPE_CHECKING:\n    from .typing import AnyCallable\n\n    AnyCallableT = TypeVar('AnyCallableT', bound=AnyCallable)\n    ConfigType = Union[None, Type[Any], Dict[str, Any]]\n\n\n@overload\ndef validate_arguments(func: None = None, *, config: 'ConfigType' = None) -> Callable[['AnyCallableT'], 'AnyCallableT']:\n    ...\n\n\n@overload\ndef validate_arguments(func: 'AnyCallableT') -> 'AnyCallableT':\n    ...\n\n\ndef validate_arguments(func: Optional['AnyCallableT'] = None, *, config: 'ConfigType' = None) -> Any:\n    \"\"\"\n    Decorator to validate the arguments passed to a function.\n    \"\"\"\n\n    def validate(_func: 'AnyCallable') -> 'AnyCallable':\n        vd = ValidatedFunction(_func, config)\n\n        @wraps(_func)\n        def wrapper_function(*args: Any, **kwargs: Any) -> Any:\n            return vd.call(*args, **kwargs)\n\n        wrapper_function.vd = vd  # type: ignore\n        wrapper_function.validate = vd.init_model_instance  # type: ignore\n        wrapper_function.raw_function = vd.raw_function  # type: ignore\n        wrapper_function.model = vd.model  # type: ignore\n        return wrapper_function\n\n    if func:\n        return validate(func)\n    else:\n        return validate\n\n\nALT_V_ARGS = 'v__args'\nALT_V_KWARGS = 'v__kwargs'\nV_POSITIONAL_ONLY_NAME = 'v__positional_only'\nV_DUPLICATE_KWARGS = 'v__duplicate_kwargs'\n\n\nclass ValidatedFunction:\n    def __init__(self, function: 'AnyCallableT', config: 'ConfigType'):  # noqa C901\n        from inspect import Parameter, signature\n\n        parameters: Mapping[str, Parameter] = signature(function).parameters\n\n        if parameters.keys() & {ALT_V_ARGS, ALT_V_KWARGS, V_POSITIONAL_ONLY_NAME, V_DUPLICATE_KWARGS}:\n            raise ConfigError(\n                f'\"{ALT_V_ARGS}\", \"{ALT_V_KWARGS}\", \"{V_POSITIONAL_ONLY_NAME}\" and \"{V_DUPLICATE_KWARGS}\" '\n                f'are not permitted as argument names when using the \"{validate_arguments.__name__}\" decorator'\n            )\n\n        self.raw_function = function\n        self.arg_mapping: Dict[int, str] = {}\n        self.positional_only_args = set()\n        self.v_args_name = 'args'\n        self.v_kwargs_name = 'kwargs'\n\n        type_hints = get_all_type_hints(function)\n        takes_args = False\n        takes_kwargs = False\n        fields: Dict[str, Tuple[Any, Any]] = {}\n        for i, (name, p) in enumerate(parameters.items()):\n            if p.annotation is p.empty:\n                annotation = Any\n            else:\n                annotation = type_hints[name]\n\n            default = ... if p.default is p.empty else p.default\n            if p.kind == Parameter.POSITIONAL_ONLY:\n                self.arg_mapping[i] = name\n                fields[name] = annotation, default\n                fields[V_POSITIONAL_ONLY_NAME] = List[str], None\n                self.positional_only_args.add(name)\n            elif p.kind == Parameter.POSITIONAL_OR_KEYWORD:\n                self.arg_mapping[i] = name\n                fields[name] = annotation, default\n                fields[V_DUPLICATE_KWARGS] = List[str], None\n            elif p.kind == Parameter.KEYWORD_ONLY:\n                fields[name] = annotation, default\n            elif p.kind == Parameter.VAR_POSITIONAL:\n                self.v_args_name = name\n                fields[name] = Tuple[annotation, ...], None\n                takes_args = True\n            else:\n                assert p.kind == Parameter.VAR_KEYWORD, p.kind\n                self.v_kwargs_name = name\n                fields[name] = Dict[str, annotation], None  # type: ignore\n                takes_kwargs = True\n\n        # these checks avoid a clash between \"args\" and a field with that name\n        if not takes_args and self.v_args_name in fields:\n            self.v_args_name = ALT_V_ARGS\n\n        # same with \"kwargs\"\n        if not takes_kwargs and self.v_kwargs_name in fields:\n            self.v_kwargs_name = ALT_V_KWARGS\n\n        if not takes_args:\n            # we add the field so validation below can raise the correct exception\n            fields[self.v_args_name] = List[Any], None\n\n        if not takes_kwargs:\n            # same with kwargs\n            fields[self.v_kwargs_name] = Dict[Any, Any], None\n\n        self.create_model(fields, takes_args, takes_kwargs, config)\n\n    def init_model_instance(self, *args: Any, **kwargs: Any) -> BaseModel:\n        values = self.build_values(args, kwargs)\n        return self.model(**values)\n\n    def call(self, *args: Any, **kwargs: Any) -> Any:\n        m = self.init_model_instance(*args, **kwargs)\n        return self.execute(m)\n\n    def build_values(self, args: Tuple[Any, ...], kwargs: Dict[str, Any]) -> Dict[str, Any]:\n        values: Dict[str, Any] = {}\n        if args:\n            arg_iter = enumerate(args)\n            while True:\n                try:\n                    i, a = next(arg_iter)\n                except StopIteration:\n                    break\n                arg_name = self.arg_mapping.get(i)\n                if arg_name is not None:\n                    values[arg_name] = a\n                else:\n                    values[self.v_args_name] = [a] + [a for _, a in arg_iter]\n                    break\n\n        var_kwargs = {}\n        wrong_positional_args = []\n        duplicate_kwargs = []\n        non_var_fields = set(self.model.__fields__) - {self.v_args_name, self.v_kwargs_name}\n        for k, v in kwargs.items():\n            if k in non_var_fields:\n                if k in self.positional_only_args:\n                    wrong_positional_args.append(k)\n                if k in values:\n                    duplicate_kwargs.append(k)\n                values[k] = v\n            else:\n                var_kwargs[k] = v\n\n        if var_kwargs:\n            values[self.v_kwargs_name] = var_kwargs\n        if wrong_positional_args:\n            values[V_POSITIONAL_ONLY_NAME] = wrong_positional_args\n        if duplicate_kwargs:\n            values[V_DUPLICATE_KWARGS] = duplicate_kwargs\n        return values\n\n    def execute(self, m: BaseModel) -> Any:\n        d = {k: v for k, v in m._iter() if k in m.__fields_set__ or m.__fields__[k].default_factory}\n        var_kwargs = d.pop(self.v_kwargs_name, {})\n\n        if self.v_args_name in d:\n            args_: List[Any] = []\n            in_kwargs = False\n            kwargs = {}\n            for name, value in d.items():\n                if in_kwargs:\n                    kwargs[name] = value\n                elif name == self.v_args_name:\n                    args_ += value\n                    in_kwargs = True\n                else:\n                    args_.append(value)\n            return self.raw_function(*args_, **kwargs, **var_kwargs)\n        elif self.positional_only_args:\n            args_ = []\n            kwargs = {}\n            for name, value in d.items():\n                if name in self.positional_only_args:\n                    args_.append(value)\n                else:\n                    kwargs[name] = value\n            return self.raw_function(*args_, **kwargs, **var_kwargs)\n        else:\n            return self.raw_function(**d, **var_kwargs)\n\n    def create_model(self, fields: Dict[str, Any], takes_args: bool, takes_kwargs: bool, config: 'ConfigType') -> None:\n        pos_args = len(self.arg_mapping)\n\n        class CustomConfig:\n            pass\n\n        if not TYPE_CHECKING:  # pragma: no branch\n            if isinstance(config, dict):\n                CustomConfig = type('Config', (), config)  # noqa: F811\n            elif config is not None:\n                CustomConfig = config  # noqa: F811\n\n        if hasattr(CustomConfig, 'fields') or hasattr(CustomConfig, 'alias_generator'):\n            raise ConfigError(\n                'Setting the \"fields\" and \"alias_generator\" property on custom Config for '\n                '@validate_arguments is not yet supported, please remove.'\n            )\n\n        class DecoratorBaseModel(BaseModel):\n            @validator(self.v_args_name, check_fields=False, allow_reuse=True)\n            def check_args(cls, v: List[Any]) -> List[Any]:\n                if takes_args:\n                    return v\n\n                raise TypeError(f'{pos_args} positional arguments expected but {pos_args + len(v)} given')\n\n            @validator(self.v_kwargs_name, check_fields=False, allow_reuse=True)\n            def check_kwargs(cls, v: Dict[str, Any]) -> Dict[str, Any]:\n                if takes_kwargs:\n                    return v\n\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v.keys()))\n                raise TypeError(f'unexpected keyword argument{plural}: {keys}')\n\n            @validator(V_POSITIONAL_ONLY_NAME, check_fields=False, allow_reuse=True)\n            def check_positional_only(cls, v: List[str]) -> None:\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v))\n                raise TypeError(f'positional-only argument{plural} passed as keyword argument{plural}: {keys}')\n\n            @validator(V_DUPLICATE_KWARGS, check_fields=False, allow_reuse=True)\n            def check_duplicate_kwargs(cls, v: List[str]) -> None:\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v))\n                raise TypeError(f'multiple values for argument{plural}: {keys}')\n\n            class Config(CustomConfig):\n                extra = Extra.forbid\n\n        self.model = create_model(to_camel(self.raw_function.__name__), __base__=DecoratorBaseModel, **fields)\n", "path": "pydantic/decorator.py"}], "after_files": [{"content": "from functools import wraps\nfrom typing import TYPE_CHECKING, Any, Callable, Dict, List, Mapping, Optional, Tuple, Type, TypeVar, Union, overload\n\nfrom . import validator\nfrom .config import Extra\nfrom .errors import ConfigError\nfrom .main import BaseModel, create_model\nfrom .typing import get_all_type_hints\nfrom .utils import to_camel\n\n__all__ = ('validate_arguments',)\n\nif TYPE_CHECKING:\n    from .typing import AnyCallable\n\n    AnyCallableT = TypeVar('AnyCallableT', bound=AnyCallable)\n    ConfigType = Union[None, Type[Any], Dict[str, Any]]\n\n\n@overload\ndef validate_arguments(func: None = None, *, config: 'ConfigType' = None) -> Callable[['AnyCallableT'], 'AnyCallableT']:\n    ...\n\n\n@overload\ndef validate_arguments(func: 'AnyCallableT') -> 'AnyCallableT':\n    ...\n\n\ndef validate_arguments(func: Optional['AnyCallableT'] = None, *, config: 'ConfigType' = None) -> Any:\n    \"\"\"\n    Decorator to validate the arguments passed to a function.\n    \"\"\"\n\n    def validate(_func: 'AnyCallable') -> 'AnyCallable':\n        vd = ValidatedFunction(_func, config)\n\n        @wraps(_func)\n        def wrapper_function(*args: Any, **kwargs: Any) -> Any:\n            return vd.call(*args, **kwargs)\n\n        wrapper_function.vd = vd  # type: ignore\n        wrapper_function.validate = vd.init_model_instance  # type: ignore\n        wrapper_function.raw_function = vd.raw_function  # type: ignore\n        wrapper_function.model = vd.model  # type: ignore\n        return wrapper_function\n\n    if func:\n        return validate(func)\n    else:\n        return validate\n\n\nALT_V_ARGS = 'v__args'\nALT_V_KWARGS = 'v__kwargs'\nV_POSITIONAL_ONLY_NAME = 'v__positional_only'\nV_DUPLICATE_KWARGS = 'v__duplicate_kwargs'\n\n\nclass ValidatedFunction:\n    def __init__(self, function: 'AnyCallableT', config: 'ConfigType'):  # noqa C901\n        from inspect import Parameter, signature\n\n        parameters: Mapping[str, Parameter] = signature(function).parameters\n\n        if parameters.keys() & {ALT_V_ARGS, ALT_V_KWARGS, V_POSITIONAL_ONLY_NAME, V_DUPLICATE_KWARGS}:\n            raise ConfigError(\n                f'\"{ALT_V_ARGS}\", \"{ALT_V_KWARGS}\", \"{V_POSITIONAL_ONLY_NAME}\" and \"{V_DUPLICATE_KWARGS}\" '\n                f'are not permitted as argument names when using the \"{validate_arguments.__name__}\" decorator'\n            )\n\n        self.raw_function = function\n        self.arg_mapping: Dict[int, str] = {}\n        self.positional_only_args = set()\n        self.v_args_name = 'args'\n        self.v_kwargs_name = 'kwargs'\n\n        type_hints = get_all_type_hints(function)\n        takes_args = False\n        takes_kwargs = False\n        fields: Dict[str, Tuple[Any, Any]] = {}\n        for i, (name, p) in enumerate(parameters.items()):\n            if p.annotation is p.empty:\n                annotation = Any\n            else:\n                annotation = type_hints[name]\n\n            default = ... if p.default is p.empty else p.default\n            if p.kind == Parameter.POSITIONAL_ONLY:\n                self.arg_mapping[i] = name\n                fields[name] = annotation, default\n                fields[V_POSITIONAL_ONLY_NAME] = List[str], None\n                self.positional_only_args.add(name)\n            elif p.kind == Parameter.POSITIONAL_OR_KEYWORD:\n                self.arg_mapping[i] = name\n                fields[name] = annotation, default\n                fields[V_DUPLICATE_KWARGS] = List[str], None\n            elif p.kind == Parameter.KEYWORD_ONLY:\n                fields[name] = annotation, default\n            elif p.kind == Parameter.VAR_POSITIONAL:\n                self.v_args_name = name\n                fields[name] = Tuple[annotation, ...], None\n                takes_args = True\n            else:\n                assert p.kind == Parameter.VAR_KEYWORD, p.kind\n                self.v_kwargs_name = name\n                fields[name] = Dict[str, annotation], None  # type: ignore\n                takes_kwargs = True\n\n        # these checks avoid a clash between \"args\" and a field with that name\n        if not takes_args and self.v_args_name in fields:\n            self.v_args_name = ALT_V_ARGS\n\n        # same with \"kwargs\"\n        if not takes_kwargs and self.v_kwargs_name in fields:\n            self.v_kwargs_name = ALT_V_KWARGS\n\n        if not takes_args:\n            # we add the field so validation below can raise the correct exception\n            fields[self.v_args_name] = List[Any], None\n\n        if not takes_kwargs:\n            # same with kwargs\n            fields[self.v_kwargs_name] = Dict[Any, Any], None\n\n        self.create_model(fields, takes_args, takes_kwargs, config)\n\n    def init_model_instance(self, *args: Any, **kwargs: Any) -> BaseModel:\n        values = self.build_values(args, kwargs)\n        return self.model(**values)\n\n    def call(self, *args: Any, **kwargs: Any) -> Any:\n        m = self.init_model_instance(*args, **kwargs)\n        return self.execute(m)\n\n    def build_values(self, args: Tuple[Any, ...], kwargs: Dict[str, Any]) -> Dict[str, Any]:\n        values: Dict[str, Any] = {}\n        if args:\n            arg_iter = enumerate(args)\n            while True:\n                try:\n                    i, a = next(arg_iter)\n                except StopIteration:\n                    break\n                arg_name = self.arg_mapping.get(i)\n                if arg_name is not None:\n                    values[arg_name] = a\n                else:\n                    values[self.v_args_name] = [a] + [a for _, a in arg_iter]\n                    break\n\n        var_kwargs = {}\n        wrong_positional_args = []\n        duplicate_kwargs = []\n        non_var_fields = set(self.model.__fields__) - {self.v_args_name, self.v_kwargs_name}\n        for k, v in kwargs.items():\n            if k in non_var_fields:\n                if k in self.positional_only_args:\n                    wrong_positional_args.append(k)\n                if k in values:\n                    duplicate_kwargs.append(k)\n                values[k] = v\n            else:\n                var_kwargs[k] = v\n\n        if var_kwargs:\n            values[self.v_kwargs_name] = var_kwargs\n        if wrong_positional_args:\n            values[V_POSITIONAL_ONLY_NAME] = wrong_positional_args\n        if duplicate_kwargs:\n            values[V_DUPLICATE_KWARGS] = duplicate_kwargs\n        return values\n\n    def execute(self, m: BaseModel) -> Any:\n        d = {k: v for k, v in m._iter() if k in m.__fields_set__ or m.__fields__[k].default_factory}\n        var_kwargs = d.pop(self.v_kwargs_name, {})\n\n        if self.v_args_name in d:\n            args_: List[Any] = []\n            in_kwargs = False\n            kwargs = {}\n            for name, value in d.items():\n                if in_kwargs:\n                    kwargs[name] = value\n                elif name == self.v_args_name:\n                    args_ += value\n                    in_kwargs = True\n                else:\n                    args_.append(value)\n            return self.raw_function(*args_, **kwargs, **var_kwargs)\n        elif self.positional_only_args:\n            args_ = []\n            kwargs = {}\n            for name, value in d.items():\n                if name in self.positional_only_args:\n                    args_.append(value)\n                else:\n                    kwargs[name] = value\n            return self.raw_function(*args_, **kwargs, **var_kwargs)\n        else:\n            return self.raw_function(**d, **var_kwargs)\n\n    def create_model(self, fields: Dict[str, Any], takes_args: bool, takes_kwargs: bool, config: 'ConfigType') -> None:\n        pos_args = len(self.arg_mapping)\n\n        class CustomConfig:\n            pass\n\n        if not TYPE_CHECKING:  # pragma: no branch\n            if isinstance(config, dict):\n                CustomConfig = type('Config', (), config)  # noqa: F811\n            elif config is not None:\n                CustomConfig = config  # noqa: F811\n\n        if hasattr(CustomConfig, 'fields') or hasattr(CustomConfig, 'alias_generator'):\n            raise ConfigError(\n                'Setting the \"fields\" and \"alias_generator\" property on custom Config for '\n                '@validate_arguments is not yet supported, please remove.'\n            )\n\n        class DecoratorBaseModel(BaseModel):\n            @validator(self.v_args_name, check_fields=False, allow_reuse=True)\n            def check_args(cls, v: Optional[List[Any]]) -> Optional[List[Any]]:\n                if takes_args or v is None:\n                    return v\n\n                raise TypeError(f'{pos_args} positional arguments expected but {pos_args + len(v)} given')\n\n            @validator(self.v_kwargs_name, check_fields=False, allow_reuse=True)\n            def check_kwargs(cls, v: Optional[Dict[str, Any]]) -> Optional[Dict[str, Any]]:\n                if takes_kwargs or v is None:\n                    return v\n\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v.keys()))\n                raise TypeError(f'unexpected keyword argument{plural}: {keys}')\n\n            @validator(V_POSITIONAL_ONLY_NAME, check_fields=False, allow_reuse=True)\n            def check_positional_only(cls, v: Optional[List[str]]) -> None:\n                if v is None:\n                    return\n\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v))\n                raise TypeError(f'positional-only argument{plural} passed as keyword argument{plural}: {keys}')\n\n            @validator(V_DUPLICATE_KWARGS, check_fields=False, allow_reuse=True)\n            def check_duplicate_kwargs(cls, v: Optional[List[str]]) -> None:\n                if v is None:\n                    return\n\n                plural = '' if len(v) == 1 else 's'\n                keys = ', '.join(map(repr, v))\n                raise TypeError(f'multiple values for argument{plural}: {keys}')\n\n            class Config(CustomConfig):\n                extra = Extra.forbid\n\n        self.model = create_model(to_camel(self.raw_function.__name__), __base__=DecoratorBaseModel, **fields)\n", "path": "pydantic/decorator.py"}]}