I'm trying to setup an ssh over https connection using nginx. I haven't found any working examples, so any help would be appreciated!

~$ cat .ssh/config
Host example.net
  Hostname example.net
  ProtocolKeepAlives 30
  DynamicForward 8118
  ProxyCommand /usr/bin/proxytunnel -p ssh.example.net:443 -d localhost:22 -E -v -H "User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Win32)"

~$ ssh user@example.net
Local proxy ssh.example.net resolves to 115.xxx.xxx.xxx
Connected to ssh.example.net:443 (local proxy)

Tunneling to localhost:22 (destination)
Communication with local proxy:
 -> CONNECT localhost:22 HTTP/1.0
 -> Proxy-Connection: Keep-Alive
 -> User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Win32)
 <- <html>
 <- <head><title>400 Bad Request</title></head>
 <- <body bgcolor="white">
 <- <center><h1>400 Bad Request</h1></center>
 <- <hr><center>nginx/1.0.5</center>
 <- </body>
 <- </html>
analyze_HTTP: readline failed: Connection closed by remote host
ssh_exchange_identification: Connection closed by remote host

Nginx config on the server;

~$ cat /etc/nginx/sites-enabled/ssh 
upstream tunnel {
    server localhost:22;
server {
    listen 443;
    server_name ssh.example.net;

    location / {
            proxy_pass http://tunnel;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_redirect off;

    ssl on;
    ssl_certificate /etc/ssl/certs/server.cer;
    ssl_certificate_key /etc/ssl/private/server.key;

~$ tail /var/log/nginx/access.log
203.xxx.xxx.xxx - - [08/Feb/2012:15:17:39 +1100] "CONNECT localhost:22 HTTP/1.0" 400 173 "-" "-"

Nginx doesn't support forward proxy requests (the HTTP CONNECT method), which is why you get the "Bad request" response from Nginx. Proxytunnel is able to connect to Nginx, but from there it stops. AFAIF the Nginx authors have no plans to support forward proxy requests, as they like to be specialized in serving HTTP really well. Apache has modules for everything else, giving you the freedom to use those exotic features.

You can look at sslh, which can multiplex the incoming traffic at port 443 to either Nginx (listening at, SSH or OpenVPN. Make sure you let sslh listen at the public IP address, and not on as that overlaps with where Nginx is listening.

Another options is using Squid, but I have no experience there.


This is old question, but still actual :-)

As others mentioned this setup is hardly to be available due to lacking HTTP CONNECT method available in Nginx.

NOTE: Apache web server supports this setup.

But, for Nginx there is solution without sslh I think in form of custom Nginx module which implements HTTP CONNECT: https://github.com/chobits/ngx_http_proxy_connect_module

By using this you should be able to use in your ssh config only ProxyCommand properly.


I've never seen this kind of setup and I doubt that it can work, because nginx expects to be able to treat the incoming connection as HTTP and talk to the upstream with HTTP. Why do you want to proxy through nginx?

  • 3
    It should be possible - proxytunnel is used to tunnel SSH sessions through HTTP(S) proxies, Here is the setup to configure this using apache
    – Thermionix
    Mar 26 '12 at 5:53
  • Apache seems to be operating as an actual HTTP proxy there, which I don't think that nginx supports (only reverse proxying).
    – mgorven
    Mar 26 '12 at 17:09

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.