summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorVlad Serebrennikov <brainvlad@gmail.com>2020-04-30 01:06:39 (GMT)
committerGitHub <noreply@github.com>2020-04-30 01:06:39 (GMT)
commit138a9b9c2a394f30f222c23391f9515a7df9d809 (patch)
tree04e0c2277414db12ea5a2acdc3cdf867f16db613
parentb1e11c31c523dc082985e9de779ceeb47224e536 (diff)
downloadcpython-138a9b9c2a394f30f222c23391f9515a7df9d809.zip
cpython-138a9b9c2a394f30f222c23391f9515a7df9d809.tar.gz
cpython-138a9b9c2a394f30f222c23391f9515a7df9d809.tar.bz2
bpo-40389: Improve repr of typing.Optional (#19714)
-rw-r--r--Lib/test/test_dataclasses.py2
-rw-r--r--Lib/test/test_typing.py2
-rw-r--r--Lib/typing.py7
-rw-r--r--Misc/NEWS.d/next/Library/2020-04-25-20-00-58.bpo-40389.FPA6f0.rst1
4 files changed, 10 insertions, 2 deletions
diff --git a/Lib/test/test_dataclasses.py b/Lib/test/test_dataclasses.py
index e8fe455..b20103b 100644
--- a/Lib/test/test_dataclasses.py
+++ b/Lib/test/test_dataclasses.py
@@ -2028,7 +2028,7 @@ class TestDocString(unittest.TestCase):
class C:
x: Union[int, type(None)] = None
- self.assertDocStrEqual(C.__doc__, "C(x:Union[int, NoneType]=None)")
+ self.assertDocStrEqual(C.__doc__, "C(x:Optional[int]=None)")
def test_docstring_list_field(self):
@dataclass
diff --git a/Lib/test/test_typing.py b/Lib/test/test_typing.py
index cab8de0..21bc7c8 100644
--- a/Lib/test/test_typing.py
+++ b/Lib/test/test_typing.py
@@ -1750,7 +1750,7 @@ class GenericTests(BaseTestCase):
self.assertEqual(repr(Union[Tuple, Tuple[int]]).replace('typing.', ''),
'Union[Tuple, Tuple[int]]')
self.assertEqual(repr(Callable[..., Optional[T]][int]).replace('typing.', ''),
- 'Callable[..., Union[int, NoneType]]')
+ 'Callable[..., Optional[int]]')
self.assertEqual(repr(Callable[[], List[T]][int]).replace('typing.', ''),
'Callable[[], List[int]]')
diff --git a/Lib/typing.py b/Lib/typing.py
index c829898..f3cd280 100644
--- a/Lib/typing.py
+++ b/Lib/typing.py
@@ -691,6 +691,13 @@ class _GenericAlias(_Final, _root=True):
return _GenericAlias(self.__origin__, params, name=self._name, inst=self._inst)
def __repr__(self):
+ if (self.__origin__ == Union and len(self.__args__) == 2
+ and type(None) in self.__args__):
+ if self.__args__[0] is not type(None):
+ arg = self.__args__[0]
+ else:
+ arg = self.__args__[1]
+ return (f'typing.Optional[{_type_repr(arg)}]')
if (self._name != 'Callable' or
len(self.__args__) == 2 and self.__args__[0] is Ellipsis):
if self._name:
diff --git a/Misc/NEWS.d/next/Library/2020-04-25-20-00-58.bpo-40389.FPA6f0.rst b/Misc/NEWS.d/next/Library/2020-04-25-20-00-58.bpo-40389.FPA6f0.rst
new file mode 100644
index 0000000..e7a60a8
--- /dev/null
+++ b/Misc/NEWS.d/next/Library/2020-04-25-20-00-58.bpo-40389.FPA6f0.rst
@@ -0,0 +1 @@
+``repr()`` now returns ``typing.Optional[T]`` when called for ``typing.Union`` of two types, one of which is ``NoneType``. \ No newline at end of file