<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Dharahas Ganapathiraju</title>
    <description>The latest articles on DEV Community by Dharahas Ganapathiraju (@dharahas_ganapathiraju).</description>
    <link>https://dev.to/dharahas_ganapathiraju</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4110903%2Fb0e55c17-5a5e-4b71-b0b9-dfa094703972.png</url>
      <title>DEV Community: Dharahas Ganapathiraju</title>
      <link>https://dev.to/dharahas_ganapathiraju</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/dharahas_ganapathiraju"/>
    <language>en</language>
    <item>
      <title>SFTP: A Developer's Beginner Guide</title>
      <dc:creator>Dharahas Ganapathiraju</dc:creator>
      <pubDate>Sat, 05 Sep 2026 11:43:14 +0000</pubDate>
      <link>https://dev.to/dharahas_ganapathiraju/sftp-a-developers-beginner-guide-4c3h</link>
      <guid>https://dev.to/dharahas_ganapathiraju/sftp-a-developers-beginner-guide-4c3h</guid>
      <description>&lt;h2&gt;
  
  
  1. What even is SFTP?
&lt;/h2&gt;

&lt;p&gt;SFTP stands for SSH File Transfer Protocol. Despite the name similarity, it has almost nothing to do with the old FTP (File Transfer Protocol) — it's an entirely different protocol built on top of SSH (Secure Shell).&lt;br&gt;
At its core, SFTP lets you securely transfer files between two computers over a network. When you need to drop a file on a remote server, pull logs off a machine, or automate moving data between systems — SFTP is one of the most common tools you'll reach for.&lt;/p&gt;
&lt;h2&gt;
  
  
  2. SFTP vs FTP vs FTPS — the confusion, cleared up
&lt;/h2&gt;

&lt;p&gt;These three names cause a lot of confusion for beginners. Here's a quick breakdown:&lt;br&gt;
&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F7wcfpvgeixi1fqf2fzhh.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F7wcfpvgeixi1fqf2fzhh.png" alt=" " width="468" height="91"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  3. How SFTP works under the hood
&lt;/h2&gt;

&lt;p&gt;SFTP runs as a subsystem of SSH. When you initiate an SFTP session, your SSH client negotiates an encrypted tunnel, and then launches the SFTP subsystem on the remote machine. All file operations — read, write, rename, delete — happen inside that tunnel.&lt;br&gt;
Here's the rough flow:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt; Client opens a TCP connection to the server on port 22.&lt;/li&gt;
&lt;li&gt; SSH handshake happens — server identity is verified, keys/passwords are exchanged.&lt;/li&gt;
&lt;li&gt; An encrypted session is established.&lt;/li&gt;
&lt;li&gt; The SFTP subsystem is started on the server side.&lt;/li&gt;
&lt;li&gt; Client and server exchange SFTP protocol messages (open file, read, write, close, etc.) over the encrypted channel.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Because it works on top of SSH, SFTP automatically gets everything SSH gives you: strong encryption, host verification, and support for public-key authentication.&lt;/p&gt;
&lt;h2&gt;
  
  
  4. Your first SFTP connection (CLI)
&lt;/h2&gt;

&lt;p&gt;On macOS and Linux, the sftp client ships with OpenSSH. On Windows, it's available via PowerShell or WSL. Connecting is straightforward&lt;/p&gt;

&lt;p&gt;For example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;sftp myUserName@sftp.example.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You'll be prompted for a password (or it will authenticate silently with your SSH key). Once connected, you'll land in an interactive shell:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Connected to sftp.example.com.
sftp&amp;gt; _
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can also specify a custom port if the server isn't on 22:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;sftp -P 2222 myUserName@sftp.example.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  5. Common SFTP commands you'll actually use
&lt;/h2&gt;

&lt;p&gt;Inside the interactive SFTP shell, you navigate the remote file system and your local file system at the same time. Commands prefixed with 'l' operate locally; others operate remotely.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fayt8ibg0a7ph7fmjn7hk.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fayt8ibg0a7ph7fmjn7hk.png" alt=" " width="468" height="287"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  6. Key-based authentication
&lt;/h2&gt;

&lt;p&gt;Typing a password every time gets old fast, and passwords are weaker than cryptographic keys. The proper way to authenticate to SFTP (and SSH in general) is with an SSH key pair.&lt;br&gt;
&lt;strong&gt;Step 1 — Generate a key pair on your machine:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;ssh-keygen -t ed25519 -C "your@email.com"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This creates two files: &lt;strong&gt;~/.ssh/id_ed25519&lt;/strong&gt; (private key — never share this) and ~&lt;strong&gt;/.ssh/id_ed25519.pub&lt;/strong&gt; (public key — safe to distribute).&lt;br&gt;
&lt;strong&gt;Step 2 — Copy your public key to the server:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;ssh-copy-id myUserName@sftp.example.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This appends your public key to &lt;strong&gt;~/.ssh/authorized_keys&lt;/strong&gt; on the server. Now connecting will work without a password prompt.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Important: Set correct permissions. Your ~/.ssh directory should be 700 and your private key file should be 600. SSH will refuse to use keys with overly permissive permissions&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  7. known_hosts — your silent security guard
&lt;/h2&gt;

