Skip to content

Commit

Permalink
Merge remote-tracking branch 'scottkmaxwell/py3-support-without-py25'…
Browse files Browse the repository at this point in the history
… into python3

Conflicts:
	dev-requirements.txt
	paramiko/__init__.py
	paramiko/file.py
	paramiko/hostkeys.py
	paramiko/message.py
	paramiko/proxy.py
	paramiko/server.py
	paramiko/transport.py
	paramiko/util.py
	paramiko/win_pageant.py
	setup.py
  • Loading branch information
bitprophet committed Mar 6, 2014
2 parents bd61c7c + ae078f5 commit b2be63e
Show file tree
Hide file tree
Showing 64 changed files with 1,978 additions and 1,601 deletions.
2 changes: 2 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ language: python
python:
- "2.6"
- "2.7"
- "3.2"
- "3.3"
install:
# Self-install for setup.py-driven deps
- pip install -e .
Expand Down
4 changes: 2 additions & 2 deletions README
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ What
----

"paramiko" is a combination of the esperanto words for "paranoid" and
"friend". it's a module for python 2.5+ that implements the SSH2 protocol
"friend". it's a module for python 2.6+ that implements the SSH2 protocol
for secure (encrypted and authenticated) connections to remote machines.
unlike SSL (aka TLS), SSH2 protocol does not require hierarchical
certificates signed by a powerful central authority. you may know SSH2 as
Expand All @@ -34,7 +34,7 @@ that should have come with this archive.
Requirements
------------

- python 2.5 or better <http://www.python.org/>
- python 2.6 or better <http://www.python.org/>
- pycrypto 2.1 or better <https://www.dlitz.net/software/pycrypto/>
- ecdsa 0.9 or better <https://pypi.python.org/pypi/ecdsa>

Expand Down
53 changes: 28 additions & 25 deletions demos/demo.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,13 @@
import sys
import time
import traceback
from paramiko.py3compat import input

import paramiko
import interactive
try:
import interactive
except ImportError:
from . import interactive


def agent_auth(transport, username):
Expand All @@ -45,24 +49,24 @@ def agent_auth(transport, username):
return

for key in agent_keys:
print 'Trying ssh-agent key %s' % hexlify(key.get_fingerprint()),
print('Trying ssh-agent key %s' % hexlify(key.get_fingerprint()))
try:
transport.auth_publickey(username, key)
print '... success!'
print('... success!')
return
except paramiko.SSHException:
print '... nope.'
print('... nope.')


def manual_auth(username, hostname):
default_auth = 'p'
auth = raw_input('Auth by (p)assword, (r)sa key, or (d)ss key? [%s] ' % default_auth)
auth = input('Auth by (p)assword, (r)sa key, or (d)ss key? [%s] ' % default_auth)
if len(auth) == 0:
auth = default_auth

if auth == 'r':
default_path = os.path.join(os.environ['HOME'], '.ssh', 'id_rsa')
path = raw_input('RSA key [%s]: ' % default_path)
path = input('RSA key [%s]: ' % default_path)
if len(path) == 0:
path = default_path
try:
Expand All @@ -73,7 +77,7 @@ def manual_auth(username, hostname):
t.auth_publickey(username, key)
elif auth == 'd':
default_path = os.path.join(os.environ['HOME'], '.ssh', 'id_dsa')
path = raw_input('DSS key [%s]: ' % default_path)
path = input('DSS key [%s]: ' % default_path)
if len(path) == 0:
path = default_path
try:
Expand All @@ -96,9 +100,9 @@ def manual_auth(username, hostname):
if hostname.find('@') >= 0:
username, hostname = hostname.split('@')
else:
hostname = raw_input('Hostname: ')
hostname = input('Hostname: ')
if len(hostname) == 0:
print '*** Hostname required.'
print('*** Hostname required.')
sys.exit(1)
port = 22
if hostname.find(':') >= 0:
Expand All @@ -109,8 +113,8 @@ def manual_auth(username, hostname):
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.connect((hostname, port))
except Exception, e:
print '*** Connect failed: ' + str(e)
except Exception as e:
print('*** Connect failed: ' + str(e))
traceback.print_exc()
sys.exit(1)

Expand All @@ -119,7 +123,7 @@ def manual_auth(username, hostname):
try:
t.start_client()
except paramiko.SSHException:
print '*** SSH negotiation failed.'
print('*** SSH negotiation failed.')
sys.exit(1)

