import { spawn } from "node:child_process"; import { program, Option } from "commander"; interface DeployLftpOptions { host: string; user: string; password: string; targetFolder: string; sourceFolder: string; } async function deployLftp({ host, user, password, targetFolder, sourceFolder }: DeployLftpOptions) { const process = spawn( "lftp", [ "-c", [ `open -u ${user},${password} ${host}`, `mirror --reverse --include-glob assets/* --delete --only-missing --no-perms --verbose ${sourceFolder} ${targetFolder}`, `mirror --reverse --exclude-glob assets/* --delete --no-perms --verbose ${sourceFolder} ${targetFolder}`, `bye`, ].join("\n"), ], { stdio: "inherit", }, ); await new Promise<void>((resolve, reject) => { process.on("close", (code) => { if (code === 0) { resolve(); } else { reject(`deploy-lftp failed with code ${code}`); } }); }); } await program .name("deploy-lftp") .description("Deploy files to remote server with LFTP") .addOption( new Option("-h, --host <hostname>", "Hostname of the LFTP (i.e. WebDav, SCP, SFTP...) remote.").env( "DEPLOY_LFTP_HOST", ), ) .addOption(new Option("-u, --user <username>", "Username portion of the LFTP credentials").env("DEPLOY_LFTP_USER")) .addOption( new Option("-p, --password <pass>", "Password portion of the LFTP credentials").env("DEPLOY_LFTP_PASSWORD"), ) .addOption( new Option("-t, --target-folder <remoteDir>", "Folder to mirror files to in the LFTP remote").env( "DEPLOY_LFTP_TARGETFOLDER", ), ) .addOption( new Option("-s, --source-folder <localDir>", "Folder to read files from in the local machine") .env("DEPLOY_LFTP_SOURCEFOLDER") .default("dist/"), ) .action(deployLftp) .parseAsync();