Deploy
A Kilim site is a folder of static files. Publish it in one of two ways:
- Upload
dist/yourself.kilim buildwrites a complete site todist/, and any host that serves files can take that folder as it is, through its own upload page, CLI or CI action. - Run
kilim deploy. It builds the site, checks it (likekilim check), compares the output with what the target has, and uploads only the difference, through an adapter set inkilim.config.ts.
kilim deploy --dry-run # build, check and list the changes; nothing is sent
kilim deploy # build, check and upload
kilim deploy --no-check # upload even when the check finds errors| Way | Status | For | Credentials | Old files | _headers, _redirects |
|---|---|---|---|---|---|
Upload dist/ | stable | any static host | the host's own | up to you | where the host reads them |
git | stable | GitHub Pages and other hosts that publish a branch | the git remote's own (SSH key, token) | the branch has only the build | GitHub Pages ignores them |
cloudflarePages | experimental | Cloudflare Pages | CLOUDFLARE_API_TOKEN | each deployment is complete | used |
s3 | experimental | Amazon S3, Cloudflare R2, MinIO | AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY | deleted (deleteRemoved: true) | not uploaded |
sftp | experimental | a VPS or hosting with SSH | SFTP_PRIVATE_KEY, SFTP_PRIVATE_KEY_PATH, SFTP_PASSWORD or ssh-agent | kept (deleteRemoved: false) | not uploaded |
ftp | experimental | shared hosting with only FTP | FTP_PASSWORD | kept (deleteRemoved: false) | not uploaded |
Stable ways are fully supported. Experimental adapters work and are tested against local stand-ins of the service (fake API servers, a local OpenSSH and FTP server), but have not been tried with real accounts yet, and their options may change in a minor release. Try them with --dry-run first, and report what you find.
The adapters live in @kilim-dev/core/adapters. Their options are checked when the config loads, and an error names the option and its line, e.g. kilim.config.ts:7: "deploy.project": .... kilim doctor checks them without building or uploading anything, along with the environment variables the adapter needs (such as CLOUDFLARE_API_TOKEN) and, for git, that git runs and the remote exists; for sftp, that the server's key is known.
Credentials always come from environment variables, never from the config, so kilim.config.ts can be committed. On a host that reads neither _headers nor _redirects, redirects from aliases and redirects.txt still work through the redirect pages Kilim writes; set the security headers and CSP in the server or CDN instead.
GitHub Pages and Cloudflare Pages answer missing URLs with 404.html at the site root (an S3 website does when it is set as the error document). Kilim writes it from content/404.md, whatever trailingSlash says; the page is noindex and stays out of the sitemap, feeds and collection lists. kilim preview serves it the same way, so try a missing URL there before you deploy. To check the site on a phone first, run kilim preview --host and open the "On your network" address it prints.
Set url in the config to the address the site is published at, so canonical links, the sitemap and feeds point there.
- Build and check.
kilim deploybuilds the site and runs the same check askilim check. Errors stop the deploy;--max-warnings <n>stops it on more thannwarnings too, and--no-checkskips the check. - Plan. The adapter compares the build with what the target has and prints the files it adds, changes and removes.
--dry-runstops here, so nothing is sent. - Upload. Stylesheets, images and other files go first, then the pages, then deletions, so a visitor never gets a page whose assets are missing.
- Manifest. The
s3,sftp,ftpandcloudflarePagesadapters write_kilim/deploy.jsonlast: the site's files and their hashes. The next plan reads it instead of downloading the site, and a deploy that stops halfway is completed by the next one.
deleteRemoved decides what happens to files of earlier deploys that the build no longer has. Files the adapter keeps stay in the manifest, so turning on deleteRemoved later still deletes them, and only them. Without a manifest (the first deploy, or files put there another way), the adapter cannot tell its files from others: with deleteRemoved: true it deletes everything in the target that the build lacks, so look at kilim deploy --dry-run first.
Run kilim doctor before the deploy step: it checks Node.js, the config, the theme, url and the adapter's options and environment variables, without building or connecting. With --json it prints the checks for other tools, and --max-warnings 0 makes a warning fail the job:
kilim doctor --max-warnings 0
kilim deploy --max-warnings 0