• About me…

ConfigMgr

VMware, Azure and Automation

  • About me…

VCF 9.1 SFTP Backup Target — Build on VMware Workstation, Migrate to VCF

24 juli 2026 Cloud Foundation VMware

Summary runbook covering: build in Workstation → export/import to vCenter → harden sshd for FIPS → verify → register in VCF Operations. Based on ITQ’s VCF 9.1 Backup Target guide, with fixes for the errors hit during this build.

1. Provision the VM in Workstation

  • Ubuntu Server 24.04 LTS, minimal install
  • Set virtual hardware version at creation time to one your target vSphere/VCF version supports (don’t accept Workstation’s newest default — it can exceed what vSphere understands). Check vSphere 8/9 compatibility; hardware version 19 or 20 is typically safe.
  • Sizing: CPU/RAM are trivial for SFTP; disk sized for your retention window (daily SDDC Manager/vCenter backups, hourly NSX backups, 7-day retention each) — start with a few hundred GB and adjust to your environment.

2. Base OS setup

sudo apt update && sudo apt upgrade -y
sudo timedatectl set-timezone <your-tz>
sudo hostnamectl set-hostname sftp01.yourdomain.com

Confirm/install OpenSSH server:

sudo apt install openssh-server -y
sudo systemctl enable --now ssh

Install open-vm-tools instead of relying on Workstation’s bundled tools (needed for a clean run under vSphere later):

sudo apt install open-vm-tools -y

Set the NIC to VMXNET3 in the VM’s virtual hardware settings (not the Workstation default e1000) for proper vSphere performance.

3. Create the service account and chroot jail

sudo groupadd sftpbackup
sudo useradd -g sftpbackup -s /sbin/nologin -m svc-vcf-bck
sudo passwd svc-vcf-bck   # strong password — store in password manager
sudo mkdir -p /sftp/svc-vcf-bck/backups
sudo chown root:root /sftp/svc-vcf-bck
sudo chmod 0755 /sftp/svc-vcf-bck
sudo chown svc-vcf-bck:sftpbackup /sftp/svc-vcf-bck/backups
sudo chmod 0750 /sftp/svc-vcf-bck/backups

The chroot directory itself must stay root-owned and not group/world writable — sshd refuses the chroot at login otherwise. Only the backups subfolder belongs to the service account.

4. Configure sshd (FIPS-ready, hardened)

Back up first:

sudo cp /etc/ssh/sshd_config /etc/ssh/sshd_config.bak

Edit /etc/ssh/sshd_config. Crypto directives must sit above the first Match block — they’re global-only and sshd won’t start if they land inside a Match block. Directive names are plural — KexAlgorithms and HostKeyAlgorithms, not the singular form (a common typo that throws Bad configuration option):

# --- VCF backup target crypto (must stay above any Match block) ---
KexAlgorithms ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521,diffie-hellman-group-exchange-sha256,curve25519-sha256
MACs hmac-sha2-256,hmac-sha2-256-etm@openssh.com,hmac-sha1
Ciphers aes256-ctr,aes256-gcm@openssh.com,chacha20-poly1305@openssh.com
HostKeyAlgorithms rsa-sha2-512,rsa-sha2-256,ecdsa-sha2-nistp256,ssh-ed25519

Subsystem sftp internal-sftp

Match Group sftpbackup
    ChrootDirectory /sftp/%u
    ForceCommand internal-sftp
    AllowTcpForwarding no
    X11Forwarding no
    PasswordAuthentication yes

No spaces after commas in the algorithm lists — a stray space (or a smart-quote/non-breaking space from a copy-paste) causes Bad SSH2 KexAlgorithms. Verify with cat -A or od -c on the line if you hit that error, and cross-check supported algorithms with ssh -Q kex.

Validate before restarting, and keep a root session open in case of a mistake:

sudo sshd -t
sudo systemctl restart ssh

5. Firewall (ufw)

Scope to the actual VCF management network CIDR(s) where the services-runtime pods, SDDC Manager, NSX Manager, and VCF Operations live — find these under VCF Operations → Build → Lifecycle → Components → VCF Services Runtime → Nodes. Don’t scope to a few named hosts — connections come from arbitrary pod IPs across several services, so a narrow rule breaks the moment a service restarts onto a new address.

sudo ufw allow from <mgmt-cidr> to any port 22 proto tcp