try:
Expand All @@ -128,47 +132,46 @@ def manual_auth(username, hostname):
try:
keys = paramiko.util.load_host_keys(os.path.expanduser('~/ssh/known_hosts'))
except IOError:
print '*** Unable to open host keys file'
print('*** Unable to open host keys file')
keys = {}

# check server's host key -- this is important.
key = t.get_remote_server_key()
if not keys.has_key(hostname):
print '*** WARNING: Unknown host key!'
elif not keys[hostname].has_key(key.get_name()):
print '*** WARNING: Unknown host key!'
if hostname not in keys:
print('*** WARNING: Unknown host key!')
elif key.get_name() not in keys[hostname]:
print('*** WARNING: Unknown host key!')
elif keys[hostname][key.get_name()] != key:
print '*** WARNING: Host key has changed!!!'
print('*** WARNING: Host key has changed!!!')
sys.exit(1)
else:
print '*** Host key OK.'
print('*** Host key OK.')

# get username
if username == '':
default_username = getpass.getuser()
username = raw_input('Username [%s]: ' % default_username)
username = input('Username [%s]: ' % default_username)
if len(username) == 0:
username = default_username

agent_auth(t, username)
if not t.is_authenticated():
manual_auth(username, hostname)
if not t.is_authenticated():
print '*** Authentication failed. :('
print('*** Authentication failed. :(')
t.close()
sys.exit(1)

chan = t.open_session()
chan.get_pty()
chan.invoke_shell()
print '*** Here we go!'
print
print('*** Here we go!\n')
interactive.interactive_shell(chan)
chan.close()
t.close()

except Exception, e:
print '*** Caught exception: ' + str(e.__class__) + ': ' + str(e)
except Exception as e:
print('*** Caught exception: ' + str(e.__class__) + ': ' + str(e))
traceback.print_exc()
try:
t.close()
Expand Down
23 changes: 11 additions & 12 deletions demos/demo_keygen.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,7 @@
# You should have received a copy of the GNU Lesser General Public License
# along with Paramiko; if not, write to the Free Software Foundation, Inc.,
# 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
from __future__ import with_statement

import string
import sys

from binascii import hexlify
Expand All @@ -28,6 +26,7 @@
from paramiko import DSSKey
from paramiko import RSAKey
from paramiko.ssh_exception import SSHException
from paramiko.py3compat import u

usage="""
%prog [-v] [-b bits] -t type [-N new_passphrase] [-f output_keyfile]"""
Expand All @@ -47,16 +46,16 @@
def progress(arg=None):

if not arg:
print '0%\x08\x08\x08',
sys.stdout.write('0%\x08\x08\x08 ')
sys.stdout.flush()
elif arg[0] == 'p':
print '25%\x08\x08\x08\x08',
sys.stdout.write('25%\x08\x08\x08\x08 ')
sys.stdout.flush()
elif arg[0] == 'h':
print '50%\x08\x08\x08\x08',
sys.stdout.write('50%\x08\x08\x08\x08 ')
sys.stdout.flush()
elif arg[0] == 'x':
print '75%\x08\x08\x08\x08',
sys.stdout.write('75%\x08\x08\x08\x08 ')
sys.stdout.flush()

if __name__ == '__main__':
Expand Down Expand Up @@ -92,8 +91,8 @@ def progress(arg=None):
parser.print_help()
sys.exit(0)

for o in default_values.keys():
globals()[o] = getattr(options, o, default_values[string.lower(o)])
for o in list(default_values.keys()):
globals()[o] = getattr(options, o, default_values[o.lower()])

if options.newphrase:
phrase = getattr(options, 'newphrase')
Expand All @@ -106,7 +105,7 @@ def progress(arg=None):
if ktype == 'dsa' and bits > 1024:
raise SSHException("DSA Keys must be 1024 bits")

if not key_dispatch_table.has_key(ktype):
if ktype not in key_dispatch_table:
raise SSHException("Unknown %s algorithm to generate keys pair" % ktype)

# generating private key
Expand All @@ -121,7 +120,7 @@ def progress(arg=None):
f.write(" %s" % comment)

if options.verbose:
print "done."
print("done.")

hash = hexlify(pub.get_fingerprint())
print "Fingerprint: %d %s %s.pub (%s)" % (bits, ":".join([ hash[i:2+i] for i in range(0, len(hash), 2)]), filename, string.upper(ktype))
hash = u(hexlify(pub.get_fingerprint()))
print("Fingerprint: %d %s %s.pub (%s)" % (bits, ":".join([ hash[i:2+i] for i in range(0, len(hash), 2)]), filename, ktype.upper()))
43 changes: 22 additions & 21 deletions demos/demo_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
import traceback

