Skip to content
You're reading the docs for DRE 0.4 (v0.4.4). This page for 0.5 · New in 0.5

FTP and FTPS

FTP and FTPS servers: the ftp destination, from the ftp package. Declare the package once in dependencies.yml; DRE installs it on demand:

dependencies.yml
plugins:
- ftp

Set in profiles.yml, under destinations:, in a target with type: ftp.

Field Default Notes
host (required) FTP server.
port 21 Port.
username (required) User name.
password Password. Secret: use env_var().
tls none None or explicit (FTPS) One of none, explicit.
passive Passive mode (default true)
tls_accept_invalid_certs Accept a self-signed server certificate.
connect_timeout 30s How long to wait for a connection (30s, 2m, or seconds) A duration (30s, 2m) or seconds.
timeout 60s How long a read or write may make no progress before it fails. A duration (30s, 2m) or seconds.
retries 3 How many times to try again after a temporary error (0: never)

Set in the report’s output.destination entry.

Option Type Default Notes
if_exists string overwrite When a file is already at the path: overwrite it, fail with error, or number the new one. One of overwrite, error, number.
atomic boolean true Upload under a temporary name, then rename, so no half-written file appears.
temp_dir string Where the temporary file goes (on the same server), for receivers that pick up any new file.

host, port (21), username, password, passive (default true), and tls: none or explicit (FTPS). tls_accept_invalid_certs allows self-signed server certificates.

Paths are relative to the folder the login starts in; a leading / means the server’s root, which on many servers isn’t the login folder (/reports/x.csv vs reports/x.csv). FTPS data connections reuse the control connection’s TLS session, which vsftpd, ProFTPD and FileZilla Server require by default. Uploads go under a temporary name first (atomic, temp_dir: see Uploads under a temporary name), and a failed upload removes the temporary file from the server when it can. With if_exists: error or number, DRE looks for the name before the rename; FTP can’t do both in one step (see A file already at the path).

Use FTP when the receiver requires it; explicit FTPS protects the connection. Adapt the report in the SFTP delivery example with the ftp package and:

profiles.yml
destinations:
partner:
targets:
dev: {deliver: false}
prod:
type: ftp
host: ftp.example.com
username: reporting
password: "{{ env_var('DRE_SECRET_FTP_PASSWORD') }}"
tls: explicit
passive: true
# within the report's output
destination:
profile: partner
path: "incoming/report-{{ run.date.yyyymmdd }}.csv"
atomic: true
temp_dir: staging
if_exists: error

Keep tls_accept_invalid_certs disabled for a real server. A certificate failure needs the server certificate or trust chain repaired. ftp/file-exists means the name is taken; delivery-failed on rename needs write access in both directories and a supported rename. For a firewall timeout, check passive data ports as well as the control port. See destination keys, atomic uploads and destination.