Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to open an SSH tunnel using python?

I am trying to connect to a remote mysql database using django.
The documentation specifies that it is required to open an SSH tunnel first to connect to the database.
Is there a python library that can open an SSH tunnel whenever certain settings are set?

like image 628
the_drow Avatar asked Dec 06 '10 08:12

the_drow


People also ask

Can you use SSH in Python?

SSH is widely used by network administrators for managing systems and applications remotely, allowing them to log in to another computer over a network, execute commands and move files from one computer to another. In python SSH is implemented by using the python library called fabric.

How do I tunnel through SSH?

Set up SSH Tunneling in WindowsLaunch Putty and enter the SSH server IP Address in the Host name (or IP address) field. Under the Connection menu, expand SSH and select Tunnels . Check the Local radio button to setup local, Remote for remote, and Dynamic for dynamic port forwarding.

What is Paramiko Python?

Paramiko is a Python library that makes a connection with a remote device through SSh. Paramiko is using SSH2 as a replacement for SSL to make a secure connection between two devices. It also supports the SFTP client and server model.


3 Answers

You could try paramiko's forward functionality. For a paramiko overview, see here.

like image 58
Vinay Sajip Avatar answered Oct 04 '22 11:10

Vinay Sajip


Try use sshtunnel package.

This is simple:

pip install sshtunnel
python -m sshtunnel -U vagrant -P vagrant -L :3306 -R 127.0.0.1:3306 -p 2222 localhost

Disclosure: I'm the author and maintainer of this package.

like image 20
pahaz Avatar answered Oct 04 '22 09:10

pahaz


Here is a code snippet for Python3 (but you should be able to retrofit it into Python2 without difficulty). It runs an SSH tunnel in a separate thread; then the main thread does something to get network traffic over the SSH tunnel.

In this example, the ssh tunnel forwards local port 2222 to port 80 on localhost. The main activity consists of running

curl http://localhost:2222

ie., fetching a webpage but from port 2222.

The class SshTunnel is initialized with 4 parameters, the local and remote port, the remote user, and the remote host. All it does, is start SSH in the following way:

ssh -N -L localport:remotehost:remoteport remoteuser@remotehost

In order to make this work, you'll need a password-less login for remoteuser@remotehost (via ~/.ssh/id_rsa.pub that's known on the remote server). The thus running ssh tunnel is on one thread; the main task must be in another one. The ssh tunnel thread is marked as daemon so that it will automatically stop once the main activity terminates.

I didn't put in a full MySQL connectivity example because it should be self-explanatory. Once SshTunnel sets up a local TCP port, you can connect to it - be it via your MySQL client, curl, or whatever.

import subprocess
import time
import threading

class SshTunnel(threading.Thread):
    def __init__(self, localport, remoteport, remoteuser, remotehost):
        threading.Thread.__init__(self)
        self.localport = localport      # Local port to listen to
        self.remoteport = remoteport    # Remote port on remotehost
        self.remoteuser = remoteuser    # Remote user on remotehost
        self.remotehost = remotehost    # What host do we send traffic to
        self.daemon = True              # So that thread will exit when
                                        # main non-daemon thread finishes

    def run(self):
        if subprocess.call([
            'ssh', '-N',
                   '-L', str(self.localport) + ':' + self.remotehost + ':' + str(self.remoteport),
                   self.remoteuser + '@' + self.remotehost ]):
            raise Exception ('ssh tunnel setup failed')


if __name__ == '__main__':
    tunnel = SshTunnel(2222, 80, 'karel', 'localhost')
    tunnel.start()
    time.sleep(1)
    subprocess.call(['curl', 'http://localhost:2222'])
like image 44
Karel Kubat Avatar answered Oct 04 '22 11:10

Karel Kubat