import paramiko
from paramiko.py3compat import b, u, decodebytes


# setup logging
Expand All @@ -35,17 +36,17 @@
host_key = paramiko.RSAKey(filename='test_rsa.key')
#host_key = paramiko.DSSKey(filename='test_dss.key')

print 'Read key: ' + hexlify(host_key.get_fingerprint())
print('Read key: ' + u(hexlify(host_key.get_fingerprint())))


class Server (paramiko.ServerInterface):
# 'data' is the output of base64.encodestring(str(key))
# (using the "user_rsa_key" files)
data = 'AAAAB3NzaC1yc2EAAAABIwAAAIEAyO4it3fHlmGZWJaGrfeHOVY7RWO3P9M7hp' + \
'fAu7jJ2d7eothvfeuoRFtJwhUmZDluRdFyhFY/hFAh76PJKGAusIqIQKlkJxMC' + \
'KDqIexkgHAfID/6mqvmnSJf0b5W8v5h2pI/stOSwTQ+pxVhwJ9ctYDhRSlF0iT' + \
'UWT10hcuO4Ks8='
good_pub_key = paramiko.RSAKey(data=base64.decodestring(data))
data = (b'AAAAB3NzaC1yc2EAAAABIwAAAIEAyO4it3fHlmGZWJaGrfeHOVY7RWO3P9M7hp'
b'fAu7jJ2d7eothvfeuoRFtJwhUmZDluRdFyhFY/hFAh76PJKGAusIqIQKlkJxMC'
b'KDqIexkgHAfID/6mqvmnSJf0b5W8v5h2pI/stOSwTQ+pxVhwJ9ctYDhRSlF0iT'
b'UWT10hcuO4Ks8=')
good_pub_key = paramiko.RSAKey(data=decodebytes(data))

def __init__(self):
self.event = threading.Event()
Expand All @@ -61,7 +62,7 @@ def check_auth_password(self, username, password):
return paramiko.AUTH_FAILED

def check_auth_publickey(self, username, key):
print 'Auth attempt with key: ' + hexlify(key.get_fingerprint())
print('Auth attempt with key: ' + u(hexlify(key.get_fingerprint())))
if (username == 'robey') and (key == self.good_pub_key):
return paramiko.AUTH_SUCCESSFUL
return paramiko.AUTH_FAILED
Expand All @@ -83,47 +84,47 @@ def check_channel_pty_request(self, channel, term, width, height, pixelwidth,
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
sock.bind(('', 2200))
except Exception, e:
print '*** Bind failed: ' + str(e)
except Exception as e:
print('*** Bind failed: ' + str(e))
traceback.print_exc()
sys.exit(1)

try:
sock.listen(100)
print 'Listening for connection ...'
print('Listening for connection ...')
client, addr = sock.accept()
except Exception, e:
print '*** Listen/accept failed: ' + str(e)
except Exception as e:
print('*** Listen/accept failed: ' + str(e))
traceback.print_exc()
sys.exit(1)

print 'Got a connection!'
print('Got a connection!')

try:
t = paramiko.Transport(client)
try:
t.load_server_moduli()
except:
print '(Failed to load moduli -- gex will be unsupported.)'
print('(Failed to load moduli -- gex will be unsupported.)')
raise
t.add_server_key(host_key)
server = Server()
try:
t.start_server(server=server)
except paramiko.SSHException, x:
print '*** SSH negotiation failed.'
except paramiko.SSHException:
print('*** SSH negotiation failed.')
sys.exit(1)

# wait for auth
chan = t.accept(20)
if chan is None:
print '*** No channel.'
print('*** No channel.')
sys.exit(1)
print 'Authenticated!'
print('Authenticated!')

server.event.wait(10)
if not server.event.isSet():
print '*** Client never asked for a shell.'
print('*** Client never asked for a shell.')
sys.exit(1)

chan.send('\r\n\r\nWelcome to my dorky little BBS!\r\n\r\n')
Expand All @@ -135,8 +136,8 @@ def check_channel_pty_request(self, channel, term, width, height, pixelwidth,
chan.send('\r\nI don\'t like you, ' + username + '.\r\n')
chan.close()

except Exception, e:
print '*** Caught exception: ' + str(e.__class__) + ': ' + str(e)
except Exception as e:
print('*** Caught exception: ' + str(e.__class__) + ': ' + str(e))
traceback.print_exc()
try:
t.close()
Expand Down
Loading

0 comments on commit b2be63e

Please sign in to comment.