prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  strawberry.utils.typing.get_optional_annotation fails when provided an `Optional[Union]`
  `strawberry.utils.typing.get_optional_annotation` fails when provided an `Optional[Union]`
  
  ```pycon
  >>> from typing import Optional, Union
  >>> from strawberry.utils.typing import get_optional_annotation
  
  >>> get_optional_annotation(Optional[Union[int, str]])
  <class 'int'>
  ```
  This should return `Union[int, str]` instead 
  
  --- 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/utils/typing.py`
  Content:
  ```
  1 import typing
  2 from collections.abc import AsyncGenerator, Callable
  3 from typing import Type, TypeVar
  4 
  5 
  6 try:
  7     from typing import ForwardRef  # type: ignore
  8 except ImportError:  # pragma: no cover
  9     # ForwardRef is private in python 3.6 and 3.7
  10     from typing import _ForwardRef as ForwardRef  # type: ignore
  11 
  12 
  13 def is_list(annotation: Type) -> bool:
  14     """Returns True if annotation is a List"""
  15 
  16     annotation_origin = getattr(annotation, "__origin__", None)
  17 
  18     return annotation_origin == list
  19 
  20 
  21 def is_union(annotation: Type) -> bool:
  22     """Returns True if annotation is a Union"""
  23 
  24     annotation_origin = getattr(annotation, "__origin__", None)
  25 
  26     return annotation_origin == typing.Union
  27 
  28 
  29 def is_optional(annotation: Type) -> bool:
  30     """Returns True if the annotation is Optional[SomeType]"""
  31 
  32     # Optionals are represented as unions
  33 
  34     if not is_union(annotation):
  35         return False
  36 
  37     types = annotation.__args__
  38 
  39     # A Union to be optional needs to have at least one None type
  40     return any([x == None.__class__ for x in types])  # noqa:E711
  41 
  42 
  43 def get_optional_annotation(annotation: Type) -> Type:
  44     types = annotation.__args__
  45     non_none_types = [x for x in types if x != None.__class__]  # noqa:E711
  46 
  47     return non_none_types[0]
  48 
  49 
  50 def get_list_annotation(annotation: Type) -> Type:
  51     return annotation.__args__[0]
  52 
  53 
  54 def is_async_generator(annotation: Type) -> bool:
  55     return getattr(annotation, "__origin__", None) == AsyncGenerator
  56 
  57 
  58 def get_async_generator_annotation(annotation: Type) -> Type:
  59     return annotation.__args__[0]
  60 
  61 
  62 def is_generic(annotation: Type) -> bool:
  63     """Returns True if the annotation is or extends a generic."""
  64     return (
  65         isinstance(annotation, type)
  66         and issubclass(annotation, typing.Generic)  # type:ignore
  67         or isinstance(annotation, typing._GenericAlias)  # type:ignore
  68         and annotation.__origin__
  69         not in (
  70             list,
  71             typing.Union,
  72             tuple,
  73             typing.ClassVar,
  74             AsyncGenerator,
  75         )
  76     )
  77 
  78 
  79 def is_type_var(annotation: Type) -> bool:
  80     """Returns True if the annotation is a TypeVar."""
  81 
  82     return isinstance(annotation, TypeVar)  # type:ignore
  83 
  84 
  85 def has_type_var(annotation: Type) -> bool:
  86     """
  87     Returns True if the annotation or any of
  88     its argument have a TypeVar as argument.
  89     """
  90     return any(
  91         is_type_var(arg) or has_type_var(arg)
  92         for arg in getattr(annotation, "__args__", [])
  93     )
  94 
  95 
  96 def get_parameters(annotation: Type):
  97     if (
  98         isinstance(annotation, typing._GenericAlias)  # type:ignore
  99         or isinstance(annotation, type)
  100         and issubclass(annotation, typing.Generic)  # type:ignore
  101         and annotation is not typing.Generic
  102     ):
  103         return annotation.__parameters__
  104     else:
  105         return ()  # pragma: no cover
  106 
  107 
  108 def get_origin(annotation: Type):
  109     if isinstance(annotation, typing._GenericAlias):  # type:ignore
  110         return (
  111             annotation.__origin__
  112             if annotation.__origin__ is not typing.ClassVar
  113             else None
  114         )
  115 
  116     if annotation is typing.Generic:  # pragma: no cover
  117         return typing.Generic
  118 
  119     return None  # pragma: no cover
  120 
  121 
  122 def get_args(annotation: Type):
  123     if isinstance(annotation, typing._GenericAlias):  # type:ignore
  124         res = annotation.__args__
  125 
  126         if (
  127             get_origin(annotation) is Callable and res[0] is not Ellipsis
  128         ):  # pragma: no cover
  129             res = (list(res[:-1]), res[-1])
  130 
  131         return res
  132 
  133     return ()
  134 
  135 
  136 def is_forward_ref(annotation: Type) -> bool:
  137     return isinstance(annotation, ForwardRef)
  138
  ```
  --- 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/utils/typing.py b/strawberry/utils/typing.py
  --- a/strawberry/utils/typing.py
  +++ b/strawberry/utils/typing.py
  @@ -42,7 +42,14 @@
   
   def get_optional_annotation(annotation: Type) -> Type:
       types = annotation.__args__
  -    non_none_types = [x for x in types if x != None.__class__]  # noqa:E711
  +
  +    non_none_types = tuple(x for x in types if x != None.__class__)  # noqa:E711
  +
  +    # if we have multiple non none types we want to return a copy of this
  +    # type (normally a Union type).
  +
  +    if len(non_none_types) > 1:
  +        return annotation.copy_with(non_none_types)
   
       return non_none_types[0]
  
verification_info: {"golden_diff": "diff --git a/strawberry/utils/typing.py b/strawberry/utils/typing.py\n--- a/strawberry/utils/typing.py\n+++ b/strawberry/utils/typing.py\n@@ -42,7 +42,14 @@\n \n def get_optional_annotation(annotation: Type) -> Type:\n     types = annotation.__args__\n-    non_none_types = [x for x in types if x != None.__class__]  # noqa:E711\n+\n+    non_none_types = tuple(x for x in types if x != None.__class__)  # noqa:E711\n+\n+    # if we have multiple non none types we want to return a copy of this\n+    # type (normally a Union type).\n+\n+    if len(non_none_types) > 1:\n+        return annotation.copy_with(non_none_types)\n \n     return non_none_types[0]\n", "issue": "strawberry.utils.typing.get_optional_annotation fails when provided an `Optional[Union]`\n`strawberry.utils.typing.get_optional_annotation` fails when provided an `Optional[Union]`\r\n\r\n```pycon\r\n>>> from typing import Optional, Union\r\n>>> from strawberry.utils.typing import get_optional_annotation\r\n\r\n>>> get_optional_annotation(Optional[Union[int, str]])\r\n<class 'int'>\r\n```\r\nThis should return `Union[int, str]` instead \n", "before_files": [{"content": "import typing\nfrom collections.abc import AsyncGenerator, Callable\nfrom typing import Type, TypeVar\n\n\ntry:\n    from typing import ForwardRef  # type: ignore\nexcept ImportError:  # pragma: no cover\n    # ForwardRef is private in python 3.6 and 3.7\n    from typing import _ForwardRef as ForwardRef  # type: ignore\n\n\ndef is_list(annotation: Type) -> bool:\n    \"\"\"Returns True if annotation is a List\"\"\"\n\n    annotation_origin = getattr(annotation, \"__origin__\", None)\n\n    return annotation_origin == list\n\n\ndef is_union(annotation: Type) -> bool:\n    \"\"\"Returns True if annotation is a Union\"\"\"\n\n    annotation_origin = getattr(annotation, \"__origin__\", None)\n\n    return annotation_origin == typing.Union\n\n\ndef is_optional(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is Optional[SomeType]\"\"\"\n\n    # Optionals are represented as unions\n\n    if not is_union(annotation):\n        return False\n\n    types = annotation.__args__\n\n    # A Union to be optional needs to have at least one None type\n    return any([x == None.__class__ for x in types])  # noqa:E711\n\n\ndef get_optional_annotation(annotation: Type) -> Type:\n    types = annotation.__args__\n    non_none_types = [x for x in types if x != None.__class__]  # noqa:E711\n\n    return non_none_types[0]\n\n\ndef get_list_annotation(annotation: Type) -> Type:\n    return annotation.__args__[0]\n\n\ndef is_async_generator(annotation: Type) -> bool:\n    return getattr(annotation, \"__origin__\", None) == AsyncGenerator\n\n\ndef get_async_generator_annotation(annotation: Type) -> Type:\n    return annotation.__args__[0]\n\n\ndef is_generic(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is or extends a generic.\"\"\"\n    return (\n        isinstance(annotation, type)\n        and issubclass(annotation, typing.Generic)  # type:ignore\n        or isinstance(annotation, typing._GenericAlias)  # type:ignore\n        and annotation.__origin__\n        not in (\n            list,\n            typing.Union,\n            tuple,\n            typing.ClassVar,\n            AsyncGenerator,\n        )\n    )\n\n\ndef is_type_var(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is a TypeVar.\"\"\"\n\n    return isinstance(annotation, TypeVar)  # type:ignore\n\n\ndef has_type_var(annotation: Type) -> bool:\n    \"\"\"\n    Returns True if the annotation or any of\n    its argument have a TypeVar as argument.\n    \"\"\"\n    return any(\n        is_type_var(arg) or has_type_var(arg)\n        for arg in getattr(annotation, \"__args__\", [])\n    )\n\n\ndef get_parameters(annotation: Type):\n    if (\n        isinstance(annotation, typing._GenericAlias)  # type:ignore\n        or isinstance(annotation, type)\n        and issubclass(annotation, typing.Generic)  # type:ignore\n        and annotation is not typing.Generic\n    ):\n        return annotation.__parameters__\n    else:\n        return ()  # pragma: no cover\n\n\ndef get_origin(annotation: Type):\n    if isinstance(annotation, typing._GenericAlias):  # type:ignore\n        return (\n            annotation.__origin__\n            if annotation.__origin__ is not typing.ClassVar\n            else None\n        )\n\n    if annotation is typing.Generic:  # pragma: no cover\n        return typing.Generic\n\n    return None  # pragma: no cover\n\n\ndef get_args(annotation: Type):\n    if isinstance(annotation, typing._GenericAlias):  # type:ignore\n        res = annotation.__args__\n\n        if (\n            get_origin(annotation) is Callable and res[0] is not Ellipsis\n        ):  # pragma: no cover\n            res = (list(res[:-1]), res[-1])\n\n        return res\n\n    return ()\n\n\ndef is_forward_ref(annotation: Type) -> bool:\n    return isinstance(annotation, ForwardRef)\n", "path": "strawberry/utils/typing.py"}], "after_files": [{"content": "import typing\nfrom collections.abc import AsyncGenerator, Callable\nfrom typing import Type, TypeVar\n\n\ntry:\n    from typing import ForwardRef  # type: ignore\nexcept ImportError:  # pragma: no cover\n    # ForwardRef is private in python 3.6 and 3.7\n    from typing import _ForwardRef as ForwardRef  # type: ignore\n\n\ndef is_list(annotation: Type) -> bool:\n    \"\"\"Returns True if annotation is a List\"\"\"\n\n    annotation_origin = getattr(annotation, \"__origin__\", None)\n\n    return annotation_origin == list\n\n\ndef is_union(annotation: Type) -> bool:\n    \"\"\"Returns True if annotation is a Union\"\"\"\n\n    annotation_origin = getattr(annotation, \"__origin__\", None)\n\n    return annotation_origin == typing.Union\n\n\ndef is_optional(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is Optional[SomeType]\"\"\"\n\n    # Optionals are represented as unions\n\n    if not is_union(annotation):\n        return False\n\n    types = annotation.__args__\n\n    # A Union to be optional needs to have at least one None type\n    return any([x == None.__class__ for x in types])  # noqa:E711\n\n\ndef get_optional_annotation(annotation: Type) -> Type:\n    types = annotation.__args__\n\n    non_none_types = tuple(x for x in types if x != None.__class__)  # noqa:E711\n\n    # if we have multiple non none types we want to return a copy of this\n    # type (normally a Union type).\n\n    if len(non_none_types) > 1:\n        return annotation.copy_with(non_none_types)\n\n    return non_none_types[0]\n\n\ndef get_list_annotation(annotation: Type) -> Type:\n    return annotation.__args__[0]\n\n\ndef is_async_generator(annotation: Type) -> bool:\n    return getattr(annotation, \"__origin__\", None) == AsyncGenerator\n\n\ndef get_async_generator_annotation(annotation: Type) -> Type:\n    return annotation.__args__[0]\n\n\ndef is_generic(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is or extends a generic.\"\"\"\n    return (\n        isinstance(annotation, type)\n        and issubclass(annotation, typing.Generic)  # type:ignore\n        or isinstance(annotation, typing._GenericAlias)  # type:ignore\n        and annotation.__origin__\n        not in (\n            list,\n            typing.Union,\n            tuple,\n            typing.ClassVar,\n            AsyncGenerator,\n        )\n    )\n\n\ndef is_type_var(annotation: Type) -> bool:\n    \"\"\"Returns True if the annotation is a TypeVar.\"\"\"\n\n    return isinstance(annotation, TypeVar)  # type:ignore\n\n\ndef has_type_var(annotation: Type) -> bool:\n    \"\"\"\n    Returns True if the annotation or any of\n    its argument have a TypeVar as argument.\n    \"\"\"\n    return any(\n        is_type_var(arg) or has_type_var(arg)\n        for arg in getattr(annotation, \"__args__\", [])\n    )\n\n\ndef get_parameters(annotation: Type):\n    if (\n        isinstance(annotation, typing._GenericAlias)  # type:ignore\n        or isinstance(annotation, type)\n        and issubclass(annotation, typing.Generic)  # type:ignore\n        and annotation is not typing.Generic\n    ):\n        return annotation.__parameters__\n    else:\n        return ()  # pragma: no cover\n\n\ndef get_origin(annotation: Type):\n    if isinstance(annotation, typing._GenericAlias):  # type:ignore\n        return (\n            annotation.__origin__\n            if annotation.__origin__ is not typing.ClassVar\n            else None\n        )\n\n    if annotation is typing.Generic:  # pragma: no cover\n        return typing.Generic\n\n    return None  # pragma: no cover\n\n\ndef get_args(annotation: Type):\n    if isinstance(annotation, typing._GenericAlias):  # type:ignore\n        res = annotation.__args__\n\n        if (\n            get_origin(annotation) is Callable and res[0] is not Ellipsis\n        ):  # pragma: no cover\n            res = (list(res[:-1]), res[-1])\n\n        return res\n\n    return ()\n\n\ndef is_forward_ref(annotation: Type) -> bool:\n    return isinstance(annotation, ForwardRef)\n", "path": "strawberry/utils/typing.py"}]}