On this page ▾
Hosting
slide-ng build writes a static site: plain files that any web server can hand out. No Node is needed to serve it.
slide-ng build # ./dist, served at /
slide-ng build --base /talk/ # for https://you.github.io/talk/
slide-ng build --out public-html # another output folder
slide-ng build --download # also writes the PDF and adds the download button
slide-ng build --without-notes # speaker notes are not shipped
slide-ng build --offline # a folder that opens from disk
Safe output folders
The build empties its output folder. To make sure it never wipes something of yours, it only does so when the folder is new, empty, or has a .slide-ng-build file written by an earlier build. Any other folder with files in it is refused. The current folder, your home folder and / are always refused.
What is in the build
| File | What for |
|---|---|
index.html, main-*.js, chunk-*.js, styles-*.css |
The app. Monaco, Mermaid and the like are separate chunks, fetched only when a slide uses them. |
404.html |
A copy of index.html. GitHub Pages shows it for unknown paths, so /talk/3 opens the app. |
_redirects |
The same rule for Netlify. |
<exportFilename>.pdf |
Only with --download or download: true. |
og-image.png |
The link preview picture, see Page head and SEO. |
remote-assets/ |
Remote pictures that were downloaded, see Bundle remote assets. |
media/ |
Font files for KaTeX and for web fonts with fonts.selfHost. |
sw.js, manifest.webmanifest |
Offline support, pwa: true. |
Addresses and the base path
The deck lives at the base. Every slide is <base><number> in history mode, the default, or <base>#/<number> with routerMode: hash.
- History mode needs the host to answer unknown paths with
index.html.404.html,_redirectsand the examples below do that. - Hash mode needs nothing from the host. Use it where you cannot change the server, such as a plain file share.
--baseis a path such as/talk/, not a full address. Build for the prefix you will serve under.
GitHub Pages
# .github/workflows/pages.yml
name: Deploy slides
on:
push: { branches: [main] }
permissions: { pages: write, id-token: write, contents: read }
jobs:
deploy:
runs-on: ubuntu-latest
environment: { name: github-pages, url: '${{ steps.deployment.outputs.page_url }}' }
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with: { node-version: 22 }
- run: npm ci
- run: npx slide-ng build --base /${{ github.event.repository.name }}/
- uses: actions/upload-pages-artifact@v3
with: { path: dist }
- id: deployment
uses: actions/deploy-pages@v4
For a user site (you.github.io) use --base /. If you use --download or seoMeta.ogImage: auto, the runner also needs a Chromium.
Netlify
The build contains _redirects. Or use netlify.toml:
[build]
command = "npx slide-ng build"
publish = "dist"
[[redirects]]
from = "/*"
to = "/index.html"
status = 200
Vercel
{
"buildCommand": "npx slide-ng build",
"outputDirectory": "dist",
"rewrites": [{ "source": "/(.*)", "destination": "/index.html" }]
}
nginx
server {
listen 80;
root /usr/share/nginx/html;
location / {
try_files $uri $uri/ /index.html; # history mode: unknown paths are deck addresses
}
location = /sw.js {
add_header Cache-Control "no-cache"; # the offline worker must be checked for updates
}
}
Under a sub-path build with --base /talk/, put the files in /usr/share/nginx/html/talk/ and use try_files $uri $uri/ /talk/index.html;.
Size
A deck without heavy features is about 450 kB at startup, about 110 kB compressed. Decks that use Monaco or KaTeX add their style sheets to that. The build warns above 1.5 MB at startup and fails above 3 MB. Monaco, Mermaid and Magic Move are lazy chunks and do not count.