ICMP isn’t a supported proto in ufw’s simple syntax (unsupported protocol icmp) — it has to go directly into /etc/ufw/before.rules:

sudo nano /etc/ufw/before.rules

Add above the existing default ICMP lines (order matters — allow rule first):

-A ufw-before-input -p icmp -s <mgmt-cidr> --icmp-type echo-request -j ACCEPT
-A ufw-before-input -p icmp --icmp-type echo-request -j DROP
sudo ufw reload

No outbound rule is needed — ufw’s default outgoing policy is allow, so echo-replies go out automatically (sudo ufw status verbose to confirm).

If you opened SSH/ICMP to “any” for quick testing: tag the rule so it doesn’t get forgotten (ufw allow 22/tcp comment 'TEMP - testing only'), keep the exposure window short, and swap it for the scoped CIDR rule immediately after verification — password auth + backup data on this box makes an open port 22 worth avoiding beyond a brief test window.

6. Shut down and export from Workstation

sudo shutdown -h now

In Workstation: File → Export to OVF. This packages the VMDK and config into a format vCenter’s OVF deploy wizard reads directly.

7. Import into vCenter (NIC disconnected first)

vCenter → right-click target cluster/folder → Deploy OVF Template → select the exported OVF/OVA → choose datastore, map the network to the correct management-adjacent segment.

Before powering on, disconnect the NIC (uncheck “Connect at power on” on the network adapter in the VM’s Edit Settings, or untick “Connected” if it’s already powered off). This keeps the VM off the network while it still carries whatever IP/netplan config it had from Workstation, so it can’t collide with another host or leak onto the production segment with stale settings.

Power on, console in, and set the real IP inside the OS while still disconnected:

sudo nano /etc/netplan/*.yaml
network:
  version: 2
  ethernets:
    ens160:                     # confirm the interface name with `ip a`
      addresses:
        - 10.0.10.50/24
      routes:
        - to: default
          via: 10.0.10.1
      nameservers:
        addresses: [10.0.10.10]
sudo netplan apply

Confirm the config took before going any further:

ip a
ip route
resolvectl status   # or cat /etc/resolv.conf

Only once the IP, gateway, and DNS are correct do you reconnect the NIC — in vCenter, edit settings and tick Connect (or Connect at power on for future reboots). At that point the VM lands on the network already carrying its final, correct address, instead of briefly appearing with Workstation-era settings.

Create the DNS A + PTR records for the new IP/hostname now if you haven’t already, since the verification steps later depend on them resolving correctly.

8. Host-key note

Treat this as a one-time build-and-move, not a template. If you later clone this VM to stamp out more SFTP servers, the host keys (and /etc/machine-id) need to be regenerated per clone, or every clone shares the same SSH identity. Do the SSH/SFTP verification below only after the VM has its final IP/hostname — don’t rely on a fingerprint fetched while it was still in Workstation.

9. Confirm host keys and sizes

ssh-keygen -lf /etc/ssh/ssh_host_ecdsa_key.pub   # expect 256
ssh-keygen -lf /etc/ssh/ssh_host_rsa_key.pub     # expect >= 2048
ssh-keygen -lf /etc/ssh/ssh_host_ed25519_key.pub

10. Verify before registering in VCF

Force the FIPS negotiation from a Linux client on the management network (not native Windows ssh-keyscan — it’s broken against modern servers due to an unsupported post-quantum KEX it advertises but can’t perform):

ssh -o KexAlgorithms=ecdh-sha2-nistp256 \
    -o MACs=hmac-sha2-256 \
    -o HostKeyAlgorithms=ecdsa-sha2-nistp256 \
    -o Ciphers=aes256-ctr \
    svc-vcf-bck@sftp01.yourdomain.com

Getting “This service allows sftp connections only” here is success, not an error — it confirms the crypto negotiated and the account authenticated; ForceCommand internal-sftp is just refusing the interactive shell ssh tried to open, exactly as configured.

Now do the real functional test with sftp (create the local test file before connecting, or the local put fails with stat testfile.txt: No such file or directory — that error is about the file missing on your local machine, not the server):

echo "vcf backup target test" > testfile.txt

sftp -o KexAlgorithms=ecdh-sha2-nistp256 \
     -o MACs=hmac-sha2-256 \
     -o HostKeyAlgorithms=ecdsa-sha2-nistp256 \
     -o Ciphers=aes256-ctr \
     svc-vcf-bck@sftp01.yourdomain.com
sftp> cd backups
sftp> put testfile.txt
sftp> ls
sftp> pwd

pwd here (e.g. /backups) is the chroot-relative path to enter in the VCF wizard — not the server’s real filesystem path.

11. Register in VCF Operations

  • Fleet/management services config: Build → Lifecycle → Backup & Restore
  • SDDC Manager + NSX config: Operate → Administration → SDDC Manager (separate screen — both need setting)
  • Host: use the server’s IP, not FQDN, if the name could ever resolve to more than one box (load balancer, round-robin DNS) — an FQDN fronting multiple hosts breaks host-key pinning even when the target itself is fine
  • Directory: the chroot-relative path from step 10 (e.g. /backups)
  • Click Fetch Fingerprint, compare against the ssh-keygen -lf output from step 9
  • vCenter backup is separate again — configure manually per instance in each vCenter’s VAMI (https://<vcenter-fqdn>:5480 → Backup)

12. Firewall cleanup

If step 5 or the verification stage used a temporary “any” rule, close it now and confirm only the scoped CIDR rule remains:

sudo ufw status numbered
sudo ufw delete <temp-rule-number>
sudo ufw status verbose

Quick error reference (from this build)

ErrorCauseFix
Bad configuration option: KexAlgorithm / HostKeyAlgorithmDirective name missing trailing sUse KexAlgorithms / HostKeyAlgorithms
Bad SSH2 KexAlgorithmsStray space after a comma, or an unsupported algorithm nameRemove spaces around commas; cross-check with ssh -Q kex
unsupported protocol icmp (ufw)ufw’s simple allow syntax doesn’t support ICMPEdit /etc/ufw/before.rules directly
This service allows sftp connections onlyExpected — ForceCommand internal-sftp blocking a shell sessionNot an error; re-test with sftp instead of ssh
stat testfile.txt: No such file or directory on putLocal file doesn’t exist on the client machineCreate it locally first (echo ... > testfile.txt)
backuprestoresftpvcfvcf management

Building a Stretched VCF Workload Cluster on NFS: Lessons from the Field

Recent Posts

  • VCF 9.1 SFTP Backup Target — Build on VMware Workstation, Migrate to VCF
  • Building a Stretched VCF Workload Cluster on NFS: Lessons from the Field
  • How to Fix “Version Drift” in VCF Operations After an SDDC Manager Upgrade
  • Hands-On Guide: How to install VCF 9.1 on NFS Principal Storage
  • Demystifying VCF 9.1 Networking: From Core Architecture to VPCs and VNAs

Recent Comments

  1. Migrating NSX Distributed Firewall Policies the Right Way: A PowerShell Toolkit – ConfigMgr op Migrating NSX Distributed Firewall Policies – part 2
  2. Migrating NSX Distributed Firewall Policies – part 2 – ConfigMgr op Migrating NSX Distributed Firewall Policies the Right Way: A PowerShell Toolkit

Archives

  • juli 2026
  • juni 2026
  • mei 2026
  • maart 2026
  • december 2025
  • juli 2025
  • mei 2025
  • april 2025
  • maart 2025
  • november 2024
  • oktober 2024
  • januari 2024
  • november 2023
  • oktober 2023
  • september 2023
  • juni 2023
  • mei 2023
  • april 2023
  • november 2022
  • maart 2021
  • februari 2021
  • januari 2021
  • november 2020
  • oktober 2020
  • september 2020
  • juli 2020
  • juni 2020
  • april 2020
  • maart 2020
  • februari 2020
  • oktober 2019
  • september 2019
  • juli 2019
  • juni 2019
  • mei 2019
  • maart 2019
  • februari 2019
  • januari 2019
  • december 2018
  • november 2018
  • april 2018
  • januari 2018
  • juli 2017
  • juni 2017
  • mei 2017

Categories

  • AnyLinq
  • Azure
  • Cloud Director
  • Cloud Foundation
  • ConfigMgr
  • DIY
  • HomeAssistant
  • ITQ
  • Microsoft
  • NSX
  • PowerCli
  • Powershell
  • SCCM
  • Script
  • SDDC Manager
  • Solutions
  • System Center
  • Veeam
  • VMware
  • vRealize Automation
  • vRealize Orchestrator
Proudly powered by WordPress | Theme: Doo by ThemeVS.