<cfftp> connects CFML directly to an FTP (or secure FTP) server, letting an application upload, download, list, and manage files on a remote server the same way cffile and cfdirectory do for the local filesystem.
Learning Objectives
After completing this lesson, you'll be able to:
- Open a persistent, named FTP connection and reuse it across multiple operations instead of reconnecting every time.
- Upload and download files, and list a remote directory's contents.
- Connect securely over SFTP using a private key, instead of a plain password.
How cfftp Fits In
Your Code
cfftp action="open"
FTP Server
Named Connection Reused
Opening a Persistent Connection
Every action after the first can reuse an already-open connection by name, instead of supplying the server, username, and password again on every single call.
<cfftp connection="myFtp"
action="open"
server="ftp.example.com"
username="deploy"
password="#ftpPassword#"
stopOnError="true"><cfftp connection="myFtp" action="listDir" directory="/uploads" name="files"> <cfftp connection="myFtp" action="close">
stopOnError="true" makes a failed operation throw a catchable exception immediately, rather than silently continuing, worth setting explicitly rather than relying on the default.
Connecting Securely Over SFTP
action="open", secure="true"
Private Key + Passphrase
Authenticated SFTP Session
<cfftp connection="secureFtp"
action="open"
secure="true"
server="sftp.example.com"
username="deploy"
key="#expandPath('./keys/deploy_id_rsa')#"
passphrase="#keyPassphrase#"
stopOnError="true">Key-based authentication avoids sending a plain password at all, the private key and its passphrase authenticate the connection instead.
Uploading and Downloading Files
<cfftp connection="myFtp" action="putFile"
localFile="#expandPath('./export/report.csv')#"
remoteFile="/uploads/report.csv"><cfftp connection="myFtp" action="getFile"
localFile="#expandPath('./incoming/data.csv')#"
remoteFile="/outbound/data.csv">The action Attribute: Common Operations
| action | What it does |
|---|---|
| open / close | Opens or closes a named, reusable connection |
| putFile / getFile | Uploads or downloads a single file |
| listDir | Returns a query describing a remote directory's contents |
| changeDir / getCurrentDir | Changes or reports the current remote working directory |
| createDir / removeDir | Creates or deletes a remote directory |
| existsFile / existsDir / exists | Checks whether a remote file, directory, or either exists |
| rename / remove | Renames or deletes a remote file |
| quote / site | Sends a raw FTP command directly to the server for anything not otherwise covered |
listDir's exact result columns are documented inconsistently across engines and versions, dump the returned query directly (cfdump) the first time to confirm exactly what a specific server and engine actually return before relying on a particular column name.
Connection and Transfer Attributes Worth Knowing
| Attribute | Meaning |
|---|---|
| server / port | The FTP host, and its port (default 21, commonly 22 for secure/SFTP) |
| username / password | Standard credential-based authentication |
| secure | Connects over SFTP instead of plain FTP |
| key / passphrase / fingerprint | Private-key authentication for secure connections, instead of a password |
| passive | Uses passive-mode FTP, often required when the client sits behind a firewall or NAT |
| transferMode | auto, ascii, or binary, auto tries to detect the right mode per file |
| timeout / retryCount | How long to wait for the server, and how many times to retry |
| stopOnError | Whether a failed operation throws a catchable exception (recommended: true) |
Lucee-Specific Notes Worth Knowing
| Detail | What it means |
|---|---|
| Separate FTP extension (Lucee 7.1+) | FTP functionality moved out of Lucee's core into a dedicated FTP extension, confirm it's installed if cfftp stops working after an upgrade |
| Public-key authentication | Added in Lucee 5.2.7.38, earlier Lucee versions support password authentication only |
| Different underlying FTP client than Adobe ColdFusion | Server-specific commands (like a raw chmod sent via quote/site) aren't guaranteed to behave identically between engines, since each uses a different FTP client library underneath |
That last point matters in practice: code sending raw site/quote commands tuned for Adobe ColdFusion's FTP client isn't guaranteed to work unchanged after switching to Lucee, since the two engines don't share the same underlying implementation.
Common Beginner Mistakes
Opening a brand-new connection for every single operation
Open one named connection with action="open", then reuse it by name for every subsequent action, closing it once at the end.
Leaving stopOnError at its default instead of setting it explicitly
Without stopOnError="true", a failed FTP operation can continue silently rather than throwing a catchable exception immediately.
Assuming transferMode="auto" always picks the right mode
For files where automatic detection is unreliable, set transferMode to "ascii" or "binary" explicitly rather than trusting auto.
Assuming a raw site/quote command written for one CFML engine works unchanged on another
Adobe ColdFusion and Lucee use different underlying FTP client implementations, a server-specific raw command isn't guaranteed to behave identically on both.
Best Practices
- Open one named connection per logical session and reuse it, rather than reconnecting for every file.
- Always close a connection explicitly with action="close" once done with it.
- Set stopOnError="true" so a failed transfer surfaces as a catchable exception instead of failing silently.
- Prefer key-based authentication (secure="true" with key/passphrase) over a plain password whenever the server supports it.
Interview Questions
Why open a named FTP connection instead of authenticating on every single cfftp call?
A named connection (via action="open", given a connection name) is established once and reused for subsequent operations, avoiding the overhead and complexity of reconnecting for every action.
How does cfftp authenticate without sending a plain password?
Setting secure="true" along with key (a private key file path) and passphrase authenticates over SFTP using key-based authentication instead of a password.
What does stopOnError control, and what's the risk of leaving it at its default?
It determines whether a failed FTP operation throws a catchable exception immediately. Left at its default, a failure can go unnoticed instead of surfacing as an exception the application can handle.
Why might a raw quote or site command behave differently between Adobe ColdFusion and Lucee?
The two engines use different underlying FTP client implementations, so server-specific raw commands aren't guaranteed to behave identically across both.
Summary
In this lesson, you opened a persistent, named FTP connection and reused it across multiple operations, uploaded and downloaded files, connected securely over SFTP using key-based authentication, and covered real differences in how Adobe ColdFusion and Lucee implement cfftp underneath.
What's Next?
The next lesson covers cfregistry, reading and writing Windows registry values directly from CFML.