Merge pull request #1357 from coffeedogs/final_code_quality_2
Changes based on style and lint checks. (final_code_quality_2)
This commit is contained in:
commit
44f5e03774
|
@ -1,14 +1,26 @@
|
||||||
#!/usr/bin/python2.7
|
#!/usr/bin/python2.7
|
||||||
|
"""
|
||||||
|
src/settingsmixin.py
|
||||||
|
====================
|
||||||
|
|
||||||
|
"""
|
||||||
|
|
||||||
from PyQt4 import QtCore, QtGui
|
from PyQt4 import QtCore, QtGui
|
||||||
|
|
||||||
|
|
||||||
class SettingsMixin(object):
|
class SettingsMixin(object):
|
||||||
|
"""Mixin for adding geometry and state saving between restarts."""
|
||||||
def warnIfNoObjectName(self):
|
def warnIfNoObjectName(self):
|
||||||
|
"""
|
||||||
|
Handle objects which don't have a name. Currently it ignores them. Objects without a name can't have their
|
||||||
|
state/geometry saved as they don't have an identifier.
|
||||||
|
"""
|
||||||
if self.objectName() == "":
|
if self.objectName() == "":
|
||||||
# TODO: logger
|
# .. todo:: logger
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def writeState(self, source):
|
def writeState(self, source):
|
||||||
|
"""Save object state (e.g. relative position of a splitter)"""
|
||||||
self.warnIfNoObjectName()
|
self.warnIfNoObjectName()
|
||||||
settings = QtCore.QSettings()
|
settings = QtCore.QSettings()
|
||||||
settings.beginGroup(self.objectName())
|
settings.beginGroup(self.objectName())
|
||||||
|
@ -16,6 +28,7 @@ class SettingsMixin(object):
|
||||||
settings.endGroup()
|
settings.endGroup()
|
||||||
|
|
||||||
def writeGeometry(self, source):
|
def writeGeometry(self, source):
|
||||||
|
"""Save object geometry (e.g. window size and position)"""
|
||||||
self.warnIfNoObjectName()
|
self.warnIfNoObjectName()
|
||||||
settings = QtCore.QSettings()
|
settings = QtCore.QSettings()
|
||||||
settings.beginGroup(self.objectName())
|
settings.beginGroup(self.objectName())
|
||||||
|
@ -23,57 +36,73 @@ class SettingsMixin(object):
|
||||||
settings.endGroup()
|
settings.endGroup()
|
||||||
|
|
||||||
def readGeometry(self, target):
|
def readGeometry(self, target):
|
||||||
|
"""Load object geometry"""
|
||||||
self.warnIfNoObjectName()
|
self.warnIfNoObjectName()
|
||||||
settings = QtCore.QSettings()
|
settings = QtCore.QSettings()
|
||||||
try:
|
try:
|
||||||
geom = settings.value("/".join([str(self.objectName()), "geometry"]))
|
geom = settings.value("/".join([str(self.objectName()), "geometry"]))
|
||||||
target.restoreGeometry(geom.toByteArray() if hasattr(geom, 'toByteArray') else geom)
|
target.restoreGeometry(geom.toByteArray() if hasattr(geom, 'toByteArray') else geom)
|
||||||
except Exception as e:
|
except Exception:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def readState(self, target):
|
def readState(self, target):
|
||||||
|
"""Load object state"""
|
||||||
self.warnIfNoObjectName()
|
self.warnIfNoObjectName()
|
||||||
settings = QtCore.QSettings()
|
settings = QtCore.QSettings()
|
||||||
try:
|
try:
|
||||||
state = settings.value("/".join([str(self.objectName()), "state"]))
|
state = settings.value("/".join([str(self.objectName()), "state"]))
|
||||||
target.restoreState(state.toByteArray() if hasattr(state, 'toByteArray') else state)
|
target.restoreState(state.toByteArray() if hasattr(state, 'toByteArray') else state)
|
||||||
except Exception as e:
|
except Exception:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class SMainWindow(QtGui.QMainWindow, SettingsMixin):
|
class SMainWindow(QtGui.QMainWindow, SettingsMixin):
|
||||||
|
"""Main window with Settings functionality."""
|
||||||
def loadSettings(self):
|
def loadSettings(self):
|
||||||
|
"""Load main window settings."""
|
||||||
self.readGeometry(self)
|
self.readGeometry(self)
|
||||||
self.readState(self)
|
self.readState(self)
|
||||||
|
|
||||||
def saveSettings(self):
|
def saveSettings(self):
|
||||||
|
"""Save main window settings"""
|
||||||
self.writeState(self)
|
self.writeState(self)
|
||||||
self.writeGeometry(self)
|
self.writeGeometry(self)
|
||||||
|
|
||||||
|
|
||||||
class STableWidget(QtGui.QTableWidget, SettingsMixin):
|
class STableWidget(QtGui.QTableWidget, SettingsMixin):
|
||||||
|
"""Table widget with Settings functionality"""
|
||||||
|
# pylint: disable=too-many-ancestors
|
||||||
def loadSettings(self):
|
def loadSettings(self):
|
||||||
|
"""Load table settings."""
|
||||||
self.readState(self.horizontalHeader())
|
self.readState(self.horizontalHeader())
|
||||||
|
|
||||||
def saveSettings(self):
|
def saveSettings(self):
|
||||||
|
"""Save table settings."""
|
||||||
self.writeState(self.horizontalHeader())
|
self.writeState(self.horizontalHeader())
|
||||||
|
|
||||||
|
|
||||||
class SSplitter(QtGui.QSplitter, SettingsMixin):
|
class SSplitter(QtGui.QSplitter, SettingsMixin):
|
||||||
|
"""Splitter with Settings functionality."""
|
||||||
def loadSettings(self):
|
def loadSettings(self):
|
||||||
|
"""Load splitter settings"""
|
||||||
self.readState(self)
|
self.readState(self)
|
||||||
|
|
||||||
def saveSettings(self):
|
def saveSettings(self):
|
||||||
|
"""Save splitter settings."""
|
||||||
self.writeState(self)
|
self.writeState(self)
|
||||||
|
|
||||||
|
|
||||||
class STreeWidget(QtGui.QTreeWidget, SettingsMixin):
|
class STreeWidget(QtGui.QTreeWidget, SettingsMixin):
|
||||||
|
"""Tree widget with settings functionality."""
|
||||||
|
# pylint: disable=too-many-ancestors
|
||||||
def loadSettings(self):
|
def loadSettings(self):
|
||||||
|
"""Load tree settings."""
|
||||||
# recurse children
|
# recurse children
|
||||||
# self.readState(self)
|
# self.readState(self)
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def saveSettings(self):
|
def saveSettings(self):
|
||||||
|
"""Save tree settings"""
|
||||||
# recurse children
|
# recurse children
|
||||||
# self.writeState(self)
|
# self.writeState(self)
|
||||||
pass
|
pass
|
||||||
|
|
|
@ -1,9 +1,18 @@
|
||||||
|
"""
|
||||||
|
src/network/socks5.py
|
||||||
|
=====================
|
||||||
|
|
||||||
|
"""
|
||||||
|
# pylint: disable=attribute-defined-outside-init
|
||||||
|
|
||||||
import socket
|
import socket
|
||||||
import struct
|
import struct
|
||||||
|
|
||||||
from proxy import Proxy, ProxyError, GeneralProxyError
|
from proxy import GeneralProxyError, Proxy, ProxyError
|
||||||
|
|
||||||
|
|
||||||
class Socks5AuthError(ProxyError):
|
class Socks5AuthError(ProxyError):
|
||||||
|
"""Thrown when the socks5 protocol encounters an authentication error"""
|
||||||
errorCodes = ("Succeeded",
|
errorCodes = ("Succeeded",
|
||||||
"Authentication is required",
|
"Authentication is required",
|
||||||
"All offered authentication methods were rejected",
|
"All offered authentication methods were rejected",
|
||||||
|
@ -12,6 +21,7 @@ class Socks5AuthError(ProxyError):
|
||||||
|
|
||||||
|
|
||||||
class Socks5Error(ProxyError):
|
class Socks5Error(ProxyError):
|
||||||
|
"""Thrown when socks5 protocol encounters an error"""
|
||||||
errorCodes = ("Succeeded",
|
errorCodes = ("Succeeded",
|
||||||
"General SOCKS server failure",
|
"General SOCKS server failure",
|
||||||
"Connection not allowed by ruleset",
|
"Connection not allowed by ruleset",
|
||||||
|
@ -25,12 +35,14 @@ class Socks5Error(ProxyError):
|
||||||
|
|
||||||
|
|
||||||
class Socks5(Proxy):
|
class Socks5(Proxy):
|
||||||
|
"""A socks5 proxy base class"""
|
||||||
def __init__(self, address=None):
|
def __init__(self, address=None):
|
||||||
Proxy.__init__(self, address)
|
Proxy.__init__(self, address)
|
||||||
self.ipaddr = None
|
self.ipaddr = None
|
||||||
self.destport = address[1]
|
self.destport = address[1]
|
||||||
|
|
||||||
def state_init(self):
|
def state_init(self):
|
||||||
|
"""Protocol initialisation (before connection is established)"""
|
||||||
if self._auth:
|
if self._auth:
|
||||||
self.append_write_buf(struct.pack('BBBB', 0x05, 0x02, 0x00, 0x02))
|
self.append_write_buf(struct.pack('BBBB', 0x05, 0x02, 0x00, 0x02))
|
||||||
else:
|
else:
|
||||||
|
@ -39,6 +51,7 @@ class Socks5(Proxy):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_auth_1(self):
|
def state_auth_1(self):
|
||||||
|
"""Perform authentication if peer is requesting it."""
|
||||||
ret = struct.unpack('BB', self.read_buf[:2])
|
ret = struct.unpack('BB', self.read_buf[:2])
|
||||||
if ret[0] != 5:
|
if ret[0] != 5:
|
||||||
# general error
|
# general error
|
||||||
|
@ -48,8 +61,8 @@ class Socks5(Proxy):
|
||||||
self.set_state("auth_done", length=2)
|
self.set_state("auth_done", length=2)
|
||||||
elif ret[1] == 2:
|
elif ret[1] == 2:
|
||||||
# username/password
|
# username/password
|
||||||
self.append_write_buf(struct.pack('BB', 1, len(self._auth[0])) + \
|
self.append_write_buf(struct.pack('BB', 1, len(self._auth[0])) +
|
||||||
self._auth[0] + struct.pack('B', len(self._auth[1])) + \
|
self._auth[0] + struct.pack('B', len(self._auth[1])) +
|
||||||
self._auth[1])
|
self._auth[1])
|
||||||
self.set_state("auth_needed", length=2, expectBytes=2)
|
self.set_state("auth_needed", length=2, expectBytes=2)
|
||||||
else:
|
else:
|
||||||
|
@ -62,6 +75,7 @@ class Socks5(Proxy):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_auth_needed(self):
|
def state_auth_needed(self):
|
||||||
|
"""Handle response to authentication attempt"""
|
||||||
ret = struct.unpack('BB', self.read_buf[0:2])
|
ret = struct.unpack('BB', self.read_buf[0:2])
|
||||||
if ret[0] != 1:
|
if ret[0] != 1:
|
||||||
# general error
|
# general error
|
||||||
|
@ -74,6 +88,7 @@ class Socks5(Proxy):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_pre_connect(self):
|
def state_pre_connect(self):
|
||||||
|
"""Handle feedback from socks5 while it is connecting on our behalf."""
|
||||||
# Get the response
|
# Get the response
|
||||||
if self.read_buf[0:1] != chr(0x05).encode():
|
if self.read_buf[0:1] != chr(0x05).encode():
|
||||||
self.close()
|
self.close()
|
||||||
|
@ -96,21 +111,31 @@ class Socks5(Proxy):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_proxy_addr_1(self):
|
def state_proxy_addr_1(self):
|
||||||
|
"""Handle IPv4 address returned for peer"""
|
||||||
self.boundaddr = self.read_buf[0:4]
|
self.boundaddr = self.read_buf[0:4]
|
||||||
self.set_state("proxy_port", length=4, expectBytes=2)
|
self.set_state("proxy_port", length=4, expectBytes=2)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_proxy_addr_2_1(self):
|
def state_proxy_addr_2_1(self):
|
||||||
|
"""
|
||||||
|
Handle other addresses than IPv4 returned for peer (e.g. IPv6, onion, ...). This is part 1 which retrieves the
|
||||||
|
length of the data.
|
||||||
|
"""
|
||||||
self.address_length = ord(self.read_buf[0:1])
|
self.address_length = ord(self.read_buf[0:1])
|
||||||
self.set_state("proxy_addr_2_2", length=1, expectBytes=self.address_length)
|
self.set_state("proxy_addr_2_2", length=1, expectBytes=self.address_length)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_proxy_addr_2_2(self):
|
def state_proxy_addr_2_2(self):
|
||||||
|
"""
|
||||||
|
Handle other addresses than IPv4 returned for peer (e.g. IPv6, onion, ...). This is part 2 which retrieves the
|
||||||
|
data.
|
||||||
|
"""
|
||||||
self.boundaddr = self.read_buf[0:self.address_length]
|
self.boundaddr = self.read_buf[0:self.address_length]
|
||||||
self.set_state("proxy_port", length=self.address_length, expectBytes=2)
|
self.set_state("proxy_port", length=self.address_length, expectBytes=2)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_proxy_port(self):
|
def state_proxy_port(self):
|
||||||
|
"""Handle peer's port being returned."""
|
||||||
self.boundport = struct.unpack(">H", self.read_buf[0:2])[0]
|
self.boundport = struct.unpack(">H", self.read_buf[0:2])[0]
|
||||||
self.__proxysockname = (self.boundaddr, self.boundport)
|
self.__proxysockname = (self.boundaddr, self.boundport)
|
||||||
if self.ipaddr is not None:
|
if self.ipaddr is not None:
|
||||||
|
@ -121,14 +146,17 @@ class Socks5(Proxy):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def proxy_sock_name(self):
|
def proxy_sock_name(self):
|
||||||
|
"""Handle return value when using SOCKS5 for DNS resolving instead of connecting."""
|
||||||
return socket.inet_ntoa(self.__proxysockname[0])
|
return socket.inet_ntoa(self.__proxysockname[0])
|
||||||
|
|
||||||
|
|
||||||
class Socks5Connection(Socks5):
|
class Socks5Connection(Socks5):
|
||||||
|
"""Child socks5 class used for making outbound connections."""
|
||||||
def __init__(self, address):
|
def __init__(self, address):
|
||||||
Socks5.__init__(self, address=address)
|
Socks5.__init__(self, address=address)
|
||||||
|
|
||||||
def state_auth_done(self):
|
def state_auth_done(self):
|
||||||
|
"""Request connection to be made"""
|
||||||
# Now we can request the actual connection
|
# Now we can request the actual connection
|
||||||
self.append_write_buf(struct.pack('BBB', 0x05, 0x01, 0x00))
|
self.append_write_buf(struct.pack('BBB', 0x05, 0x01, 0x00))
|
||||||
# If the given destination address is an IP address, we'll
|
# If the given destination address is an IP address, we'll
|
||||||
|
@ -138,10 +166,12 @@ class Socks5Connection(Socks5):
|
||||||
self.append_write_buf(chr(0x01).encode() + self.ipaddr)
|
self.append_write_buf(chr(0x01).encode() + self.ipaddr)
|
||||||
except socket.error:
|
except socket.error:
|
||||||
# Well it's not an IP number, so it's probably a DNS name.
|
# Well it's not an IP number, so it's probably a DNS name.
|
||||||
if Proxy._remote_dns:
|
if Proxy._remote_dns: # pylint: disable=protected-access
|
||||||
# Resolve remotely
|
# Resolve remotely
|
||||||
self.ipaddr = None
|
self.ipaddr = None
|
||||||
self.append_write_buf(chr(0x03).encode() + chr(len(self.destination[0])).encode() + self.destination[0])
|
self.append_write_buf(chr(0x03).encode() +
|
||||||
|
chr(len(self.destination[0])).encode() +
|
||||||
|
self.destination[0])
|
||||||
else:
|
else:
|
||||||
# Resolve locally
|
# Resolve locally
|
||||||
self.ipaddr = socket.inet_aton(socket.gethostbyname(self.destination[0]))
|
self.ipaddr = socket.inet_aton(socket.gethostbyname(self.destination[0]))
|
||||||
|
@ -151,6 +181,7 @@ class Socks5Connection(Socks5):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def state_pre_connect(self):
|
def state_pre_connect(self):
|
||||||
|
"""Tell socks5 to initiate a connection"""
|
||||||
try:
|
try:
|
||||||
return Socks5.state_pre_connect(self)
|
return Socks5.state_pre_connect(self)
|
||||||
except Socks5Error as e:
|
except Socks5Error as e:
|
||||||
|
@ -159,12 +190,14 @@ class Socks5Connection(Socks5):
|
||||||
|
|
||||||
|
|
||||||
class Socks5Resolver(Socks5):
|
class Socks5Resolver(Socks5):
|
||||||
|
"""DNS resolver class using socks5"""
|
||||||
def __init__(self, host):
|
def __init__(self, host):
|
||||||
self.host = host
|
self.host = host
|
||||||
self.port = 8444
|
self.port = 8444
|
||||||
Socks5.__init__(self, address=(self.host, self.port))
|
Socks5.__init__(self, address=(self.host, self.port))
|
||||||
|
|
||||||
def state_auth_done(self):
|
def state_auth_done(self):
|
||||||
|
"""Perform resolving"""
|
||||||
# Now we can request the actual connection
|
# Now we can request the actual connection
|
||||||
self.append_write_buf(struct.pack('BBB', 0x05, 0xF0, 0x00))
|
self.append_write_buf(struct.pack('BBB', 0x05, 0xF0, 0x00))
|
||||||
self.append_write_buf(chr(0x03).encode() + chr(len(self.host)).encode() + str(self.host))
|
self.append_write_buf(chr(0x03).encode() + chr(len(self.host)).encode() + str(self.host))
|
||||||
|
@ -173,4 +206,8 @@ class Socks5Resolver(Socks5):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
def resolved(self):
|
def resolved(self):
|
||||||
|
"""
|
||||||
|
Resolving is done, process the return value. To use this within PyBitmessage, a callback needs to be
|
||||||
|
implemented which hasn't been done yet.
|
||||||
|
"""
|
||||||
print "Resolved %s as %s" % (self.host, self.proxy_sock_name())
|
print "Resolved %s as %s" % (self.host, self.proxy_sock_name())
|
||||||
|
|
Reference in New Issue
Block a user