&lt;p&gt;Every time you connect to an SSH/SFTP server for the first time, your client saves the server's host public key to a local file: &lt;strong&gt;~/.ssh/known_hosts&lt;/strong&gt;. On subsequent connections, SSH checks the server's fingerprint against this record. If they match, the connection proceeds silently. If they don't, SSH throws a loud warning and refuses to connect.&lt;br&gt;
This mechanism protects you against man-in-the-middle (MITM) attacks — where someone intercepts your connection and impersonates the server. Without it, an attacker on the same network could silently intercept your file transfers and credentials.&lt;br&gt;
What a known_hosts entry looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# ~/.ssh/known_hosts
sftp.example.com ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAI...
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each line stores: the hostname/IP, the key algorithm, and the base64-encoded public key. You never need to edit this file by hand — SSH manages it automatically.&lt;br&gt;
  What the warning looks like (and what to do)&lt;br&gt;
If a server's fingerprint changes — perhaps the server was rebuilt, or the SSH keys were rotated — you'll see this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@    WARNING: REMOTE HOST           @
@    IDENTIFICATION HAS CHANGED!    @
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
IT IS POSSIBLE THAT SOMEONE IS DOING SOMETHING NASTY!
Offending key for IP in /Users/you/.ssh/known_hosts:12
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Do NOT blindly clear the entry and reconnect. First verify out-of-band (ask the server admin, check the cloud console, or use a trusted internal tool) that the server's keys legitimately changed. Only once you've confirmed it's safe should you remove the stale entry:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;ssh-keygen -R sftp.example.com
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then reconnect and SSH will prompt you to confirm and save the new fingerprint.&lt;/p&gt;

&lt;h2&gt;
  
  
  8. Using SFTP in code
&lt;/h2&gt;

&lt;p&gt;For automation or application-level file transfers, you don't use the CLI — you use a library. Here are the most common picks by language:&lt;br&gt;
&lt;strong&gt;Node.js — using ssh2-sftp-client:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import Client from 'ssh2-sftp-client';

const sftp = new Client();

await sftp.connect({
  host: 'sftp.example.com',
  port: 22,
  username: 'myUserName',
  privateKey: require('fs').readFileSync('/home/you/.ssh/id_ed25519'),
});

await sftp.put('./report.csv', '/remote/reports/report.csv');
await sftp.end();
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Python — using paramiko:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import paramiko

transport = paramiko.Transport(('sftp.example.com', 22))
transport.connect(username='myUserName',
  pkey=paramiko.Ed25519Key.from_private_key_file('/home/you/.ssh/id_ed25519'))

sftp = paramiko.SFTPClient.from_transport(transport)
sftp.put('./report.csv', '/remote/reports/report.csv')

sftp.close()
transport.close()
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Java — using JSch:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;JSch jsch = new JSch();
jsch.addIdentity("/home/you/.ssh/id_ed25519");

jsch.setKnownHosts("/home/you/.ssh/known_hosts");

Session session = jsch.getSession("myUserName", "sftp.example.com", 22);
session.connect();

ChannelSftp channelSftp = (ChannelSftp) session.openChannel("sftp");
channelSftp.connect();

channelSftp.put("./report.csv", "/remote/reports/report.csv");

channelSftp.exit();
session.disconnect();
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  9. Things that trip beginners up
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Port 22 blocked by a firewall. If you can't connect, check if port 22 is open. Ask your sysadmin or check with: telnet hostname 22&lt;/li&gt;
&lt;li&gt;"Host key verification failed". This happens when the server's fingerprint isn't in your ~/.ssh/known_hosts. Run: ssh-keyscan hostname &amp;gt;&amp;gt; ~/.ssh/known_hosts&lt;/li&gt;
&lt;li&gt;Permission denied despite correct credentials. The server's sshd_config may restrict SFTP access, or the authorized_keys file has wrong permissions (chmod 600 ~/.ssh/authorized_keys on the server).&lt;/li&gt;
&lt;li&gt;Paths are confusing. The remote path is relative to the user's home directory by default. Use pwd inside the SFTP shell to confirm where you are.&lt;/li&gt;
&lt;li&gt;Large file transfers timing out. For big files in scripts, increase the ServerAliveInterval in your SSH config, or use rsync over SSH which supports resuming.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Wrapping up
&lt;/h2&gt;

&lt;p&gt;SFTP isn't glamorous, but it shows up constantly in real-world systems — automated deployments, data pipelines, legacy integrations, and secure log collection. The essentials are simple: it's SSH-based, it's encrypted, and port 22 is all you need.&lt;br&gt;
Start with the CLI to get a feel for navigating remote filesystems, switch to key-based auth as soon as possible, and reach for a library when you need to automate. Once you've done it a few times it becomes second nature.&lt;/p&gt;

</description>
      <category>sftp</category>
      <category>ssh</category>
      <category>programming</category>
      <category>beginners</category>
    </item>
  </channel>
</rss>
