Skip to main content
Access Rexec terminals with your favorite SSH client — perfect for tmux, mosh, or terminal purists.

What is SSH Gateway?

Rexec provides an SSH gateway that lets you connect to your cloud terminals and agent servers using standard SSH. No need to use the web interface — just ssh like you normally would.

Key Benefits

Native Tools

Use your preferred SSH client, tmux, mosh, or terminal emulator.

Key-Based Auth

Authenticate with your SSH public keys, no passwords needed.

Same Terminals

Access the exact same containers as the web UI.

Full Compatibility

Works with all SSH features: port forwarding, SCP, rsync, etc.

How It Works

  1. Add your SSH public key to Rexec dashboard
  2. Connect via SSH gateway at ssh.rexec.io
  3. Select terminal from interactive menu or direct connection
  4. Use like any SSH server — fully native experience
The SSH gateway is a proxy. Your SSH keys authenticate you, then you’re connected to your container.

Adding SSH Keys

Generate SSH Key (if needed)

# Generate ED25519 key (recommended)
ssh-keygen -t ed25519 -C "[email protected]"

# Or RSA 4096-bit
ssh-keygen -t rsa -b 4096 -C "[email protected]"

# Keys saved to:
~/.ssh/id_ed25519      # Private key (keep secret!)
~/.ssh/id_ed25519.pub  # Public key (safe to share)

Add Key to Rexec

Via Dashboard

  1. Go to Settings → SSH Keys
  2. Click “Add SSH Key”
  3. Paste your public key:
    # Copy public key to clipboard
    cat ~/.ssh/id_ed25519.pub | pbcopy  # macOS
    cat ~/.ssh/id_ed25519.pub | xclip   # Linux
    
  4. Give it a name: laptop-work, desktop-home, etc.
  5. Click Save

Via API

curl -X POST https://api.rexec.io/api/ssh/keys \
  -H "Authorization: Bearer $REXEC_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "laptop-work",
    "public_key": "ssh-ed25519 AAAAC3Nza... user@host"
  }'
Only add public keys (.pub files). Never share or upload private keys!

Supported Key Types

TypeRecommendedNotes
ED25519✅ YesModern, secure, fast
RSA 4096✅ YesWidely compatible
RSA 2048⚠️ OKLess secure, but works
ECDSA⚠️ OKCompatible
DSA❌ NoDeprecated, insecure

Connecting via SSH

Interactive Menu

Connect and choose a terminal:
ssh ssh.rexec.io

# You'll see:
Welcome to Rexec SSH Gateway!

Your terminals:
  1) ubuntu-dev-01        [running]   ☁️  Cloud
  2) production-web       [running]   🖥️  Agent
  3) node-testing         [stopped]   ☁️  Cloud
  4) alpine-minimal       [running]   ☁️  Cloud

Enter number (1-4) or 'q' to quit: 1

Connecting to ubuntu-dev-01...
user@ubuntu-dev-01:~$

Direct Connection

Connect to specific terminal by name:
# Format: [email protected]
ssh [email protected]

# Or use container ID
ssh [email protected]
Your Rexec username is required as prefix. Find it in Settings → Profile.

SSH Config

Simplify connections with ~/.ssh/config:
# ~/.ssh/config
Host rexec-*
  Hostname ssh.rexec.io
  User alice  # Your Rexec username
  IdentityFile ~/.ssh/id_ed25519
  ServerAliveInterval 60
  ServerAliveCountMax 3

# Specific terminals
Host ubuntu-dev
  Hostname ssh.rexec.io
  User alice.ubuntu-dev-01

Host prod-web
  Hostname ssh.rexec.io
  User alice.production-web
Now just:
ssh ubuntu-dev
ssh prod-web

SSH Features Support

Port Forwarding

# Forward remote port 3000 to local 8080
ssh -L 8080:localhost:3000 [email protected]

# Now access http://localhost:8080 in your browser
# Traffic goes to container's port 3000

File Transfer

# Upload file to container
scp app.py [email protected]:/home/user/

# Download from container
scp [email protected]:/var/log/app.log ./

# Recursive directory copy
scp -r ./src [email protected]:/home/user/project/

Remote Commands

# Execute single command
ssh [email protected] 'ls -la'

# Run script
ssh [email protected] 'bash -s' < local-script.sh

# Pipe remote output
ssh [email protected] 'docker logs api' | grep ERROR

# Chain commands
ssh [email protected] 'cd /var/log && tail -f app.log'

Tmux/Screen Support

# Start tmux on container
ssh [email protected]
user@container:~$ tmux new -s work

# Detach and reconnect later
<Ctrl-B> D

# Reconnect
ssh [email protected]
user@container:~$ tmux attach -t work
Tmux sessions persist even if you disconnect. Perfect for long-running tasks.

Mosh Support

Mosh (mobile shell) support coming soon. Currently, standard SSH only.

SSH Gateway Configuration

Environment Variables

Configure SSH gateway in .env:
# SSH Gateway
SSH_GATEWAY_ENABLED=true
SSH_GATEWAY_HOST=0.0.0.0
SSH_GATEWAY_PORT=2222

# Host key (generated automatically if not set)
SSH_HOST_KEY_PATH=/var/lib/rexec/ssh_host_key

# Banner
SSH_BANNER="Welcome to Rexec SSH Gateway!"

# Idle timeout
SSH_IDLE_TIMEOUT=30m

