> ## Documentation Index
> Fetch the complete documentation index at: https://www.integrate.io/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# SSH tunnel setup for ELT & CDC

> Set up an SSH tunnel in Integrate.io ELT & CDC for secure database connections over untrusted networks. Encrypt data transfers through SSH.

## Creating Integrate.io ELT Connection

<Steps>
  <Step>
    On **Connection options** of Source or Destination creation, select **Connect via secure tunnel**. Select **Create a new tunnel**

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-26.webp?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=098087def834deb7cbca777caaeeadf2" alt="Connection options with Connect via secure tunnel and Create a new tunnel selected" width="1200" height="570" data-path="images/cdc/security/image-26.webp" />
    </Frame>
  </Step>

  <Step>
    Supply the region, tunnel name and the SSH tunnel details. Click **Create SSH Tunnel** to create the tunnel

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-20.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=5742635f11e22037d82736c105dd642f" alt="SSH tunnel creation form with region, name, and connection details" width="1200" height="446" data-path="images/cdc/security/image-20.png" />
    </Frame>
  </Step>

  <Step>
    Copy the **SSH Public Key** by clicking the Copy button and prepare your tunnel host for access.

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-21.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=3d2fb705eb8eebf96a7a962d51bb424d" alt="SSH Public Key displayed with a copy button" width="1200" height="171" data-path="images/cdc/security/image-21.png" />
    </Frame>
  </Step>

  <Step>
    Once your tunnel host is prepared, click **Test Tunnel Connection** to test the connection. If connection is successful, you should see the **Active** check.

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-22.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=9db546625038282e465591ae50353148" alt="Successful tunnel connection test showing Active status" width="1200" height="167" data-path="images/cdc/security/image-22.png" />
    </Frame>
  </Step>
</Steps>

### For Linux - Preparing the tunnel host

You will need to prepare your host (either bastion host or tunnel server) by creating an integrate.io ELT user. Here’s how:

<Steps>
  <Step title="Create group integrate.io ELT">
    `sudo groupadd integrate-io`
  </Step>

  <Step title="Create user integrate.io ELT and its home directory">
    `sudo useradd -m -g integrate-io integrate-io`
  </Step>

  <Step title="Switch to the integrate.io ELT user">
    `sudo su - integrate-io`
  </Step>

  <Step title="Create the .ssh directory and change permission">
    `mkdir ~/.ssh && chmod 700 ~/.ssh`
  </Step>

  <Step title="Create the authorization\_keys file and change permission">
    `touch ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys`
  </Step>

  <Step title="Add the previously copied public key to the authorized\_keys">
    `echo '<SSH public key>' >> ~/.ssh/authorized_keys`
  </Step>

  <Step>
    Allow access to your server's host and port from [Integrate.io ELT's IP addresses](/cdc/ip-list)
    `sudo ufw allow from <Integrate.io ELT's IP addresses> to any port 22 proto tcp`
  </Step>
</Steps>

### For Windows - Preparing the tunnel host

We will use the `Administrator` user for this guide. If you are using a different user, please make sure that it belongs to the `Adminstrator` group.

Run the following commands in Powershell as Administrator.

<Steps>
  <Step title="Check if SSH features are enabled">
    ```bash theme={null}
    Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*'
    ```

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-23.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=e55b53b8016764684426a46f965c4414" alt="PowerShell output showing OpenSSH capability status" width="1882" height="294" data-path="images/cdc/security/image-23.png" />
    </Frame>
  </Step>

  <Step title="Enable SSH features if they are not installed">
    ```bash theme={null}
    # Install the OpenSSH Client
    Add-WindowsCapability -Online -Name OpenSSH.Client~~~~0.0.1.0
    # Install the OpenSSH Server
    Add-WindowsCapability -Online -Name OpenSSH.Server~~~~0.0.1.0
    ```

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-24.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=35eef779d08779533e129e7dfd15a9f6" alt="PowerShell output after installing OpenSSH Client and Server" width="1919" height="530" data-path="images/cdc/security/image-24.png" />
    </Frame>
  </Step>

  <Step title="Enable public key authentication in SSH server configuration file">
    ```bash theme={null}
    Add-Content -Force -Path $env:ProgramData\ssh\sshd_config -Value "\`nPubkeyAuthentication yes"
    ```

    You can also open the file using notepad and look for `PubkeyAuthentication`

    ```bash theme={null}
    notepad.exe  $env:ProgramData\ssh\sshd_config
    ```
  </Step>

  <Step title="Start the SSH server service">
    ```bash theme={null}
    # Start the sshd service
    Start-Service sshd
    # Make the SSH service automatically start on startup
    Set-Service -Name sshd -StartupType 'Automatic'
    ```
  </Step>

  <Step title="Create a firewall rule for the SSH port">
    ```bash theme={null}
    if (!(Get-NetFirewallRule -Name "Allow SSH Port (22)" -ErrorAction SilentlyContinue | Select-Object Name, Enabled)) {
    Write-Output "Firewall Rule 'Allow SSH Port (22)' does not exist, creating it..."
    New-NetFirewallRule -Name 'Allow SSH Port (22)' -DisplayName 'OpenSSH Server (sshd)' -Enabled True -Direction Inbound -Protocol TCP -Action Allow -LocalPort 22
    } else {
        Write-Output "Firewall rule 'Allow SSH Port (22)' has been created and exists."
    }
    ```

    <Frame>
      <img src="https://mintcdn.com/integrateio/MGWLTifrhXADDsEf/images/cdc/security/image-25.png?fit=max&auto=format&n=MGWLTifrhXADDsEf&q=85&s=967dc552c0a9e8ec81afd96c0ccc5c47" alt="PowerShell output confirming SSH firewall rule creation" width="1452" height="782" data-path="images/cdc/security/image-25.png" />
    </Frame>
  </Step>

  <Step>
    Add the public key from [Integrate.io](http://Integrate.io). Replace `ssh-rsa ...` with the public key content

    ```bash theme={null}
    $authorizedKey = "ssh-rsa ..."
    Add-Content -Force -Path $env:ProgramData\ssh\administrators_authorized_keys -Value $authorizedKey
    # Apply the necessary permission changes
    icacls.exe ""$env:ProgramData\ssh\administrators_authorized_keys"" /inheritance:r /grant ""Administrators:F"" /grant ""SYSTEM:F""
    ```
  </Step>

  <Step>
    Allow access to your server's host and port from [Integrate.io ELT's IP addresses](/cdc/ip-list).
  </Step>
</Steps>

<Note>
  **Notes:**

  * If the database is hosted inside the Windows machine and accessible locally, use the local IP of the Windows machine as the database host in [Integrate.io](http://Integrate.io). You can get it by running `ipconfig`.
  * The SSH tunnel username is `Administrator` for this guide.
</Note>

## Related

<CardGroup cols={2}>
  <Card title="IP Allowlist" icon="arrow-right" href="/cdc/ip-list" horizontal />

  <Card title="PrivateLink for MySQL" icon="arrow-right" href="/cdc/privatelink-set-up" horizontal />

  <Card title="PrivateLink for PostgreSQL" icon="arrow-right" href="/cdc/postgresql-privatelink-set-up" horizontal />
</CardGroup>
