From d499004860fc74cd95f40b786133229f1d0550bf Mon Sep 17 00:00:00 2001
From: Guido van Rossum <guido@python.org>
Date: Sun, 28 Dec 1997 04:21:20 +0000
Subject: Solve two annoying problems with ftp URLs for Jack: when repeated
 retrieving files from the same host and directory, you had to close the
 previous instance before opening a new one; and retrieving a non-existent
 file would return an empty file.  (The latter fix relies on maybe an
 undocumented property of NLST -- NLST of a file returns just that file, while
 NLST of a non-existent file returns nothing.  A side effect, unfortunately,
 seems to be that now ftp-retrieving an *empty* directory may fail.  Ah well.)

---
 Lib/urllib.py | 14 ++++++++++++++
 1 file changed, 14 insertions(+)

diff --git a/Lib/urllib.py b/Lib/urllib.py
index a16529a..b9a82d1 100644
--- a/Lib/urllib.py
+++ b/Lib/urllib.py
@@ -497,6 +497,7 @@ class ftpwrapper:
 		self.init()
 	def init(self):
 		import ftplib
+		self.busy = 0
 		self.ftp = ftplib.FTP()
 		self.ftp.connect(self.host, self.port)
 		self.ftp.login(self.user, self.passwd)
@@ -504,6 +505,7 @@ class ftpwrapper:
 			self.ftp.cwd(dir)
 	def retrfile(self, file, type):
 		import ftplib
+		self.endtransfer()
 		if type in ('d', 'D'): cmd = 'TYPE A'; isdir = 1
 		else: cmd = 'TYPE ' + type; isdir = 0
 		try:
@@ -513,6 +515,13 @@ class ftpwrapper:
 			self.ftp.voidcmd(cmd)
 		conn = None
 		if file and not isdir:
+			# Use nlst to see if the file exists at all
+			try:
+				self.ftp.nlst(file)
+			except ftplib.error_perm, reason:
+				raise IOError, ('ftp error', reason), \
+				      sys.exc_info()[2]
+			# Try to retrieve as a file
 			try:
 				cmd = 'RETR ' + file
 				conn = self.ftp.transfercmd(cmd)
@@ -525,13 +534,18 @@ class ftpwrapper:
 			if file: cmd = 'LIST ' + file
 			else: cmd = 'LIST'
 			conn = self.ftp.transfercmd(cmd)
+		self.busy = 1
 		return addclosehook(conn.makefile('rb'), self.endtransfer)
 	def endtransfer(self):
+		if not self.busy:
+			return
+		self.busy = 0
 		try:
 			self.ftp.voidresp()
 		except ftperrors():
 			pass
 	def close(self):
+		self.endtransfer()
 		try:
 			self.ftp.close()
 		except ftperrors():
-- 
cgit v0.12