Security Settings

# Allowed authentication methods
SSH_AUTH_METHODS=publickey  # Only keys, no passwords

# Require MFA for SSH access (Pro+)
SSH_REQUIRE_MFA=true

# Max concurrent connections per user
SSH_MAX_CONNECTIONS=10

# Rate limiting
SSH_RATE_LIMIT=10/minute

Managing SSH Keys

List Keys

# Via dashboard
Settings SSH Keys

# Via API
curl https://api.rexec.io/api/ssh/keys \
  -H "Authorization: Bearer $REXEC_TOKEN"

Rotate Keys

  1. Generate new key: ssh-keygen -t ed25519
  2. Add new key to Rexec
  3. Test new key: ssh -i ~/.ssh/id_ed25519_new ssh.rexec.io
  4. Delete old key once confirmed working

Key Limits

TierSSH Keys per User
FreeUp to 5
ProUp to 10
EnterpriseUnlimited

Advanced: Jump Hosts

Use Rexec as SSH jump host:
# ~/.ssh/config
Host internal-server
  Hostname 10.0.1.100
  User root
  ProxyJump [email protected]

# Connect through Rexec container to internal server
ssh internal-server
Useful for accessing internal networks through a Rexec agent.

Troubleshooting

Causes:
  • SSH key not added to Rexec
  • Using wrong private key
  • Key permissions too open (should be 0600)
Fix:
# Check key is added
curl https://api.rexec.io/api/ssh/keys \
  -H "Authorization: Bearer $REXEC_TOKEN"

# Fix permissions
chmod 600 ~/.ssh/id_ed25519
chmod 644 ~/.ssh/id_ed25519.pub

# Test specific key
ssh -i ~/.ssh/id_ed25519 -v ssh.rexec.io
Causes:
  • Firewall blocking port 2222
  • SSH gateway offline
  • Network issues
Fix:
# Test connectivity
nc -zv ssh.rexec.io 2222

# Check gateway status
curl https://api.rexec.io/health

# Try with verbose output
ssh -vvv ssh.rexec.io
Causes:
  • Terminal stopped or deleted
  • Wrong terminal name
  • Container not yet started
Fix:
# List available terminals
curl https://api.rexec.io/api/containers \
  -H "Authorization: Bearer $REXEC_TOKEN"

# Start terminal via dashboard first
# Then retry SSH connection

Security Best Practices

Key Management

  • Use ED25519 or RSA 4096 keys
  • Passphrase-protect private keys
  • Rotate keys every 6-12 months
  • Delete unused keys promptly

Access Control

  • Enable MFA for SSH access (Pro+)
  • Use unique keys per device
  • Audit SSH access logs regularly
  • Restrict which terminals allow SSH

Network Security

  • Use port forwarding instead of exposing ports
  • Enable firewall rules on containers
  • Avoid root login (Rexec uses ‘user’ by default)

Performance Tips

Compression

Enable SSH compression for slow connections:
ssh -C [email protected]

# Or in ~/.ssh/config:
Host rexec-*
  Compression yes

Connection Multiplexing

Reuse connections for faster subsequent SSH commands:
# ~/.ssh/config
Host rexec-*
  ControlMaster auto
  ControlPath ~/.ssh/control-%r@%h:%p
  ControlPersist 10m

# First connection establishes master
ssh [email protected]

# Subsequent connections are instant (reuse master)
scp file.txt [email protected]:/tmp/
ssh [email protected] 'ls -la'

Keep-Alive

Prevent connection drops:
# ~/.ssh/config
Host rexec-*
  ServerAliveInterval 60
  ServerAliveCountMax 3
  TCPKeepAlive yes

Integration with CI/CD

GitHub Actions

name: Deploy

on: [push]

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      
      - name: Setup SSH
        run: |
          mkdir -p ~/.ssh
          echo "${{ secrets.REXEC_SSH_PRIVATE_KEY }}" > ~/.ssh/id_ed25519
          chmod 600 ~/.ssh/id_ed25519
      
      - name: Deploy to container
        run: |
          rsync -avz --delete \
            -e "ssh -o StrictHostKeyChecking=no" \
            ./ [email protected]:/var/www/app/
          
          ssh [email protected] 'systemctl restart app'

GitLab CI

deploy:
  stage: deploy
  before_script:
    - eval $(ssh-agent -s)
    - echo "$REXEC_SSH_PRIVATE_KEY" | ssh-add -
    - mkdir -p ~/.ssh
    - echo "StrictHostKeyChecking no" >> ~/.ssh/config
  script:
    - rsync -avz ./ [email protected]:/var/www/app/
    - ssh [email protected] 'pm2 restart app'

API Reference

Add SSH Key

POST /api/ssh/keys
Content-Type: application/json
Authorization: Bearer $REXEC_TOKEN

{
  "name": "laptop-work",
  "public_key": "ssh-ed25519 AAAAC3Nza... user@host"
}

List SSH Keys

GET /api/ssh/keys
Authorization: Bearer $REXEC_TOKEN

Delete SSH Key

DELETE /api/ssh/keys/{key_id}
Authorization: Bearer $REXEC_TOKEN
See API Reference for complete documentation.

Cloud Terminals

SSH into cloud terminals

BYOS Agent

SSH into your own servers

Session Recording

Record SSH sessions

Collaboration

Share terminals accessed via SSH

Build docs developers (and LLMs) love