prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  `strawberry.directive` type hints appear to be incorrect.
  <!-- Provide a general summary of the bug in the title above. -->
  
  <!--- This template is entirely optional and can be removed, but is here to help both you and us. -->
  <!--- Anything on lines wrapped in comments like these will not show up in the final text. -->
  
  ## Describe the Bug
  
  A function like:
  
  ```py
  @strawberry.directive(
      locations=[DirectiveLocation.FRAGMENT_DEFINITION],
      description="Do nothing, but add a base class for query generation in the python client.",
  )
  def identity(value: str, a: str, b: str | None = None) -> str:
      """Do nothing, but add a directive so that the python client can use this to add metadata."""
      return value
  
  reveal_type(identity)
  ```
  
  `mypy` will say that the revealed type here is `builtins.str`.  Looking at the code for `directive`, it appears that the type hints imply that the decorated object is going to return the same type that the function returns (in this case, the return type of `identity`)
  
  
  ## System Information
  
   - Operating system:
   - Strawberry version (if applicable):
  
  ## Additional Context
  
  <!-- Add any other relevant information about the problem here. -->
  
  
  <!-- POLAR PLEDGE BADGE START -->
  ## Upvote & Fund
  
  - We're using [Polar.sh](https://polar.sh/strawberry-graphql) so you can upvote and help fund this issue.
  - We receive the funding once the issue is completed & confirmed by you.
  - Thank you in advance for helping prioritize & fund our backlog.
  
  <a href="https://polar.sh/strawberry-graphql/strawberry/issues/2846">
  <picture>
    <source media="(prefers-color-scheme: dark)" srcset="https://polar.sh/api/github/strawberry-graphql/strawberry/issues/2846/pledge.svg?darkmode=1">
    <img alt="Fund with Polar" src="https://polar.sh/api/github/strawberry-graphql/strawberry/issues/2846/pledge.svg">
  </picture>
  </a>
  <!-- POLAR PLEDGE BADGE END -->
  
  
  --- END ISSUE ---
  
  Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
  --- BEGIN FILES ---
  Path: `strawberry/directive.py`
  Content:
  ```
  1 from __future__ import annotations
  2 
  3 import dataclasses
  4 from typing import TYPE_CHECKING, Any, Callable, List, Optional, TypeVar
  5 from typing_extensions import Annotated
  6 
  7 from graphql import DirectiveLocation
  8 
  9 from strawberry.field import StrawberryField
  10 from strawberry.types.fields.resolver import (
  11     INFO_PARAMSPEC,
  12     ReservedType,
  13     StrawberryResolver,
  14 )
  15 from strawberry.unset import UNSET
  16 from strawberry.utils.cached_property import cached_property
  17 
  18 if TYPE_CHECKING:
  19     import inspect
  20 
  21     from strawberry.arguments import StrawberryArgument
  22 
  23 
  24 def directive_field(name: str, default: object = UNSET) -> Any:
  25     return StrawberryField(
  26         python_name=None,
  27         graphql_name=name,
  28         default=default,
  29     )
  30 
  31 
  32 T = TypeVar("T")
  33 
  34 
  35 class StrawberryDirectiveValue:
  36     ...
  37 
  38 
  39 DirectiveValue = Annotated[T, StrawberryDirectiveValue()]
  40 DirectiveValue.__doc__ = (
  41     """Represents the ``value`` argument for a GraphQL query directive."""
  42 )
  43 
  44 # Registers `DirectiveValue[...]` annotated arguments as reserved
  45 VALUE_PARAMSPEC = ReservedType(name="value", type=StrawberryDirectiveValue)
  46 
  47 
  48 class StrawberryDirectiveResolver(StrawberryResolver[T]):
  49     RESERVED_PARAMSPEC = (
  50         INFO_PARAMSPEC,
  51         VALUE_PARAMSPEC,
  52     )
  53 
  54     @cached_property
  55     def value_parameter(self) -> Optional[inspect.Parameter]:
  56         return self.reserved_parameters.get(VALUE_PARAMSPEC)
  57 
  58 
  59 @dataclasses.dataclass
  60 class StrawberryDirective:
  61     python_name: str
  62     graphql_name: Optional[str]
  63     resolver: StrawberryDirectiveResolver
  64     locations: List[DirectiveLocation]
  65     description: Optional[str] = None
  66 
  67     @cached_property
  68     def arguments(self) -> List[StrawberryArgument]:
  69         return self.resolver.arguments
  70 
  71 
  72 def directive(
  73     *,
  74     locations: List[DirectiveLocation],
  75     description: Optional[str] = None,
  76     name: Optional[str] = None,
  77 ) -> Callable[[Callable[..., T]], T]:
  78     def _wrap(f: Callable[..., T]) -> T:
  79         return StrawberryDirective(  # type: ignore
  80             python_name=f.__name__,
  81             graphql_name=name,
  82             locations=locations,
  83             description=description,
  84             resolver=StrawberryDirectiveResolver(f),
  85         )
  86 
  87     return _wrap
  88 
  89 
  90 __all__ = ["DirectiveLocation", "StrawberryDirective", "directive"]
  91
  ```
  --- 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()
  
  ```
  
golden_diff: diff --git a/strawberry/directive.py b/strawberry/directive.py
  --- a/strawberry/directive.py
  +++ b/strawberry/directive.py
  @@ -1,7 +1,7 @@
   from __future__ import annotations
   
   import dataclasses
  -from typing import TYPE_CHECKING, Any, Callable, List, Optional, TypeVar
  +from typing import TYPE_CHECKING, Any, Callable, Generic, List, Optional, TypeVar
   from typing_extensions import Annotated
   
   from graphql import DirectiveLocation
  @@ -57,10 +57,10 @@
   
   
   @dataclasses.dataclass
  -class StrawberryDirective:
  +class StrawberryDirective(Generic[T]):
       python_name: str
       graphql_name: Optional[str]
  -    resolver: StrawberryDirectiveResolver
  +    resolver: StrawberryDirectiveResolver[T]
       locations: List[DirectiveLocation]
       description: Optional[str] = None
   
  @@ -74,9 +74,9 @@
       locations: List[DirectiveLocation],
       description: Optional[str] = None,
       name: Optional[str] = None,
  -) -> Callable[[Callable[..., T]], T]:
  -    def _wrap(f: Callable[..., T]) -> T:
  -        return StrawberryDirective(  # type: ignore
  +) -> Callable[[Callable[..., T]], StrawberryDirective[T]]:
  +    def _wrap(f: Callable[..., T]) -> StrawberryDirective[T]:
  +        return StrawberryDirective(
               python_name=f.__name__,
               graphql_name=name,
               locations=locations,
  
verification_info: {"golden_diff": "diff --git a/strawberry/directive.py b/strawberry/directive.py\n--- a/strawberry/directive.py\n+++ b/strawberry/directive.py\n@@ -1,7 +1,7 @@\n from __future__ import annotations\n \n import dataclasses\n-from typing import TYPE_CHECKING, Any, Callable, List, Optional, TypeVar\n+from typing import TYPE_CHECKING, Any, Callable, Generic, List, Optional, TypeVar\n from typing_extensions import Annotated\n \n from graphql import DirectiveLocation\n@@ -57,10 +57,10 @@\n \n \n @dataclasses.dataclass\n-class StrawberryDirective:\n+class StrawberryDirective(Generic[T]):\n     python_name: str\n     graphql_name: Optional[str]\n-    resolver: StrawberryDirectiveResolver\n+    resolver: StrawberryDirectiveResolver[T]\n     locations: List[DirectiveLocation]\n     description: Optional[str] = None\n \n@@ -74,9 +74,9 @@\n     locations: List[DirectiveLocation],\n     description: Optional[str] = None,\n     name: Optional[str] = None,\n-) -> Callable[[Callable[..., T]], T]:\n-    def _wrap(f: Callable[..., T]) -> T:\n-        return StrawberryDirective(  # type: ignore\n+) -> Callable[[Callable[..., T]], StrawberryDirective[T]]:\n+    def _wrap(f: Callable[..., T]) -> StrawberryDirective[T]:\n+        return StrawberryDirective(\n             python_name=f.__name__,\n             graphql_name=name,\n             locations=locations,\n", "issue": "`strawberry.directive` type hints appear to be incorrect.\n<!-- Provide a general summary of the bug in the title above. -->\r\n\r\n<!--- This template is entirely optional and can be removed, but is here to help both you and us. -->\r\n<!--- Anything on lines wrapped in comments like these will not show up in the final text. -->\r\n\r\n## Describe the Bug\r\n\r\nA function like:\r\n\r\n```py\r\n@strawberry.directive(\r\n    locations=[DirectiveLocation.FRAGMENT_DEFINITION],\r\n    description=\"Do nothing, but add a base class for query generation in the python client.\",\r\n)\r\ndef identity(value: str, a: str, b: str | None = None) -> str:\r\n    \"\"\"Do nothing, but add a directive so that the python client can use this to add metadata.\"\"\"\r\n    return value\r\n\r\nreveal_type(identity)\r\n```\r\n\r\n`mypy` will say that the revealed type here is `builtins.str`.  Looking at the code for `directive`, it appears that the type hints imply that the decorated object is going to return the same type that the function returns (in this case, the return type of `identity`)\r\n\r\n\r\n## System Information\r\n\r\n - Operating system:\r\n - Strawberry version (if applicable):\r\n\r\n## Additional Context\r\n\r\n<!-- Add any other relevant information about the problem here. -->\r\n\n\n<!-- POLAR PLEDGE BADGE START -->\n## Upvote & Fund\n\n- We're using [Polar.sh](https://polar.sh/strawberry-graphql) so you can upvote and help fund this issue.\n- We receive the funding once the issue is completed & confirmed by you.\n- Thank you in advance for helping prioritize & fund our backlog.\n\n<a href=\"https://polar.sh/strawberry-graphql/strawberry/issues/2846\">\n<picture>\n  <source media=\"(prefers-color-scheme: dark)\" srcset=\"https://polar.sh/api/github/strawberry-graphql/strawberry/issues/2846/pledge.svg?darkmode=1\">\n  <img alt=\"Fund with Polar\" src=\"https://polar.sh/api/github/strawberry-graphql/strawberry/issues/2846/pledge.svg\">\n</picture>\n</a>\n<!-- POLAR PLEDGE BADGE END -->\n\n", "before_files": [{"content": "from __future__ import annotations\n\nimport dataclasses\nfrom typing import TYPE_CHECKING, Any, Callable, List, Optional, TypeVar\nfrom typing_extensions import Annotated\n\nfrom graphql import DirectiveLocation\n\nfrom strawberry.field import StrawberryField\nfrom strawberry.types.fields.resolver import (\n    INFO_PARAMSPEC,\n    ReservedType,\n    StrawberryResolver,\n)\nfrom strawberry.unset import UNSET\nfrom strawberry.utils.cached_property import cached_property\n\nif TYPE_CHECKING:\n    import inspect\n\n    from strawberry.arguments import StrawberryArgument\n\n\ndef directive_field(name: str, default: object = UNSET) -> Any:\n    return StrawberryField(\n        python_name=None,\n        graphql_name=name,\n        default=default,\n    )\n\n\nT = TypeVar(\"T\")\n\n\nclass StrawberryDirectiveValue:\n    ...\n\n\nDirectiveValue = Annotated[T, StrawberryDirectiveValue()]\nDirectiveValue.__doc__ = (\n    \"\"\"Represents the ``value`` argument for a GraphQL query directive.\"\"\"\n)\n\n# Registers `DirectiveValue[...]` annotated arguments as reserved\nVALUE_PARAMSPEC = ReservedType(name=\"value\", type=StrawberryDirectiveValue)\n\n\nclass StrawberryDirectiveResolver(StrawberryResolver[T]):\n    RESERVED_PARAMSPEC = (\n        INFO_PARAMSPEC,\n        VALUE_PARAMSPEC,\n    )\n\n    @cached_property\n    def value_parameter(self) -> Optional[inspect.Parameter]:\n        return self.reserved_parameters.get(VALUE_PARAMSPEC)\n\n\n@dataclasses.dataclass\nclass StrawberryDirective:\n    python_name: str\n    graphql_name: Optional[str]\n    resolver: StrawberryDirectiveResolver\n    locations: List[DirectiveLocation]\n    description: Optional[str] = None\n\n    @cached_property\n    def arguments(self) -> List[StrawberryArgument]:\n        return self.resolver.arguments\n\n\ndef directive(\n    *,\n    locations: List[DirectiveLocation],\n    description: Optional[str] = None,\n    name: Optional[str] = None,\n) -> Callable[[Callable[..., T]], T]:\n    def _wrap(f: Callable[..., T]) -> T:\n        return StrawberryDirective(  # type: ignore\n            python_name=f.__name__,\n            graphql_name=name,\n            locations=locations,\n            description=description,\n            resolver=StrawberryDirectiveResolver(f),\n        )\n\n    return _wrap\n\n\n__all__ = [\"DirectiveLocation\", \"StrawberryDirective\", \"directive\"]\n", "path": "strawberry/directive.py"}], "after_files": [{"content": "from __future__ import annotations\n\nimport dataclasses\nfrom typing import TYPE_CHECKING, Any, Callable, Generic, List, Optional, TypeVar\nfrom typing_extensions import Annotated\n\nfrom graphql import DirectiveLocation\n\nfrom strawberry.field import StrawberryField\nfrom strawberry.types.fields.resolver import (\n    INFO_PARAMSPEC,\n    ReservedType,\n    StrawberryResolver,\n)\nfrom strawberry.unset import UNSET\nfrom strawberry.utils.cached_property import cached_property\n\nif TYPE_CHECKING:\n    import inspect\n\n    from strawberry.arguments import StrawberryArgument\n\n\ndef directive_field(name: str, default: object = UNSET) -> Any:\n    return StrawberryField(\n        python_name=None,\n        graphql_name=name,\n        default=default,\n    )\n\n\nT = TypeVar(\"T\")\n\n\nclass StrawberryDirectiveValue:\n    ...\n\n\nDirectiveValue = Annotated[T, StrawberryDirectiveValue()]\nDirectiveValue.__doc__ = (\n    \"\"\"Represents the ``value`` argument for a GraphQL query directive.\"\"\"\n)\n\n# Registers `DirectiveValue[...]` annotated arguments as reserved\nVALUE_PARAMSPEC = ReservedType(name=\"value\", type=StrawberryDirectiveValue)\n\n\nclass StrawberryDirectiveResolver(StrawberryResolver[T]):\n    RESERVED_PARAMSPEC = (\n        INFO_PARAMSPEC,\n        VALUE_PARAMSPEC,\n    )\n\n    @cached_property\n    def value_parameter(self) -> Optional[inspect.Parameter]:\n        return self.reserved_parameters.get(VALUE_PARAMSPEC)\n\n\n@dataclasses.dataclass\nclass StrawberryDirective(Generic[T]):\n    python_name: str\n    graphql_name: Optional[str]\n    resolver: StrawberryDirectiveResolver[T]\n    locations: List[DirectiveLocation]\n    description: Optional[str] = None\n\n    @cached_property\n    def arguments(self) -> List[StrawberryArgument]:\n        return self.resolver.arguments\n\n\ndef directive(\n    *,\n    locations: List[DirectiveLocation],\n    description: Optional[str] = None,\n    name: Optional[str] = None,\n) -> Callable[[Callable[..., T]], StrawberryDirective[T]]:\n    def _wrap(f: Callable[..., T]) -> StrawberryDirective[T]:\n        return StrawberryDirective(\n            python_name=f.__name__,\n            graphql_name=name,\n            locations=locations,\n            description=description,\n            resolver=StrawberryDirectiveResolver(f),\n        )\n\n    return _wrap\n\n\n__all__ = [\"DirectiveLocation\", \"StrawberryDirective\", \"directive\"]\n", "path": "strawberry/directive.py"}]}