diff --git a/Lib/test/test_urllib2net.py b/Lib/test/test_urllib2net.py index 5da41c37bbfb8e..d8d882b2d33589 100644 --- a/Lib/test/test_urllib2net.py +++ b/Lib/test/test_urllib2net.py @@ -134,7 +134,9 @@ def setUp(self): # They do sometimes catch some major disasters, though. def test_ftp(self): + # Testing the same URL twice exercises the caching in CacheFTPHandler urls = [ + 'ftp://www.pythontest.net/README', 'ftp://www.pythontest.net/README', ('ftp://www.pythontest.net/non-existent-file', None, urllib.error.URLError), diff --git a/Lib/urllib/request.py b/Lib/urllib/request.py index 73ad0127ecc969..24911bb0190b8e 100644 --- a/Lib/urllib/request.py +++ b/Lib/urllib/request.py @@ -2469,7 +2469,13 @@ def retrfile(self, file, type): return (ftpobj, retrlen) def endtransfer(self): + if not self.busy: + return self.busy = 0 + try: + self.ftp.voidresp() + except ftperrors(): + pass def close(self): self.keepalive = False diff --git a/Misc/NEWS.d/next/Library/2023-04-22-22-14-09.gh-issue-81403.zVz9Td.rst b/Misc/NEWS.d/next/Library/2023-04-22-22-14-09.gh-issue-81403.zVz9Td.rst new file mode 100644 index 00000000000000..6adb71f7677229 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2023-04-22-22-14-09.gh-issue-81403.zVz9Td.rst @@ -0,0 +1,3 @@ +:class:`urllib.request.CacheFTPHandler` no longer raises :class:`URLError` +if a cached FTP instance is reused. ftplib's endtransfer method calls +voidresp to drain the connection to handle FTP instance reuse properly.