From 29ac57f565ac94021dee46b365daa56a3d27333e Mon Sep 17 00:00:00 2001 From: Jeff Forcier Date: Tue, 10 Oct 2017 18:24:34 -0700 Subject: String format modernization, part 1 Choosing to skip it in some edge/corner cases where it's more harmful than helpful. Also choosing to replace many non-%s specifiers with regular old {} since I don't see why one would normally care. Again, eschewing that in spots where it seems like it might matter. --- paramiko/auth_handler.py | 45 +++++++++++++++++++++------------------ paramiko/ber.py | 8 ++++--- paramiko/channel.py | 28 ++++++++++++------------ paramiko/client.py | 34 ++++++++++++++++------------- paramiko/config.py | 4 ++-- paramiko/ecdsakey.py | 4 ++-- paramiko/hostkeys.py | 16 ++++++++------ paramiko/kex_ecdh_nist.py | 2 +- paramiko/kex_gex.py | 15 +++++++------ paramiko/kex_group1.py | 2 +- paramiko/kex_gss.py | 35 +++++++++++++++++------------- paramiko/packet.py | 23 ++++++++++++-------- paramiko/pkey.py | 4 ++-- paramiko/primes.py | 2 +- paramiko/py3compat.py | 8 +++---- paramiko/server.py | 3 ++- paramiko/sftp_attr.py | 16 ++++++++------ paramiko/sftp_client.py | 54 ++++++++++++++++++++++++----------------------- 18 files changed, 167 insertions(+), 136 deletions(-) diff --git a/paramiko/auth_handler.py b/paramiko/auth_handler.py index b6d07f65..263ad8cf 100644 --- a/paramiko/auth_handler.py +++ b/paramiko/auth_handler.py @@ -320,7 +320,8 @@ class AuthHandler (object): self.transport.send_message(m) else: raise SSHException( - "Received Package: %s" % MSG_NAMES[ptype]) + "Received Package: {}".format(MSG_NAMES[ptype]) + ) m = Message() m.add_byte(cMSG_USERAUTH_GSSAPI_MIC) # send the MIC to the server @@ -336,17 +337,17 @@ class AuthHandler (object): min_status = m.get_int() err_msg = m.get_string() m.get_string() # Lang tag - discarded - raise SSHException("GSS-API Error:\nMajor Status: %s\n\ - Minor Status: %s\ \nError Message:\ - %s\n") % (str(maj_status), - str(min_status), - err_msg) + raise SSHException("""GSS-API Error: +Major Status: {} +Minor Status: {} +Error Message: {} +""".format(maj_status, min_status, err_msg)) elif ptype == MSG_USERAUTH_FAILURE: self._parse_userauth_failure(m) return else: raise SSHException( - "Received Package: %s" % MSG_NAMES[ptype]) + "Received Package: {}".format(MSG_NAMES[ptype])) elif ( self.auth_method == 'gssapi-keyex' and self.transport.gss_kex_used @@ -359,22 +360,22 @@ class AuthHandler (object): pass else: raise SSHException( - 'Unknown auth method "%s"' % self.auth_method) + 'Unknown auth method "{}"'.format(self.auth_method)) self.transport._send_message(m) else: self.transport._log( DEBUG, - 'Service request "%s" accepted (?)' % service) + 'Service request "{}" accepted (?)'.format(service)) def _send_auth_result(self, username, method, result): # okay, send result m = Message() if result == AUTH_SUCCESSFUL: - self.transport._log(INFO, 'Auth granted (%s).' % method) + self.transport._log(INFO, 'Auth granted ({}).'.format(method)) m.add_byte(cMSG_USERAUTH_SUCCESS) self.authenticated = True else: - self.transport._log(INFO, 'Auth rejected (%s).' % method) + self.transport._log(INFO, 'Auth rejected ({}).'.format(method)) m.add_byte(cMSG_USERAUTH_FAILURE) m.add_string( self.transport.server_object.get_allowed_auths(username)) @@ -419,8 +420,10 @@ class AuthHandler (object): method = m.get_text() self.transport._log( DEBUG, - 'Auth request (type=%s) service=%s, username=%s' % ( - method, service, username)) + 'Auth request (type={}) service={}, username={}'.format( + method, service, username + ) + ) if service != 'ssh-connection': self._disconnect_service_not_available() return @@ -472,7 +475,7 @@ class AuthHandler (object): except SSHException as e: self.transport._log( INFO, - 'Auth rejected: public key: %s' % str(e)) + 'Auth rejected: public key: {}'.format(str(e))) key = None except Exception as e: msg = 'Auth rejected: unsupported or mangled public key ({}: {})' # noqa @@ -571,7 +574,7 @@ class AuthHandler (object): def _parse_userauth_success(self, m): self.transport._log( INFO, - 'Authentication (%s) successful!' % self.auth_method) + 'Authentication ({}) successful!'.format(self.auth_method)) self.authenticated = True self.transport._auth_trigger() if self.auth_event is not None: @@ -587,7 +590,7 @@ class AuthHandler (object): elif self.auth_method not in authlist: self.transport._log( DEBUG, - 'Authentication type (%s) not permitted.' % self.auth_method) + 'Authentication type ({}) not permitted.'.format(self.auth_method)) self.transport._log( DEBUG, 'Allowed methods: ' + str(authlist)) @@ -596,7 +599,7 @@ class AuthHandler (object): else: self.transport._log( INFO, - 'Authentication (%s) failed.' % self.auth_method) + 'Authentication ({}) failed.'.format(self.auth_method)) self.authenticated = False self.username = None if self.auth_event is not None: @@ -605,7 +608,7 @@ class AuthHandler (object): def _parse_userauth_banner(self, m): banner = m.get_string() self.banner = banner - self.transport._log(INFO, 'Auth banner: %s' % banner) + self.transport._log(INFO, 'Auth banner: {}'.format(banner)) # who cares. def _parse_userauth_info_request(self, m): @@ -646,9 +649,9 @@ class AuthHandler (object): def _handle_local_gss_failure(self, e): self.transport.saved_exception = e - self.transport._log(DEBUG, "GSSAPI failure: %s" % str(e)) - self.transport._log(INFO, 'Authentication (%s) failed.' % - self.auth_method) + self.transport._log(DEBUG, "GSSAPI failure: {}".format(e)) + self.transport._log(INFO, 'Authentication ({}) failed.'.format( + self.auth_method)) self.authenticated = False self.username = None if self.auth_event is not None: diff --git a/paramiko/ber.py b/paramiko/ber.py index 7725f944..876347e0 100644 --- a/paramiko/ber.py +++ b/paramiko/ber.py @@ -88,8 +88,8 @@ class BER(object): return util.inflate_long(data) else: # 1: boolean (00 false, otherwise true) - raise BERException( - 'Unknown ber encoding type %d (robey is lazy)' % ident) + msg = 'Unknown ber encoding type {:d} (robey is lazy)' + raise BERException(msg.format(ident)) @staticmethod def decode_sequence(data): @@ -125,7 +125,9 @@ class BER(object): elif (type(x) is list) or (type(x) is tuple): self.encode_tlv(0x30, self.encode_sequence(x)) else: - raise BERException('Unknown type for encoding: %s' % repr(type(x))) + raise BERException( + 'Unknown type for encoding: {!r}'.format(type(x)) + ) @staticmethod def encode_sequence(data): diff --git a/paramiko/channel.py b/paramiko/channel.py index f3572c66..749749d9 100644 --- a/paramiko/channel.py +++ b/paramiko/channel.py @@ -135,7 +135,7 @@ class Channel (ClosingContextManager): """ Return a string representation of this object, for debugging. """ - out = ' 0: - out += ' in-buffer=%d' % (len(self.in_buffer),) + out += ' in-buffer={}'.format(len(self.in_buffer)) out += ' -> ' + repr(self.transport) out += '>' return out @@ -976,7 +976,7 @@ class Channel (ClosingContextManager): # a window update self.in_window_threshold = window_size // 10 self.in_window_sofar = 0 - self._log(DEBUG, 'Max packet in: %d bytes' % max_packet_size) + self._log(DEBUG, 'Max packet in: {} bytes'.format(max_packet_size)) def _set_remote_channel(self, chanid, window_size, max_packet_size): self.remote_chanid = chanid @@ -985,10 +985,10 @@ class Channel (ClosingContextManager): max_packet_size ) self.active = 1 - self._log(DEBUG, 'Max packet out: %d bytes' % self.out_max_packet_size) + self._log(DEBUG, 'Max packet out: {} bytes'.format(self.out_max_packet_size)) def _request_success(self, m): - self._log(DEBUG, 'Sesch channel %d request ok' % self.chanid) + self._log(DEBUG, 'Sesch channel {} request ok'.format(self.chanid)) self.event_ready = True self.event.set() return @@ -1017,7 +1017,7 @@ class Channel (ClosingContextManager): if code != 1: self._log( ERROR, - 'unknown extended_data type %d; discarding' % code + 'unknown extended_data type {}; discarding'.format(code) ) return if self.combine_stderr: @@ -1030,7 +1030,7 @@ class Channel (ClosingContextManager): self.lock.acquire() try: if self.ultra_debug: - self._log(DEBUG, 'window up %d' % nbytes) + self._log(DEBUG, 'window up {}'.format(nbytes)) self.out_window_size += nbytes self.out_buffer_cv.notifyAll() finally: @@ -1122,7 +1122,7 @@ class Channel (ClosingContextManager): else: ok = server.check_channel_forward_agent_request(self) else: - self._log(DEBUG, 'Unhandled channel request "%s"' % key) + self._log(DEBUG, 'Unhandled channel request "{}"'.format(key)) ok = False if want_reply: m = Message() @@ -1144,7 +1144,7 @@ class Channel (ClosingContextManager): self._pipe.set_forever() finally: self.lock.release() - self._log(DEBUG, 'EOF received (%s)', self._name) + self._log(DEBUG, 'EOF received ({})'.format(self._name)) def _handle_close(self, m): self.lock.acquire() @@ -1216,7 +1216,7 @@ class Channel (ClosingContextManager): m.add_byte(cMSG_CHANNEL_EOF) m.add_int(self.remote_chanid) self.eof_sent = True - self._log(DEBUG, 'EOF sent (%s)', self._name) + self._log(DEBUG, 'EOF sent ({})'.format(self._name)) return m def _close_internal(self): @@ -1250,12 +1250,12 @@ class Channel (ClosingContextManager): if self.closed or self.eof_received or not self.active: return 0 if self.ultra_debug: - self._log(DEBUG, 'addwindow %d' % n) + self._log(DEBUG, 'addwindow {}'.format(n)) self.in_window_sofar += n if self.in_window_sofar <= self.in_window_threshold: return 0 if self.ultra_debug: - self._log(DEBUG, 'addwindow send %d' % self.in_window_sofar) + self._log(DEBUG, 'addwindow send {}'.format(self.in_window_sofar)) out = self.in_window_sofar self.in_window_sofar = 0 return out @@ -1298,7 +1298,7 @@ class Channel (ClosingContextManager): size = self.out_max_packet_size - 64 self.out_window_size -= size if self.ultra_debug: - self._log(DEBUG, 'window down to %d' % self.out_window_size) + self._log(DEBUG, 'window down to {}'.format(self.out_window_size)) return size diff --git a/paramiko/client.py b/paramiko/client.py index 2808d228..b08c6e64 100644 --- a/paramiko/client.py +++ b/paramiko/client.py @@ -143,8 +143,9 @@ class SSHClient (ClosingContextManager): with open(filename, 'w') as f: for hostname, keys in self._host_keys.items(): for keytype, key in keys.items(): - f.write('%s %s %s\n' % ( - hostname, keytype, key.get_base64())) + f.write('{} {} {}\n'.format( + hostname, keytype, key.get_base64() + )) def get_host_keys(self): """ @@ -370,7 +371,7 @@ class SSHClient (ClosingContextManager): if port == SSH_PORT: server_hostkey_name = hostname else: - server_hostkey_name = "[%s]:%d" % (hostname, port) + server_hostkey_name = "[{}]:{}".format(hostname, port) our_server_keys = None our_server_keys = self._system_host_keys.get(server_hostkey_name) @@ -598,7 +599,7 @@ class SSHClient (ClosingContextManager): try: self._log( DEBUG, - 'Trying SSH key %s' % hexlify(pkey.get_fingerprint())) + 'Trying SSH key {}'.format(hexlify(pkey.get_fingerprint()))) allowed_types = set( self._transport.auth_publickey(username, pkey)) two_factor = (allowed_types & two_factor_types) @@ -631,8 +632,9 @@ class SSHClient (ClosingContextManager): try: self._log( DEBUG, - 'Trying SSH agent key %s' % hexlify( - key.get_fingerprint())) + 'Trying SSH agent key {}'.format( + hexlify(key.get_fingerprint()) + )) # for 2-factor auth a successfully auth'd key password # will return an allowed 2fac auth method allowed_types = set( @@ -656,7 +658,7 @@ class SSHClient (ClosingContextManager): # ~/ssh/ is for windows for directory in [".ssh", "ssh"]: full_path = os.path.expanduser( - "~/%s/id_%s" % (directory, name) + "~/{}/id_{}".format(directory, name) ) if os.path.isfile(full_path): # TODO: only do this append if below did not run @@ -736,8 +738,9 @@ class AutoAddPolicy (MissingHostKeyPolicy): client._host_keys.add(hostname, key.get_name(), key) if client._host_keys_filename is not None: client.save_host_keys(client._host_keys_filename) - client._log(DEBUG, 'Adding %s host key for %s: %s' % - (key.get_name(), hostname, hexlify(key.get_fingerprint()))) + client._log(DEBUG, 'Adding {} host key for {}: {}'.format( + key.get_name(), hostname, hexlify(key.get_fingerprint()), + )) class RejectPolicy (MissingHostKeyPolicy): @@ -747,9 +750,10 @@ class RejectPolicy (MissingHostKeyPolicy): """ def missing_host_key(self, client, hostname, key): - client._log(DEBUG, 'Rejecting %s host key for %s: %s' % - (key.get_name(), hostname, hexlify(key.get_fingerprint()))) - raise SSHException('Server %r not found in known_hosts' % hostname) + client._log(DEBUG, 'Rejecting {} host key for {}: {}'.format( + key.get_name(), hostname, hexlify(key.get_fingerprint()), + )) + raise SSHException('Server {!r} not found in known_hosts'.format(hostname)) class WarningPolicy (MissingHostKeyPolicy): @@ -758,6 +762,6 @@ class WarningPolicy (MissingHostKeyPolicy): accepting it. This is used by `.SSHClient`. """ def missing_host_key(self, client, hostname, key): - warnings.warn('Unknown %s host key for %s: %s' % - (key.get_name(), hostname, hexlify( - key.get_fingerprint()))) + warnings.warn('Unknown {} host key for {}: {}'.format( + key.get_name(), hostname, hexlify(key.get_fingerprint()), + )) diff --git a/paramiko/config.py b/paramiko/config.py index 073abb36..038d84ea 100644 --- a/paramiko/config.py +++ b/paramiko/config.py @@ -65,7 +65,7 @@ class SSHConfig (object): match = re.match(self.SETTINGS_REGEX, line) if not match: - raise Exception("Unparsable line %s" % line) + raise Exception("Unparsable line {}".format(line)) key = match.group(1).lower() value = match.group(2) @@ -239,7 +239,7 @@ class SSHConfig (object): try: return shlex.split(host) except ValueError: - raise Exception("Unparsable host %s" % host) + raise Exception("Unparsable host {}".format(host)) class LazyFqdn(object): diff --git a/paramiko/ecdsakey.py b/paramiko/ecdsakey.py index 819e1d6a..3448bc39 100644 --- a/paramiko/ecdsakey.py +++ b/paramiko/ecdsakey.py @@ -144,7 +144,7 @@ class ECDSAKey(PKey): ) curvename = msg.get_text() if curvename != self.ecdsa_curve.nist_name: - raise SSHException("Can't handle curve of type %s" % curvename) + raise SSHException("Can't handle curve of type {}".format(curvename)) pointinfo = msg.get_binary() try: @@ -249,7 +249,7 @@ class ECDSAKey(PKey): if bits is not None: curve = cls._ECDSA_CURVES.get_by_key_length(bits) if curve is None: - raise ValueError("Unsupported key length: %d" % bits) + raise ValueError("Unsupported key length: {:d}".format(bits)) curve = curve.curve_class() private_key = ec.generate_private_key(curve, backend=default_backend()) diff --git a/paramiko/hostkeys.py b/paramiko/hostkeys.py index d023b33d..7bd75bb5 100644 --- a/paramiko/hostkeys.py +++ b/paramiko/hostkeys.py @@ -300,7 +300,7 @@ class HostKeys (MutableMapping): salt = decodebytes(b(salt)) assert len(salt) == sha1().digest_size hmac = HMAC(salt, b(hostname), sha1).digest() - hostkey = '|1|%s|%s' % (u(encodebytes(salt)), u(encodebytes(hmac))) + hostkey = '|1|{}|{}'.format(u(encodebytes(salt)), u(encodebytes(hmac))) return hostkey.replace('\n', '') @@ -338,8 +338,9 @@ class HostKeyEntry: fields = line.split(' ') if len(fields) < 3: # Bad number of fields - log.info("Not enough fields found in known_hosts in line %s (%r)" % - (lineno, line)) + log.info("Not enough fields found in known_hosts in line {} ({!r})".format( + lineno, line + )) return None fields = fields[:3] @@ -359,7 +360,7 @@ class HostKeyEntry: elif keytype == 'ssh-ed25519': key = Ed25519Key(data=decodebytes(key)) else: - log.info("Unable to handle key of type %s" % (keytype,)) + log.info("Unable to handle key of type {}".format(keytype)) return None except binascii.Error as e: @@ -374,11 +375,12 @@ class HostKeyEntry: included. """ if self.valid: - return '%s %s %s\n' % ( + return '{} {} {}\n'.format( ','.join(self.hostnames), self.key.get_name(), - self.key.get_base64()) + self.key.get_base64(), + ) return None def __repr__(self): - return '' % (self.hostnames, self.key) + return ''.format(self.hostnames, self.key) diff --git a/paramiko/kex_ecdh_nist.py b/paramiko/kex_ecdh_nist.py index 702a872d..a5451c69 100644 --- a/paramiko/kex_ecdh_nist.py +++ b/paramiko/kex_ecdh_nist.py @@ -45,7 +45,7 @@ class KexNistp256(): return self._parse_kexecdh_init(m) elif not self.transport.server_mode and (ptype == _MSG_KEXECDH_REPLY): return self._parse_kexecdh_reply(m) - raise SSHException('KexECDH asked to handle packet type %d' % ptype) + raise SSHException('KexECDH asked to handle packet type {:d}'.format(ptype)) def _generate_key_pair(self): self.P = ec.generate_private_key(self.curve, default_backend()) diff --git a/paramiko/kex_gex.py b/paramiko/kex_gex.py index ba45da18..f60f49a4 100644 --- a/paramiko/kex_gex.py +++ b/paramiko/kex_gex.py @@ -92,7 +92,7 @@ class KexGex (object): elif ptype == _MSG_KEXDH_GEX_REQUEST_OLD: return self._parse_kexdh_gex_request_old(m) raise SSHException( - 'KexGex %s asked to handle packet type %d' % self.name, ptype) + 'KexGex {} asked to handle packet type {:d}'.format(self.name, ptype)) # ...internals... @@ -141,8 +141,10 @@ class KexGex (object): 'Can\'t do server-side gex with no modulus pack') self.transport._log( DEBUG, - 'Picking p (%d <= %d <= %d bits)' % ( - minbits, preferredbits, maxbits)) + 'Picking p ({} <= {} <= {} bits)'.format( + minbits, preferredbits, maxbits, + ) + ) self.g, self.p = pack.get_modulus(minbits, preferredbits, maxbits) m = Message() m.add_byte(c_MSG_KEXDH_GEX_GROUP) @@ -166,7 +168,8 @@ class KexGex (object): raise SSHException( 'Can\'t do server-side gex with no modulus pack') self.transport._log( - DEBUG, 'Picking p (~ %d bits)' % (self.preferred_bits,)) + DEBUG, 'Picking p (~ {} bits)'.format(self.preferred_bits) + ) self.g, self.p = pack.get_modulus( self.min_bits, self.preferred_bits, self.max_bits) m = Message() @@ -185,8 +188,8 @@ class KexGex (object): if (bitlen < 1024) or (bitlen > 8192): raise SSHException( 'Server-generated gex p (don\'t ask) is out of range ' - '(%d bits)' % bitlen) - self.transport._log(DEBUG, 'Got server p (%d bits)' % bitlen) + '({} bits)'.format(bitlen)) + self.transport._log(DEBUG, 'Got server p ({} bits)'.format(bitlen)) self._generate_x() # now compute e = g^x mod p self.e = pow(self.g, self.x, self.p) diff --git a/paramiko/kex_group1.py b/paramiko/kex_group1.py index e8f042b1..64d463cd 100644 --- a/paramiko/kex_group1.py +++ b/paramiko/kex_group1.py @@ -73,7 +73,7 @@ class KexGroup1(object): return self._parse_kexdh_init(m) elif not self.transport.server_mode and (ptype == _MSG_KEXDH_REPLY): return self._parse_kexdh_reply(m) - raise SSHException('KexGroup1 asked to handle packet type %d' % ptype) + raise SSHException('KexGroup1 asked to handle packet type {:d}'.format(ptype)) # ...internals... diff --git a/paramiko/kex_gss.py b/paramiko/kex_gss.py index a2ea9fca..e21620fe 100644 --- a/paramiko/kex_gss.py +++ b/paramiko/kex_gss.py @@ -120,8 +120,8 @@ class KexGSSGroup1(object): return self._parse_kexgss_complete(m) elif ptype == MSG_KEXGSS_ERROR: return self._parse_kexgss_error(m) - raise SSHException('GSS KexGroup1 asked to handle packet type %d' - % ptype) + msg = 'GSS KexGroup1 asked to handle packet type {:d}' + raise SSHException(msg.format(ptype)) # ## internals... @@ -282,10 +282,11 @@ class KexGSSGroup1(object): min_status = m.get_int() err_msg = m.get_string() m.get_string() # we don't care about the language! - raise SSHException("GSS-API Error:\nMajor Status: %s\nMinor Status: %s\ - \nError Message: %s\n") % (str(maj_status), - str(min_status), - err_msg) + raise SSHException("""GSS-API Error: +Major Status: {} +Minor Status: {} +Error Message: {} +""".format(maj_status, min_status, err_msg)) class KexGSSGroup14(KexGSSGroup1): @@ -361,7 +362,8 @@ class KexGSSGex(object): return self._parse_kexgss_complete(m) elif ptype == MSG_KEXGSS_ERROR: return self._parse_kexgss_error(m) - raise SSHException('KexGex asked to handle packet type %d' % ptype) + msg = 'KexGex asked to handle packet type {:d}' + raise SSHException(msg.format(ptype)) # ## internals... @@ -416,8 +418,10 @@ class KexGSSGex(object): 'Can\'t do server-side gex with no modulus pack') self.transport._log( DEBUG, # noqa - 'Picking p (%d <= %d <= %d bits)' % ( - minbits, preferredbits, maxbits)) + 'Picking p ({} <= {} <= {} bits)'.format( + minbits, preferredbits, maxbits, + ) + ) self.g, self.p = pack.get_modulus(minbits, preferredbits, maxbits) m = Message() m.add_byte(c_MSG_KEXGSS_GROUP) @@ -439,8 +443,8 @@ class KexGSSGex(object): if (bitlen < 1024) or (bitlen > 8192): raise SSHException( 'Server-generated gex p (don\'t ask) is out of range ' - '(%d bits)' % bitlen) - self.transport._log(DEBUG, 'Got server p (%d bits)' % bitlen) # noqa + '({} bits)'.format(bitlen)) + self.transport._log(DEBUG, 'Got server p ({} bits)'.format(bitlen)) # noqa self._generate_x() # now compute e = g^x mod p self.e = pow(self.g, self.x, self.p) @@ -603,10 +607,11 @@ class KexGSSGex(object): min_status = m.get_int() err_msg = m.get_string() m.get_string() # we don't care about the language (lang_tag)! - raise SSHException("GSS-API Error:\nMajor Status: %s\nMinor Status: %s\ - \nError Message: %s\n") % (str(maj_status), - str(min_status), - err_msg) + raise SSHException("""GSS-API Error: +Major Status: {} +Minor Status: {} +Error Message: {} +""".format(maj_status, min_status, err_msg)) class NullHostKey(object): diff --git a/paramiko/packet.py b/paramiko/packet.py index 95a26c6e..840a59a7 100644 --- a/paramiko/packet.py +++ b/paramiko/packet.py @@ -368,7 +368,7 @@ class Packetizer (object): if cmd in MSG_NAMES: cmd_name = MSG_NAMES[cmd] else: - cmd_name = '$%x' % cmd + cmd_name = '${:x}'.format(cmd) orig_len = len(data) self.__write_lock.acquire() try: @@ -378,7 +378,8 @@ class Packetizer (object): if self.__dump_packets: self._log( DEBUG, - 'Write packet <%s>, length %d' % (cmd_name, orig_len)) + 'Write packet <{}>, length {}'.format(cmd_name, orig_len) + ) self._log(DEBUG, util.format_binary(packet, 'OUT: ')) if self.__block_engine_out is not None: out = self.__block_engine_out.update(packet) @@ -404,8 +405,9 @@ class Packetizer (object): ) if sent_too_much and not self.__need_rekey: # only ask once for rekeying - self._log(DEBUG, 'Rekeying (hit %d packets, %d bytes sent)' % - (self.__sent_packets, self.__sent_bytes)) + self._log(DEBUG, 'Rekeying (hit {} packets, {} bytes sent)'.format( + self.__sent_packets, self.__sent_bytes, + )) self.__received_bytes_overflow = 0 self.__received_packets_overflow = 0 self._trigger_rekey() @@ -456,7 +458,8 @@ class Packetizer (object): if self.__dump_packets: self._log( DEBUG, - 'Got payload (%d bytes, %d padding)' % (packet_size, padding)) + 'Got payload ({} bytes, {} padding)'.format(packet_size, padding), + ) if self.__compress_engine_in is not None: payload = self.__compress_engine_in(payload) @@ -483,8 +486,9 @@ class Packetizer (object): elif (self.__received_packets >= self.REKEY_PACKETS) or \ (self.__received_bytes >= self.REKEY_BYTES): # only ask once for rekeying - self._log(DEBUG, 'Rekeying (hit %d packets, %d bytes received)' % - (self.__received_packets, self.__received_bytes)) + self._log(DEBUG, 'Rekeying (hit {} packets, {} bytes received)'.format( + self.__received_packets, self.__received_bytes, + )) self.__received_bytes_overflow = 0 self.__received_packets_overflow = 0 self._trigger_rekey() @@ -493,11 +497,12 @@ class Packetizer (object): if cmd in MSG_NAMES: cmd_name = MSG_NAMES[cmd] else: - cmd_name = '$%x' % cmd + cmd_name = '${:x}'.format(cmd) if self.__dump_packets: self._log( DEBUG, - 'Read packet <%s>, length %d' % (cmd_name, len(payload))) + 'Read packet <{}>, length {}'.format(cmd_name, len(payload)) + ) return cmd, msg # ...protected... diff --git a/paramiko/pkey.py b/paramiko/pkey.py index 533d0797..ae01dca2 100644 --- a/paramiko/pkey.py +++ b/paramiko/pkey.py @@ -312,14 +312,14 @@ class PKey(object): # encrypted keyfile: will need a password if headers['proc-type'] != '4,ENCRYPTED': raise SSHException( - 'Unknown private key structure "%s"' % headers['proc-type']) + 'Unknown private key structure "{}"'.format(headers['proc-type'])) try: encryption_type, saltstr = headers['dek-info'].split(',') except: raise SSHException("Can't parse DEK-info in private key file") if encryption_type not in self._CIPHER_TABLE: raise SSHException( - 'Unknown private key cipher "%s"' % encryption_type) + 'Unknown private key cipher "{}"'.format(encryption_type)) # if no password was passed in, # raise an exception pointing out that we need one if password is None: diff --git a/paramiko/primes.py b/paramiko/primes.py index 65617914..ca8f9bec 100644 --- a/paramiko/primes.py +++ b/paramiko/primes.py @@ -91,7 +91,7 @@ class ModulusPack (object): bl = util.bit_length(modulus) if (bl != size) and (bl != size + 1): self.discarded.append( - (modulus, 'incorrectly reported bit length %d' % size)) + (modulus, 'incorrectly reported bit length {}'.format(size))) return if bl not in self.pack: self.pack[bl] = [] diff --git a/paramiko/py3compat.py b/paramiko/py3compat.py index 6703ace8..cb9de412 100644 --- a/paramiko/py3compat.py +++ b/paramiko/py3compat.py @@ -46,7 +46,7 @@ if PY2: elif isinstance(s, buffer): # NOQA return s else: - raise TypeError("Expected unicode or bytes, got %r" % s) + raise TypeError("Expected unicode or bytes, got {!r}".format(s)) def u(s, encoding='utf8'): # NOQA @@ -58,7 +58,7 @@ if PY2: elif isinstance(s, buffer): # NOQA return s.decode(encoding) else: - raise TypeError("Expected unicode or bytes, got %r" % s) + raise TypeError("Expected unicode or bytes, got {!r}".format(s)) def b2s(s): @@ -135,7 +135,7 @@ else: elif isinstance(s, str): return s.encode(encoding) else: - raise TypeError("Expected unicode or bytes, got %r" % s) + raise TypeError("Expected unicode or bytes, got {!r}".format(s)) def u(s, encoding='utf8'): """cast bytes or unicode to unicode""" @@ -144,7 +144,7 @@ else: elif isinstance(s, str): return s else: - raise TypeError("Expected unicode or bytes, got %r" % s) + raise TypeError("Expected unicode or bytes, got {!r}".format(s)) def b2s(s): return s.decode() if isinstance(s, bytes) else s diff --git a/paramiko/server.py b/paramiko/server.py index 1f96451e..c80fbc97 100644 --- a/paramiko/server.py +++ b/paramiko/server.py @@ -667,7 +667,8 @@ class SubsystemHandler (threading.Thread): def _run(self): try: self.__transport._log( - DEBUG, 'Starting handler for subsystem %s' % self.__name) + DEBUG, 'Starting handler for subsystem {}'.format(self.__name) + ) self.start_subsystem(self.__name, self.__transport, self.__channel) except Exception as e: self.__transport._log( diff --git a/paramiko/sftp_attr.py b/paramiko/sftp_attr.py index 5597948a..ea12b2f6 100644 --- a/paramiko/sftp_attr.py +++ b/paramiko/sftp_attr.py @@ -82,7 +82,7 @@ class SFTPAttributes (object): return attr def __repr__(self): - return '' % self._debug_str() + return ''.format(self._debug_str()) # ...internals... @classmethod @@ -146,15 +146,15 @@ class SFTPAttributes (object): def _debug_str(self): out = '[ ' if self.st_size is not None: - out += 'size=%d ' % self.st_size + out += 'size={} '.format(self.st_size) if (self.st_uid is not None) and (self.st_gid is not None): - out += 'uid=%d gid=%d ' % (self.st_uid, self.st_gid) + out += 'uid={} gid={} '.format(self.st_uid, self.st_gid) if self.st_mode is not None: out += 'mode=' + oct(self.st_mode) + ' ' if (self.st_atime is not None) and (self.st_mtime is not None): - out += 'atime=%d mtime=%d ' % (self.st_atime, self.st_mtime) + out += 'atime={} mtime={} '.format(self.st_atime, self.st_mtime) for k, v in self.attr.items(): - out += '"%s"=%r ' % (str(k), v) + out += '"{}"={!r} '.format(str(k), v) out += ']' return out @@ -222,8 +222,12 @@ class SFTPAttributes (object): if size is None: size = 0 + # TODO: not sure this actually worked as expected beforehand, leaving + # it untouched for the time being, re: .format() upgrade, until someone + # has time to doublecheck return '%s 1 %-8d %-8d %8d %-12s %s' % ( - ks, uid, gid, size, datestr, filename) + ks, uid, gid, size, datestr, filename, + ) def asbytes(self): return b(str(self)) diff --git a/paramiko/sftp_client.py b/paramiko/sftp_client.py index 14b8b58a..d52cf943 100644 --- a/paramiko/sftp_client.py +++ b/paramiko/sftp_client.py @@ -105,7 +105,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): raise SSHException('EOF during negotiation') self._log( INFO, - 'Opened sftp connection (server version %d)' % server_version) + 'Opened sftp connection (server version {})'.format(server_version)) @classmethod def from_transport(cls, t, window_size=None, max_packet_size=None): @@ -143,6 +143,8 @@ class SFTPClient(BaseSFTP, ClosingContextManager): for m in msg: self._log(level, m, *args) else: + # NOTE: these bits MUST continue using %-style format junk because + # logging.Logger.log() explicitly requires it. Grump. # escape '%' in msg (they could come from file or directory names) # before logging msg = msg.replace('%', '%%') @@ -200,7 +202,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): .. versionadded:: 1.2 """ path = self._adjust_cwd(path) - self._log(DEBUG, 'listdir(%r)' % path) + self._log(DEBUG, 'listdir({!r})'.format(path)) t, msg = self._request(CMD_OPENDIR, path) if t != CMD_HANDLE: raise SFTPError('Expected handle') @@ -239,7 +241,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): .. versionadded:: 1.15 """ path = self._adjust_cwd(path) - self._log(DEBUG, 'listdir(%r)' % path) + self._log(DEBUG, 'listdir({!r})'.format(path)) t, msg = self._request(CMD_OPENDIR, path) if t != CMD_HANDLE: @@ -322,7 +324,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :raises: ``IOError`` -- if the file could not be opened. """ filename = self._adjust_cwd(filename) - self._log(DEBUG, 'open(%r, %r)' % (filename, mode)) + self._log(DEBUG, 'open({!r}, {!r})'.format(filename, mode)) imode = 0 if ('r' in mode) or ('+' in mode): imode |= SFTP_FLAG_READ @@ -341,7 +343,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): handle = msg.get_binary() self._log( DEBUG, - 'open(%r, %r) -> %s' % (filename, mode, u(hexlify(handle)))) + 'open({!r}, {!r}) -> {}'.format(filename, mode, u(hexlify(handle)))) return SFTPFile(self, handle, mode, bufsize) # Python continues to vacillate about "open" vs "file"... @@ -357,7 +359,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :raises: ``IOError`` -- if the path refers to a folder (directory) """ path = self._adjust_cwd(path) - self._log(DEBUG, 'remove(%r)' % path) + self._log(DEBUG, 'remove({!r})'.format(path)) self._request(CMD_REMOVE, path) unlink = remove @@ -382,7 +384,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): """ oldpath = self._adjust_cwd(oldpath) newpath = self._adjust_cwd(newpath) - self._log(DEBUG, 'rename(%r, %r)' % (oldpath, newpath)) + self._log(DEBUG, 'rename({!r}, {!r})'.format(oldpath, newpath)) self._request(CMD_RENAME, oldpath, newpath) def posix_rename(self, oldpath, newpath): @@ -402,7 +404,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): """ oldpath = self._adjust_cwd(oldpath) newpath = self._adjust_cwd(newpath) - self._log(DEBUG, 'posix_rename(%r, %r)' % (oldpath, newpath)) + self._log(DEBUG, 'posix_rename({!r}, {!r})'.format(oldpath, newpath)) self._request( CMD_EXTENDED, "posix-rename@openssh.com", oldpath, newpath ) @@ -417,7 +419,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param int mode: permissions (posix-style) for the newly-created folder """ path = self._adjust_cwd(path) - self._log(DEBUG, 'mkdir(%r, %r)' % (path, mode)) + self._log(DEBUG, 'mkdir({!r}, {!r})'.format(path, mode)) attr = SFTPAttributes() attr.st_mode = mode self._request(CMD_MKDIR, path, attr) @@ -429,7 +431,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param str path: name of the folder to remove """ path = self._adjust_cwd(path) - self._log(DEBUG, 'rmdir(%r)' % path) + self._log(DEBUG, 'rmdir({!r})'.format(path)) self._request(CMD_RMDIR, path) def stat(self, path): @@ -452,7 +454,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): file """ path = self._adjust_cwd(path) - self._log(DEBUG, 'stat(%r)' % path) + self._log(DEBUG, 'stat({!r})'.format(path)) t, msg = self._request(CMD_STAT, path) if t != CMD_ATTRS: raise SFTPError('Expected attributes') @@ -470,7 +472,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): file """ path = self._adjust_cwd(path) - self._log(DEBUG, 'lstat(%r)' % path) + self._log(DEBUG, 'lstat({!r})'.format(path)) t, msg = self._request(CMD_LSTAT, path) if t != CMD_ATTRS: raise SFTPError('Expected attributes') @@ -484,7 +486,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param str dest: path of the newly created symlink """ dest = self._adjust_cwd(dest) - self._log(DEBUG, 'symlink(%r, %r)' % (source, dest)) + self._log(DEBUG, 'symlink({!r}, {!r})'.format(source, dest)) source = bytestring(source) self._request(CMD_SYMLINK, source, dest) @@ -498,7 +500,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param int mode: new permissions """ path = self._adjust_cwd(path) - self._log(DEBUG, 'chmod(%r, %r)' % (path, mode)) + self._log(DEBUG, 'chmod({!r}, {!r})'.format(path, mode)) attr = SFTPAttributes() attr.st_mode = mode self._request(CMD_SETSTAT, path, attr) @@ -515,7 +517,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param int gid: new group id """ path = self._adjust_cwd(path) - self._log(DEBUG, 'chown(%r, %r, %r)' % (path, uid, gid)) + self._log(DEBUG, 'chown({!r}, {!r}, {!r})'.format(path, uid, gid)) attr = SFTPAttributes() attr.st_uid, attr.st_gid = uid, gid self._request(CMD_SETSTAT, path, attr) @@ -537,7 +539,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): path = self._adjust_cwd(path) if times is None: times = (time.time(), time.time()) - self._log(DEBUG, 'utime(%r, %r)' % (path, times)) + self._log(DEBUG, 'utime({!r}, {!r})'.format(path, times)) attr = SFTPAttributes() attr.st_atime, attr.st_mtime = times self._request(CMD_SETSTAT, path, attr) @@ -552,7 +554,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :param int size: the new size of the file """ path = self._adjust_cwd(path) - self._log(DEBUG, 'truncate(%r, %r)' % (path, size)) + self._log(DEBUG, 'truncate({!r}, {!r})'.format(path, size)) attr = SFTPAttributes() attr.st_size = size self._request(CMD_SETSTAT, path, attr) @@ -567,7 +569,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :return: target path, as a `str` """ path = self._adjust_cwd(path) - self._log(DEBUG, 'readlink(%r)' % path) + self._log(DEBUG, 'readlink({!r})'.format(path)) t, msg = self._request(CMD_READLINK, path) if t != CMD_NAME: raise SFTPError('Expected name response') @@ -575,7 +577,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): if count == 0: return None if count != 1: - raise SFTPError('Readlink returned %d results' % count) + raise SFTPError('Readlink returned {} results'.format(count)) return _to_unicode(msg.get_string()) def normalize(self, path): @@ -591,13 +593,13 @@ class SFTPClient(BaseSFTP, ClosingContextManager): :raises: ``IOError`` -- if the path can't be resolved on the server """ path = self._adjust_cwd(path) - self._log(DEBUG, 'normalize(%r)' % path) + self._log(DEBUG, 'normalize({!r})'.format(path)) t, msg = self._request(CMD_REALPATH, path) if t != CMD_NAME: raise SFTPError('Expected name response') count = msg.get_int() if count != 1: - raise SFTPError('Realpath returned %d results' % count) + raise SFTPError('Realpath returned {} results'.format(count)) return msg.get_text() def chdir(self, path=None): @@ -621,7 +623,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): return if not stat.S_ISDIR(self.stat(path).st_mode): raise SFTPError( - errno.ENOTDIR, "%s: %s" % (os.strerror(errno.ENOTDIR), path)) + errno.ENOTDIR, "{}: {}".format(os.strerror(errno.ENOTDIR), path)) self._cwd = b(self.normalize(path)) def getcwd(self): @@ -683,7 +685,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): s = self.stat(remotepath) if s.st_size != size: raise IOError( - 'size mismatch in put! %d != %d' % (s.st_size, size)) + 'size mismatch in put! {} != {}'.format(s.st_size, size)) else: s = SFTPAttributes() return s @@ -765,7 +767,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): s = os.stat(localpath) if s.st_size != size: raise IOError( - 'size mismatch in get! %d != %d' % (s.st_size, size)) + 'size mismatch in get! {} != {}'.format(s.st_size, size)) # ...internals... @@ -803,7 +805,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): try: t, data = self._read_packet() except EOFError as e: - raise SSHException('Server connection dropped: %s' % str(e)) + raise SSHException('Server connection dropped: {}'.format(e)) msg = Message(data) num = msg.get_int() self._lock.acquire() @@ -811,7 +813,7 @@ class SFTPClient(BaseSFTP, ClosingContextManager): if num not in self._expecting: # might be response for a file that was closed before # responses came back - self._log(DEBUG, 'Unexpected response #%d' % (num,)) + self._log(DEBUG, 'Unexpected response #{}'.format(num)) if waitfor is None: # just doing a single check break -- cgit v1.2.1