Skip to content
Go back

Multi-Protocol Remote Access – SSH, RDP & node app hosting to Your local linux PC and accessible from Anywhere Using Cloudflare Tunnel

Published:

💻 Prerequisites

Before you start, make sure you have:

I am gonna do ssh, access remote desktop (RDP) and access localhost:3000 app on my local pc form anywhere on internet (different network).

what is Cloudflare Tunnel?

Cloudflare Tunnel is a secure way to connect your local server or device to the internet through Cloudflare without exposing your IP address or opening ports. It creates an outbound-only encrypted connection from your server to Cloudflare, which then safely routes internet traffic to your server. This improves security by keeping your server hidden behind a firewall and simplifies remote access without complex network setups.​


Host Setup – The Local Linux Server

The Host Machine is your local PC that you want to access remotely.

Install Cloudflare Tunnel (cloudflared) on you local/host server

The cloudflared daemon is the service that creates the secure tunnel.

  1. Download and Install: Use the appropriate package manager for your Linux distribution (e.g., Debian/Ubuntu): On the Host Machine
    wget https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-linux-amd64.deb
    sudo dpkg -i cloudflared-linux-amd64.deb
  2. Verify Path: Confirm the installation path.
    which cloudflared

Install and Verify Services (SSH & RDP) on you local/host server

We must ensure the services are installed and listening locally before the tunnel can expose them.

OpenSSH Server

  1. Install OpenSSH server:
    sudo apt update
    sudo apt install openssh-server -y
  2. Enable and start the SSH service:
    sudo systemctl enable --now ssh
  3. Verify SSH service status:
    sudo systemctl restart ssh
    # OR
    sudo systemctl restart sshd
    You should see the service as active (running).

XRDP - for remote desktop access

  1. Install xrdp:
    sudo apt update
    sudo apt install xrdp -y
  2. Add xrdp user to ssl-cert group for certificate access:
    sudo adduser xrdp ssl-cert
  3. Enable and start the xrdp service:
    sudo systemctl enable --now xrdp
  4. Verify xrdp service status:
    sudo systemctl status xrdp
    You should see it active (running).

This will set up SSH server for remote terminal access on port 22 and xrdp for remote desktop protocol (RDP) access on port 3389 on your linux machine. Both services will be enabled to start automatically on system boot.|

Run the following command to check the service on specifed port.

sudo ss -tuln | grep -E ':22 |:3389 |:3000 '
sudo ss -tuln | grep 22

Create the Named Tunnel and Configuration**

  1. Authenticate Cloudflared: This opens a browser. Log in to your Cloudflare account, authorize and save cert.pem.
    cloudflared tunnel login
  2. Create a new tunnel. You can name it whatever you like (remote-ssh):
    cloudflared tunnel create remote-ssh

This generates your UUID (tunnel ID) (e.g., bbfb870f-c972-…) and JSON credentials inside /home/USERNAME/.cloudflared/.

  1. Create/Edit config.yml: Define the hostnames and the services they map to.
    nano ~/.cloudflared/config.yml
    Paste your configuration (substituting your UUID):
    #tunnel: YOUR_TUNNEL_ID
    tunnel: bbfb870f-c972-4653-97af-41667bd5cb71  # Your Tunnel UUID
    #credentials-file: /home/YOUR_USERNAME/.cloudflared/YOUR_TUNNEL_ID.json
    credentials-file: /home/janak/.cloudflared/bbfb870f-c972-4653-97af-41667bd5cb71.json # Give path acccording to yours  
    ingress:
      - hostname: ssh.janakkumarshrestha0.com.np # for ssh server
        service: ssh://localhost:22
      - hostname: desktop.janakkumarshrestha0.com.np # For remote desktop
        service: tcp://localhost:3389    
      - hostname: localnode.janakkumarshrestha0.com.np # For node app
        service: http://localhost:3000
      #If you have any other services on local host, go on like this...
      - service: http_status:404

DNS Configuration - Create DNS Records (Cloudflare)

You need to tell Cloudflare to route traffic from your chosen hostname to the tunnel.

cloudflared tunnel route dns remote-ssh ssh.janakkumarshrestha0.com.np # for ssh server
cloudflared tunnel route dns remote-ssh desktop.janakkumarshrestha0.com.np # For remote desktop
cloudflared tunnel route dns remote-ssh localnode.janakkumarshrestha0.com.np # For node app

