Helpviewer/Network/FtpReply.py

changeset 2074
5cb87968aad5
parent 2054
099993935e6d
child 2080
4b33165dd55b
equal deleted inserted replaced
2071:136eb25e4314 2074:5cb87968aad5
12 import errno 12 import errno
13 import mimetypes 13 import mimetypes
14 14
15 from PyQt4.QtCore import QByteArray, QIODevice, Qt, QUrl, QTimer, QBuffer, \ 15 from PyQt4.QtCore import QByteArray, QIODevice, Qt, QUrl, QTimer, QBuffer, \
16 QCoreApplication 16 QCoreApplication
17 from PyQt4.QtGui import QPixmap 17 from PyQt4.QtGui import QPixmap, QDialog
18 from PyQt4.QtNetwork import QNetworkReply, QNetworkRequest, QNetworkProxyQuery, \ 18 from PyQt4.QtNetwork import QNetworkReply, QNetworkRequest, QAuthenticator
19 QNetworkProxy, QAuthenticator
20 from PyQt4.QtWebKit import QWebSettings 19 from PyQt4.QtWebKit import QWebSettings
21 20
21 from E5Network.E5Ftp import E5Ftp, E5FtpProxyError, E5FtpProxyType
22
23 from UI.AuthenticationDialog import AuthenticationDialog
22 import UI.PixmapCache 24 import UI.PixmapCache
25
23 from Utilities.FtpUtilities import FtpDirLineParser, FtpDirLineParserError 26 from Utilities.FtpUtilities import FtpDirLineParser, FtpDirLineParserError
27
28 import Preferences
24 29
25 ftpListPage_html = """\ 30 ftpListPage_html = """\
26 <?xml version="1.0" encoding="UTF-8" ?> 31 <?xml version="1.0" encoding="UTF-8" ?>
27 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" 32 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
28 "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> 33 "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
113 super().__init__(parent) 118 super().__init__(parent)
114 119
115 self.__manager = parent 120 self.__manager = parent
116 self.__handler = accessHandler 121 self.__handler = accessHandler
117 122
118 self.__ftp = ftplib.FTP() 123 self.__ftp = E5Ftp()
119 124
120 self.__items = [] 125 self.__items = []
121 self.__content = QByteArray() 126 self.__content = QByteArray()
122 self.__units = ["Bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"] 127 self.__units = ["Bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"]
123 self.__dirLineParser = FtpDirLineParser() 128 self.__dirLineParser = FtpDirLineParser()
126 if url.path() == "": 131 if url.path() == "":
127 url.setPath("/") 132 url.setPath("/")
128 self.setUrl(url) 133 self.setUrl(url)
129 134
130 # do proxy setup 135 # do proxy setup
131 self.__proxy = None 136 if not Preferences.getUI("UseProxy"):
132 query = QNetworkProxyQuery(url) 137 proxyType = E5FtpProxyType.NoProxy
133 proxyList = parent.proxyFactory().queryProxy(query) 138 else:
134 ftpProxy = QNetworkProxy() 139 proxyType = Preferences.getUI("ProxyType/Ftp")
135 for proxy in proxyList: 140 if proxyType != E5FtpProxyType.NoProxy:
136 if proxy.type() == QNetworkProxy.NoProxy or \ 141 self.__ftp.setProxy(proxyType,
137 proxy.type() == QNetworkProxy.FtpCachingProxy: 142 Preferences.getUI("ProxyHost/Ftp"),
138 ftpProxy = proxy 143 Preferences.getUI("ProxyPort/Ftp"))
139 break 144 if proxyType != E5FtpProxyType.NonAuthorizing:
140 if ftpProxy.type() == QNetworkProxy.DefaultProxy: 145 self.__ftp.setProxyAuthentication(
141 self.setError(QNetworkReply.ProxyNotFoundError, 146 Preferences.getUI("ProxyUser/Ftp"),
142 self.trUtf8("No suitable proxy found.")) 147 Preferences.getUI("ProxyPassword/Ftp"),
143 QTimer.singleShot(0, self.__errorSignals) 148 Preferences.getUI("ProxyAccount/Ftp"))
144 return
145 elif ftpProxy.type() == QNetworkProxy.FtpCachingProxy:
146 self.__proxy = ftpProxy
147
148 self.__loggingIn = False
149 149
150 QTimer.singleShot(0, self.__doFtpCommands) 150 QTimer.singleShot(0, self.__doFtpCommands)
151 151
152 def abort(self): 152 def abort(self):
153 """ 153 """
192 retry = True 192 retry = True
193 try: 193 try:
194 username = self.url().userName() 194 username = self.url().userName()
195 password = self.url().password() 195 password = self.url().password()
196 byAuth = False 196 byAuth = False
197
197 while retry: 198 while retry:
198 if self.__proxy: 199 try:
199 self.__ftp.connect(self.__proxy.hostName(), self.__proxy.port(), 200 self.__ftp.connect(self.url().host(),
201 self.url().port(ftplib.FTP_PORT),
200 timeout=10) 202 timeout=10)
201 else: 203 except E5FtpProxyError as err:
202 self.__ftp.connect( 204 self.setError(QNetworkReply.ProxyNotFoundError, str(err))
203 self.url().host(), self.url().port(ftplib.FTP_PORT), timeout=10) 205 self.error.emit(QNetworkReply.ProxyNotFoundError)
206 self.finished.emit()
204 ok, retry = self.__doFtpLogin(username, password, byAuth) 207 ok, retry = self.__doFtpLogin(username, password, byAuth)
205 if not ok and retry: 208 if not ok and retry:
206 auth = self.__handler.getAuthenticator(self.url().host()) 209 auth = self.__handler.getAuthenticator(self.url().host())
207 if auth and not auth.isNull() and auth.user(): 210 if auth and not auth.isNull() and auth.user():
208 username = auth.user() 211 username = auth.user()
244 @param byAuth flag indicating that the login data was provided by an 247 @param byAuth flag indicating that the login data was provided by an
245 authenticator (boolean) 248 authenticator (boolean)
246 @return tuple of two flags indicating a successful login and 249 @return tuple of two flags indicating a successful login and
247 if the login should be retried (boolean, boolean) 250 if the login should be retried (boolean, boolean)
248 """ 251 """
249 # 1. do proxy login, if a proxy is used
250 if self.__proxy:
251 try:
252 self.__ftp.login(self.__proxy.user(), self.__proxy.password())
253 except ftplib.error_perm as err:
254 code, msg = err.args[0].split(None, 1)
255 if code.strip() == "530":
256 auth = QAuthenticator()
257 auth.setOption("realm", self.__proxy.hostName())
258 self.__manager.proxyAuthenticationRequired.emit(self.__proxy, auth)
259 if not auth.isNull() and auth.user():
260 self.__proxy.setUser(auth.user())
261 self.__proxy.setPassword(auth.password())
262 return False, True
263 return False, False
264
265 # 2. do the real login
266 try: 252 try:
267 if self.__proxy: 253 self.__ftp.login(username, password)
268 loginName = "{0}@{1}".format(username, self.url().host())
269 if self.url().port(ftplib.FTP_PORT) != ftplib.FTP_PORT:
270 loginName = "{0}:{1}".format(loginName, self.url().port())
271 else:
272 loginName = username
273 self.__ftp.login(loginName, password)
274 return True, False 254 return True, False
255 except E5FtpProxyError as err:
256 code = str(err)[:3]
257 if code[1] == "5":
258 # could be a 530, check second line
259 lines = str(err).splitlines()
260 if lines[1][:3] == "530":
261 if "usage" in "\n".join(lines[1:].lower()):
262 # found a not supported proxy
263 self.setError(QNetworkReply.ProxyConnectionRefusedError,
264 self.trUtf8("The proxy type seems to be wrong."
265 " If it is not in the list of supported"
266 " proxy types please report it with the"
267 " instructions given by the proxy.\n{0}").format(
268 "\n".join(lines[1:])))
269 self.error.emit(QNetworkReply.ProxyConnectionRefusedError)
270 return False, False
271 else:
272 info = self.trUtf8("<b>Connect to proxy '{0}' using:</b>")\
273 .format(Qt.escape(Preferences.getUI("ProxyHost/Ftp")))
274 dlg = AuthenticationDialog(info,
275 Preferences.getUI("ProxyUser/Ftp"), True)
276 dlg.setData(Preferences.getUI("ProxyUser/Ftp"),
277 Preferences.getUI("ProxyPassword/Ftp"))
278 if dlg.exec_() == QDialog.Accepted:
279 username, password = dlg.getData()
280 if dlg.shallSave():
281 Preferences.setUI("ProxyUser/Ftp", username)
282 Preferences.setUI("ProxyPassword/Ftp", password)
283 self.__ftp.setProxyAuthentication(username, password)
284 return False, True
285 return False, False
275 except ftplib.error_perm as err: 286 except ftplib.error_perm as err:
276 code, msg = err.args[0].split(None, 1) 287 code = err.args[0].strip()[:3]
277 if code.strip() == "530": 288 if code in ["530", "421"]:
278 # error 530 -> Login incorrect 289 # error 530 -> Login incorrect
290 # error 421 -> Login may be incorrect (reported by some proxies)
279 if byAuth: 291 if byAuth:
280 self.__handler.setAuthenticator(self.url().host(), None) 292 self.__handler.setAuthenticator(self.url().host(), None)
281 auth = None 293 auth = None
282 else: 294 else:
283 auth = self.__handler.getAuthenticator(self.url().host()) 295 auth = self.__handler.getAuthenticator(self.url().host())
288 if not auth.isNull(): 300 if not auth.isNull():
289 if auth.user(): 301 if auth.user():
290 self.__handler.setAuthenticator(self.url().host(), auth) 302 self.__handler.setAuthenticator(self.url().host(), auth)
291 return False, True 303 return False, True
292 return False, False 304 return False, False
293 else: 305 return False, True
294 return False, True
295 else: 306 else:
296 raise 307 raise
297 308
298 def __dirCallback(self, line): 309 def __dirCallback(self, line):
299 """ 310 """

eric ide

mercurial