Pfsense haproxy to ssh host

I’m doing something here that i thought would be easy, but i think i’m missing some bit of information that is making this fail.

we host a few websites on azure. I’m dns-ing these hostnames so that it goes to our pfsense box, looks up the destination with haproxy, then does a back end connect to that website from our pfsense box.

so: [internet user] → [our pfsense box:443] ->[azure site:443]

we have some need to do sftp to these sites for file transfer.
So I made a frontend listening on port 22, determine the host to which we wish to sftp using a hostname matches, and directing them to a backend.

the backend is defined with the single host:
mode: active
name: the site name
forward-to: address+port
address: the azure public ip address
port: 22
encrypt(ssl): no (also tried yes)
SSL checks: no

connecting to the pfsense with a command:
sftp user@sitename
comes back with:
kex_exchange_identification: Connection close by remote host

The haproxy specific things i’ve found on the web seem to deal with setting up some proxy variable in the call that has information and sni variable.

I realize i could do a port XXXX on the pfsense port forwards to port 22 on the site, and set up a different XXXX for each site, but we don’t want our users to have to do anything special, just normal sftp to a user@sitename.

ssh access is not enabled on pfsense, and there is a firewall rule that passes on port 22.
sftp to a user on our lan can access the site by username@directpublicIP

Clearly I’m missing something basic.

SSH is not a protocol designed to go over HAProxy

1 Like

Thanks @LTS_Tom,
If you say it can’t be done, then I’m confident that pursuing this line of thought is pointless.

Any clever suggestions to achieve this aside from just pointing them to the public ip of the host? (which isn’t very clever)

Maybe hosting a single sftp box on a DMZed subnet behind pfsense and forcing all file transfers there?

SSH connections are designed to be direct connections.

As Tom said, HAProxy is not capable of proxying SSH. HTTP(S) and SSH are two different protocols. HTTP has this great feature called Server Name Indication (SNI) which allows multiple sites distinguished by their domain name to be hosted on the same server (meaning same IP address). Or in the case of reverse proxying, they aren’t exactly hosted on that IP address, but to the client it looks that way.

To my knowledge, there is no equivalent mechanism for SSH. A possible solution might be to use something like SSHFS. Then you can have one central server that “mounts” all the individual Azure servers’ webroot directory. Might be a pain to setup permissions correctly though.

Hi @LTS_Tom !

I landed here while I was searching how to use haproxy on pfsense to forward ssh traffic and since I found a way to achieve that, I thought I would share that here ( maybe you will find this interesting and add it to a one of you tutorial ).

My use case:
On my private network, I want to be able to reach my gitea server ( git self hosted server) with ssh to do git push/pull/etc…
I already have Haproxy setup with let’s encrypt ( pretty much what you demonstrate in your tutorial).
The web server of gitea is is defined with my HTTP frontend in Haproxy.

First, I create a backend:

  1. in the server list I give the network alias ( defined in DNS resolver) for the server IP that host gitea
    2.I give the port gitea is listening to for ssh traffic
  2. (optionnal) I use basic health check

Then , I create a new frontend for TCP traffic:

1.this frontend listen to my VLAN50
2.it listen to port 22 ( I changed the pfsense ssh port in system => Advanced => ssh port to some other value than 22)
3.the frontend is defined as tcp
4 & 5.the acl rule gitea-ssh only allow ip from the VLAN50 subnet ( this is an alias , you can limit to only 1 IP if needed
6 & 7. using the acl gitea-ssh , I connect with the backend gitea-ssh