This command automatically creates the correct CNAME record in your Cloudflare DNS, pointing your all hostname to the tunnel named remote-ssh.

OR

Go to your Cloudflare DNS settings and add the CNAME records.

  1. Add CNAME for SSH:
    • Name: ssh
    • Target: [YOUR-TUNNEL-UUID].cfargotunnel.com
    • Proxy Status: Proxied (Orange Cloud)
  2. Add CNAME for RDP:
    • Name: desktop
    • Target: [YOUR-TUNNEL-UUID].cfargotunnel.com
    • Proxy Status: Proxied (Orange Cloud)
  3. Add CNAME for local node app:
    • Name: localnode
    • Target: [YOUR-TUNNEL-UUID].cfargotunnel.com
    • Proxy Status: Proxied (Orange Cloud)

Run the Tunnel

Start the tunnel service so it can connect to the Cloudflare network and begin listening for traffic:

cloudflared tunnel run remote-ssh # Replace with you tunnel name

After you run the cloudflared tunnel the you can immedaiately

Access your node app running on 3000 port is accessible form the internet / any networks

localnode.janakkumarshrestha0.com.np

Client Configuration the SSH Client (Client Machine on different network)

On the PC you’re connecting from (your remote client or there pc on different networks), you need to install cloudflared and configure your SSH client to use it as a proxy.

sudo apt update
wget https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-linux-amd64.deb
sudo dpkg -i cloudflared-linux-amd64.deb
which cloudflared

Edit your SSH configuration file (on Linux/macOS, or a similar configuration on Windows tools like PuTTY).

  1. Edit ~/.ssh/config:

    nano ~/.ssh/config
  2. Add SSH Configuration:

    Host remote-ssh-janak # Give host name you like
      Hostname ssh.janakkumarshrestha0.com.np   # Replace with you actual host name.
      # The key line that uses cloudflared to proxy the connection
      ProxyCommand /usr/local/bin/cloudflared access ssh --hostname %h
      User janak  # Replace with the username on the local server / host machine.
    
      # (Optional) Use a specific port if your server isn't on default port, otherwise, this line isn't necessary
      # Port 22
    • The ProxyCommand tells the SSH client to route the connection through cloudflared, which handles the tunnel authentication. Replace or match the ouptput form which cloudflared command in /usr/local/bin/cloudflared path. Note: Make sure the path to cloudflared (/usr/local/bin/cloudflared) is correct for your client machine’s installation. Check using this command which cloudflared and match.
  3. Connect via SSH

You can now connect to your local PC from anywhere on the internet using the simplified SSH command from the client machine:

ssh remote-ssh-janak
# or
ssh -vvv remote-ssh-janak # for more details

SSH connect directly using a single command without having to rely on the configuration block in your ~/.ssh/config file.

To connect directly while still using the Cloudflare Tunnel as a proxy, you need to embed the ProxyCommand directly into the ssh command using the -o (Option) flag.

Here is the format you would use:

ssh [email protected] \
    -o ProxyCommand="/usr/local/bin/cloudflared access ssh --hostname %h"
Part of CommandPurpose
ssh janak@...Specifies the user (janak) and the destination host (ssh.janakkumarshrestha0.com.np).
-o ProxyCommand="..."The -o flag overrides or sets an option usually found in ~/.ssh/config.
"/usr/local/bin/cloudflared access ssh --hostname %h"This is the command that initiates the tunnel connection.
%hThis is a placeholder that is replaced by the actual hostname (ssh.janakkumarshrestha0.com.np) at runtime.

Since you have set up Cloudflare Access and disabled password login, the connection sequence will be:

  1. The command runs the ProxyCommand.
  2. Your browser opens to verify your identity (Cloudflare Access).
  3. Once verified, the SSH client uses your private key (~/.ssh/id_ed25519 or similar) to complete the login without asking for a password.

If you want to make this long command easier to type repeatedly without using your ~/.ssh/config file, you could create a shell alias in your shell startup file (~/.bashrc or ~/.zshrc):

# Add this line to ~/.bashrc or ~/.zshrc
alias remote-ssh='ssh [email protected] -o ProxyCommand="/usr/local/bin/cloudflared access ssh --hostname %h"'

After reloading your shell (source ~/.bashrc), you could simply type:

remote-ssh

Stronger Authentication (SSH Keys)

Relying on a password is less secure than using SSH keys. Since your SSH server is now running, you should configure key-based authentication.

On the Client Machine (Your Laptop):

  1. Generate a new SSH key pair (if you don’t already have one):

    ssh-keygen -t ed25519
  2. Copy the public key to your remote server:

    ssh-copy-id remote-ssh-janak

    This command will prompt for your server password one last time and then install your public key (~/.ssh/id_ed25519.pub) into the ~/.ssh/authorized_keys file on the remote server.

After this, when you run ssh remote-ssh-janak, you will no longer be asked for a password, as your secure SSH key will handle the final authentication step automatically.


Disabling Password-Based SSH Login

You need to edit the configuration file for the SSH server (sshd) on your host machine.

sudo nano /etc/ssh/sshd_config

Scroll through the file (or use Ctrl+W to search) and ensure the following two directives are set exactly as shown below. Make sure to uncomment the lines (remove the # symbol) if they are commented out.

DirectiveValuePurpose
PasswordAuthenticationnoThis is the main directive that blocks all password logins.
PubkeyAuthenticationyesThis ensures SSH key-based login remains active (it’s usually yes by default).
sudo systemctl restart ssh
# OR
sudo systemctl restart sshd
# Verify password authentication is disabled
grep -E 'PasswordAuthentication|PubkeyAuthentication' /etc/ssh/sshd_config

Prepare your host Deskop for remote desktop (RDP)

This step fixes the common issue where RDP connects but immediately closes or shows a blank screen on KDE/Plasma environments.

  1. Modify the xRDP Startup Script: This tells xRDP exactly which desktop environment to launch.

    sudo nano /etc/xrdp/startwm.sh
  2. Edit the Script: Scroll to the bottom and comment out the two default startup lines, then add the startplasma-x11 command:

    # test -x /etc/X11/Xsession && exec /etc/X11/Xsession
    # exec /bin/sh /etc/X11/Xsession
    
    # Add these lines for KDE
    startplasma-x11
  3. Create .xinitrc File: This ensures the session environment is initialized correctly for your user.

    nano ~/.xinitrc

    Paste:

    #!/bin/sh
    exec startplasma-x11
  4. Restart xRDP Service: Apply the session changes.

    sudo systemctl restart xrdp
  5. Reconnect

    1. Ensure the cloudflared access tcp proxy is running on your client.
    2. Connect your RDP client to rdp://[email protected]:33389.
    3. Enter your username and password.

    This combination of the explicit startplasma-x11 command in both startwm.sh and the newly created ~/.xinitrc is the most reliable way to force xrdp to launch a functional KDE session.


Run the Cloudflared Client in TCP Mode (Client Machine)

You need to run a separate cloudflared command on the client machine that listens on a local port (e.g., 33389), performs the Cloudflare Access handshake, and forwards all traffic to your tunnel hostname.

  1. Open a New Terminal on your Client Machine.

  2. Run the RDP Proxy Command: On the Client Machine (Keep this terminal open)

    /usr/local/bin/cloudflared access tcp --hostname desktop.janakkumarshrestha0.com.np --url 127.0.0.1:33389
    • access tcp: Tells cloudflared to act as a TCP proxy client.
    • --hostname: Specifies the remote hostname to connect to (your tunnel endpoint).
    • --url 127.0.0.1:33389: Tells cloudflared to listen on your local machine at port 33389 and forward any traffic it receives.

Connect the RDP Client

Once the browser authentication is complete, your local proxy is running!

  1. Open your RDP Client (e.g., Remmina and KRDC).
  2. Connect to the local proxy address:
    • Host/IP: 127.0.0.1 (or localhost)
    • Port: 33389 (The local port specified in the cloudflared command)

Your RDP client connects locally to 33389, cloudflared forwards the traffic securely through the tunnel, and you should see the RDP login screen for your host machine.


If you are Windows OS user:


💻 Phase 1: Windows Client Setup

1. Install Cloudflared on Windows

You need the cloudflared client on your Windows machine to handle the secure tunneling and Cloudflare Access authentication.

  1. Download: Download the latest cloudflared executable file from Cloudflare Download page
  2. Rename & Place: Rename the downloaded file to just cloudflared.exe and place it in a simple location, like C:\Cloudflared\.
  3. Add to Path (Optional but Recommended): Add C:\Cloudflared to your Windows System Environment Variables PATH so you can run the command from any terminal (PowerShell or Command Prompt).

🔒 Phase 2: SSH Access (Using PowerShell/CMD)

For SSH, you’ll use the built-in OpenSSH Client in Windows (or PuTTY/Git Bash).

2. Run the SSH Command

Since Windows SSH clients don’t use the simple ~/.ssh/config file in the same way, you must include the ProxyCommand directly in your terminal, or use a tool like Git Bash which supports the Linux-style configuration.

In PowerShell or Command Prompt: Run this command to SSH:

ssh janak@ssh.janakkumarshrestha0.com.np -o ProxyCommand="C:\Cloudflared\cloudflared.exe access ssh --hostname %h"

Connection Flow:

  1. The command runs, executing the ProxyCommand.
  2. A browser window opens, prompting you to log in for Cloudflare Access authentication.
  3. Once authenticated, the terminal prompts you to accept the host key, and then logs you in using your SSH Key (if previously set up).

🖥️ Phase 3: RDP Access (Using Remote Desktop Client)

For RDP, you must use the same local proxy method used on your Linux client, as the RDP client cannot run the authentication command itself.

3. Start the Cloudflared RDP Proxy

You need to run the cloudflared command in a separate, dedicated terminal window on your Windows machine.

  1. Open PowerShell/Command Prompt (as a normal user).

  2. Run the RDP Proxy Command: Keep this terminal window open for the entire session.

    C:\Cloudflared\cloudflared.exe access tcp --hostname desktop.janakkumarshrestha0.com.np --url 127.0.0.1:33389

    This command will prompt for Cloudflare Access authentication in a browser.

4. Connect with Microsoft Remote Desktop

  1. Open the Microsoft Remote Desktop Connection (MSTSC) client (or another RDP client like Remmina).
  2. Connect to the local proxy address:
    • Computer/Host: 127.0.0.1:33389
  3. Once the connection establishes, the RDP client will show the login prompt for your remote Linux host machine.

If you want to Make the Tunnel Permanent/auto start on boot (Host Machine)

Manual Systemd Service Creation

We will create a service file that explicitly tells the operating system to run cloudflared using your user’s configuration file.

1. Stop the Foreground Tunnel (If Running)

Make sure you’ve pressed Ctrl + C in the terminal where the tunnel was running.

2. Create the Service File

You need to create a new file for the service definition.

On the Host Machine:

sudo nano /etc/systemd/system/cloudflared-remote.service

3. Paste the Service Configuration

Paste the following configuration into the file. This file is configured specifically for your setup:

[Unit]
Description=Cloudflare Tunnel Remote SSH Service
After=network.target

[Service]
# Set the user and group to run the tunnel as
User=janak #Your hostmachine's username
# The main executable. We use 'tunnel run' with the name of your tunnel.
ExecStart=/usr/local/bin/cloudflared tunnel run remote-ssh
# Ensure the service restarts if it fails
Restart=always
# Point the service to your existing config file
Environment="CLOUDFLARED_OPTS=--config /home/janak/.cloudflared/config.yml"
# Give up waiting if start takes too long
TimeoutStopSec=5

[Install]
WantedBy=multi-user.target

Note: Make sure to verify the username janak is correct.

Save the file and exit the editor.

4. Manage the cloudflared-remote Service

Now, tell systemd about the new service file, enable it for boot, and start it.

On the Host Machine:

# Reload the systemd manager configuration
sudo systemctl daemon-reload

# Enable the service to start automatically on boot
sudo systemctl enable cloudflared-remote.service

# Start the tunnel service
sudo systemctl start cloudflared-remote.service

# Stop the tunnel service
sudo systemctl stop cloudflared-remote.service

# Disable this service on startup
sudo systemctl disable cloudflared-remote.service

# Check the status
sudo systemctl status cloudflared-remote.service

You should see “Active: active (running)”. You can now close your host terminal, and the tunnel will remain active.

Apply Zero Trust Access Policies

You must secure both new hostnames in your Cloudflare Zero Trust Dashboard $\to$ Access $\to$ Applications, creating a separate Self-hosted Application for:

For both, set the Access Policy to Allow only your verified Email Address.



Suggest Changes

Next Post
Install XFCE, LXQt, MATE, Cinnamon, Enlightenment, Gnome, KDE Plasma Desktop Environment with XRDP for Remote Desltop Access on a single Ubuntu Server.