加载中...
加载中...
Slidev 是一个基于 Web 的演示文稿框架,它使用 Markdown 编写幻灯片,支持 Vue 组件、动画效果、演讲者注释等强大功能。在开发阶段,Slidev 作为 Web 服务器运行,提供了实时预览和编辑功能。然而,当我们需要将演示文稿分享给他人、部署到生产环境,或者需要离线访问时,就需要将 Slidev 项目构建为静态文件并进行部署。
与传统的 PowerPoint 或 Keynote 不同,Slidev 构建后的演示文稿仍然保持交互性,支持动画、代码高亮、LaTeX 数学公式等特性。这使得 Slidev 不仅适合技术分享、产品演示,也适合在线教育、文档展示等场景。
本文将深入探讨 Slidev 的构建与部署流程,从基础的 SPA(单页应用)构建开始,逐步介绍 PDF 导出、远程资源打包、多平台托管方案,以及 Docker 容器化部署。无论您是第一次部署 Slidev 项目,还是希望优化现有的部署流程,都能从本文中获得全面的指导和实践建议。
Slidev 基于 Vite 构建系统,可以将 Markdown 编写的幻灯片转换为静态的 Single-page Application(SPA)。构建后的文件是完全静态的,可以部署到任何静态文件托管服务,无需服务器端支持。
构建的核心优势
最简单的构建命令是:
slidev build
这个命令会:
slides.md 文件(或通过配置指定的入口文件)dist 目录构建后的目录结构
dist/
├── index.html # 主 HTML 文件
├── assets/ # 静态资源(JS、CSS、图片等)
│ ├── index-[hash].js
│ ├── index-[hash].css
│ └── ...
└── [其他静态资源]
测试构建结果
构建完成后,可以使用以下命令在本地预览构建结果:
# 使用 Vite 预览
npx vite preview
# 或使用其他静态服务器
npx serve dist
npx http-server dist
python -m http.server -d dist
默认情况下,构建产物会输出到 dist 目录。如果需要自定义输出目录,可以使用 --out 选项:
slidev build --out my-build-folder
这个选项在以下场景特别有用:
示例:多环境构建
# 开发版本
slidev build --out dist-dev
# 生产版本
slidev build --out dist-prod
# 演示版本(移除演讲者注释)
slidev build --out dist-demo --without-notes
当需要将幻灯片部署到子路径(sub-route)时,必须配置 --base 选项。这个选项告诉 Vite 构建系统应用的基础路径,确保资源路径正确解析。
Base Path 规则
/ 开头和结尾/(根路径)示例:部署到子路径
假设您要将幻灯片部署到 https://example.com/talks/my-cool-talk/,构建命令应该是:
slidev build --base /talks/my-cool-talk/
Base Path 的工作原理
当设置了 base path 后,Vite 会:
常见场景示例
# GitHub Pages:用户名/仓库名
slidev build --base /my-repo/
# Netlify:部署到子目录
slidev build --base /presentations/2024/
# 自定义域名子路径
slidev build --base /slides/tech-talk/
验证 Base Path
构建完成后,检查 dist/index.html 文件中的资源路径,应该都包含 base path 前缀:
<!-- 正确 -->
<script type="module" src="/talks/my-cool-talk/assets/index-abc123.js"></script>
<!-- 错误(缺少 base path) -->
<script type="module" src="/assets/index-abc123.js"></script>
演讲者注释(Speaker Notes)是 Slidev 的一个重要功能,允许演讲者在演示时查看额外的提示信息。然而,在公开分享的演示文稿中,这些注释可能包含敏感信息或不适合公开的内容。
使用 --without-notes 选项
slidev build --without-notes
这个选项会:
何时使用
注意事项
使用 --without-notes 后,构建版本将无法查看或使用演讲者注释功能。如果需要保留注释功能,应该使用不同的构建配置或部署方案。
Slidev 支持在构建时自动生成 PDF 版本,这对于需要离线访问、打印或存档的场景非常有用。
启用 PDF 生成
slidev build --pdf
构建过程会:
PDF 生成配置
可以在 slides.md 的 frontmatter 中配置 PDF 选项:
---
# PDF 相关配置
pdf:
# PDF 文件名
filename: my-presentation.pdf
# 页面大小
format: A4
# 打印背景
printBackground: true
# 页面边距
margin:
top: 10mm
right: 10mm
bottom: 10mm
left: 10mm
---
PDF 生成的最佳实践
PDF 生成的限制
默认情况下,Slidev 构建时不会下载和打包远程资源(如图片、字体等)。如果幻灯片中引用了外部 URL 的资源,这些资源在构建后仍然需要从原始服务器加载。
使用 --download 选项
slidev build --download
这个选项会:
适用场景
注意事项
配置下载选项
可以在配置文件中设置下载行为:
// vite.config.ts
export default {
slidev: {
download: {
// 下载超时时间(毫秒)
timeout: 30000,
// 并发下载数
concurrency: 5,
// 允许下载的文件类型
allowedTypes: ['image', 'font'],
},
},
}
Slidev 支持一次构建多个演示文稿,这对于管理多个项目或需要构建多个版本的场景非常有用。
构建多个文件
slidev build slides1.md slides2.md slides3.md
每个输入文件会:
使用 Glob 模式
如果 shell 支持 glob 模式,可以使用通配符:
# 构建所有 .md 文件
slidev build *.md
# 构建特定目录下的文件
slidev build talks/*.md
# 递归构建
slidev build **/*.md
批量构建的输出结构
dist/
├── slides1/
│ ├── index.html
│ └── assets/
├── slides2/
│ ├── index.html
│ └── assets/
└── slides3/
├── index.html
└── assets/
批量构建的最佳实践
示例:构建脚本
#!/bin/bash
# build-all.sh
# 构建所有演示文稿
for file in talks/*.md; do
name=$(basename "$file" .md)
echo "Building $name..."
slidev build "$file" --out "dist/$name"
done
echo "All presentations built successfully!"
GitHub Pages 是 GitHub 提供的免费静态网站托管服务,非常适合部署 Slidev 构建的演示文稿。它支持自定义域名、HTTPS、CDN 加速等功能,是个人项目和小型团队的首选方案。
GitHub Pages 的优势
第一步:启用 GitHub Actions
Settings > PagesBuild and deployment 部分,选择 GitHub ActionsDeploy from a branch,因为我们需要通过 Actions 构建第二步:创建部署工作流
创建 .github/workflows/deploy.yml 文件:
name: Deploy Pages
on:
push:
branches:
- main
permissions:
contents: read
pages: write
id-token: write
concurrency:
group: 'pages'
cancel-in-progress: false
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v2
with:
version: 8
- uses: actions/setup-node@v4
with:
node-version: 20
cache: pnpm
- name: Install dependencies
run: pnpm install
- name: Build
run: pnpm run build
- name: Setup Pages
uses: actions/configure-pages@v4
- name: Upload artifact
uses: actions/upload-pages-artifact@v3
with:
path: dist
deploy:
needs: build
runs-on: ubuntu-latest
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
steps:
- name: Deploy to GitHub Pages
id: deployment
uses: actions/deploy-pages@v4
工作流配置说明
main 分支时触发pages: write 和 id-token: write 权限concurrency 避免并发部署冲突如果仓库名称不是 username.github.io,需要配置 base path。
获取 Base Path
Base path 格式为:/repository-name/
例如,如果仓库名是 my-slides,base path 就是 /my-slides/
配置方法
在 vite.config.ts 或构建命令中设置:
// vite.config.ts
export default {
base: process.env.NODE_ENV === 'production' ? '/my-slides/' : '/',
}
或者在构建命令中:
- name: Build
run: pnpm run build --base /my-slides/
验证部署
部署完成后,访问 https://username.github.io/repository-name/ 查看部署结果。
示例:带环境变量的构建
- name: Build
env:
VITE_API_URL: ${{ secrets.API_URL }}
run: pnpm run build
Netlify 是一个现代化的静态网站托管平台,提供持续部署、表单处理、服务器less 函数等功能。对于 Slidev 项目,Netlify 提供了简单易用的部署方案。
Netlify 的优势
第一步:创建 netlify.toml
在项目根目录创建 netlify.toml 文件:
[build]
command = "npm run build"
publish = "dist"
[[redirects]]
from = "/*"
to = "/index.html"
status = 200
配置说明
command:构建命令,根据您的包管理器调整(npm/pnpm/yarn)publish:构建产物目录,通常是 distredirects:SPA 路由重定向规则,确保所有路由都指向 index.html第二步:连接仓库
netlify.toml 配置第三步:配置环境变量(如需要)
如果构建需要环境变量,在 Netlify 控制台的 "Site settings" > "Environment variables" 中配置。
多分支部署
[build]
command = "npm run build"
publish = "dist"
[context.production]
command = "npm run build -- --base /"
[context.deploy-preview]
command = "npm run build -- --base /preview/"
构建优化
[build]
command = "npm run build"
publish = "dist"
[build.environment]
NODE_VERSION = "20"
PNPM_VERSION = "8"
自定义 Headers
[[headers]]
for = "/*"
[headers.values]
X-Frame-Options = "DENY"
X-XSS-Protection = "1; mode=block"
X-Content-Type-Options = "nosniff"
本地测试
# 安装 Netlify CLI
npm install -g netlify-cli
# 本地测试构建
netlify build
# 本地预览
netlify dev
Vercel 是另一个流行的静态网站托管平台,特别适合前端项目。它由 Next.js 的创建者开发,对现代前端工具链有很好的支持。
Vercel 的优势
第一步:创建 vercel.json
在项目根目录创建 vercel.json 文件:
{
"buildCommand": "npm run build",
"outputDirectory": "dist",
"rewrites": [
{
"source": "/(.*)",
"destination": "/index.html"
}
]
}
配置说明
buildCommand:构建命令outputDirectory:构建产物目录rewrites:SPA 路由重写规则第二步:连接仓库
第三步:配置项目设置
在项目设置中可以配置:
多环境配置
{
"buildCommand": "npm run build",
"outputDirectory": "dist",
"rewrites": [
{
"source": "/(.*)",
"destination": "/index.html"
}
],
"env": {
"NODE_ENV": "production"
}
}
自定义 Headers
{
"headers": [
{
"source": "/(.*)",
"headers": [
{
"key": "X-Content-Type-Options",
"value": "nosniff"
},
{
"key": "X-Frame-Options",
"value": "DENY"
}
]
}
]
}
图片优化
Vercel 自动优化图片,无需额外配置。如果使用 Vercel 的图片优化 API,可以在代码中使用:
// 使用 Vercel 图片优化
const optimizedImage = `https://your-domain.vercel.app/_next/image?url=${encodeURIComponent(imageUrl)}&w=800&q=75`
本地测试
# 安装 Vercel CLI
npm install -g vercel
# 本地开发
vercel dev
# 预览部署
vercel
虽然 Slidev 构建后是静态文件,但在某些场景下,使用 Docker 容器部署仍然有其优势:
tangramor 维护了一个 Slidev 的 Docker 镜像,可以直接使用:
运行容器
docker run -d \
--name slidev \
-p 3030:3030 \
-v $(pwd):/slidev \
-e SLIDEV_THEME=default \
tangramor/slidev:latest
参数说明
-d:后台运行-p 3030:3030:端口映射-v $(pwd):/slidev:挂载当前目录-e SLIDEV_THEME=default:设置主题构建阶段 Dockerfile
# 构建阶段
FROM node:20-alpine AS builder
WORKDIR /app
# 复制依赖文件
COPY package*.json ./
COPY pnpm-lock.yaml ./
# 安装依赖
RUN npm install -g pnpm && pnpm install
# 复制源代码
COPY . .
# 构建
RUN pnpm run build
# 运行阶段
FROM nginx:alpine
# 复制构建产物
COPY /app/dist /usr/share/nginx/html
# 复制 Nginx 配置
COPY nginx.conf /etc/nginx/conf.d/default.conf
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
Nginx 配置(nginx.conf)
server {
listen 80;
server_name localhost;
root /usr/share/nginx/html;
index index.html;
# SPA 路由支持
location / {
try_files $uri $uri/ /index.html;
}
# 静态资源缓存
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg)$ {
expires 1y;
add_header Cache-Control "public, immutable";
}
# Gzip 压缩
gzip on;
gzip_vary on;
gzip_min_length 1024;
gzip_types text/plain text/css text/xml text/javascript application/javascript application/xml+rss application/json;
}
构建和运行
# 构建镜像
docker build -t my-slidev .
# 运行容器
docker run -d -p 8080:80 my-slidev
对于更复杂的部署,可以使用 Docker Compose:
version: '3.8'
services:
slidev:
build: .
ports:
- '8080:80'
volumes:
- ./dist:/usr/share/nginx/html:ro
restart: unless-stopped
environment:
- NGINX_HOST=localhost
- NGINX_PORT=80
使用 Docker Compose
# 启动服务
docker-compose up -d
# 查看日志
docker-compose logs -f
# 停止服务
docker-compose down
健康检查示例
HEALTHCHECK \
CMD curl -f http://localhost/ || exit 1
在部署 Slidev 项目之前,建议检查以下事项:
内容检查
配置检查
性能优化
安全检查
问题 1:资源 404 错误
症状:构建后某些资源(图片、字体等)无法加载
原因:
解决方案:
// vite.config.ts
export default {
base: '/your-base-path/',
assetsInclude: ['**/*.png', '**/*.jpg'],
}
问题 2:路由刷新 404
症状:直接访问子路由返回 404
原因:SPA 路由需要服务器重写规则
解决方案:
netlify.toml 中配置 redirectsvercel.json 中配置 rewrites问题 3:构建产物过大
症状:构建后的文件体积很大,加载缓慢
解决方案:
// vite.config.ts
export default {
build: {
rollupOptions: {
output: {
manualChunks: {
vendor: ['vue', 'vue-router'],
},
},
},
chunkSizeWarningLimit: 1000,
},
}
问题 4:PDF 生成失败
症状:构建 PDF 时出错或超时
原因:
解决方案:
# 确保 Playwright 已安装
npx playwright install
# 增加内存限制
NODE_OPTIONS="--max-old-space-size=4096" slidev build --pdf
问题 5:动画在构建后不工作
症状:本地开发正常,构建后动画失效
原因:可能是构建优化导致的问题
解决方案:
// vite.config.ts
export default {
build: {
cssCodeSplit: false, // 保持 CSS 完整性
},
}
1. 图片优化
2. 代码分割
// vite.config.ts
export default {
build: {
rollupOptions: {
output: {
manualChunks(id) {
if (id.includes('node_modules')) {
return 'vendor'
}
},
},
},
},
}
3. 缓存策略
配置适当的 HTTP 缓存头:
# 静态资源长期缓存
location ~* \.(js|css|png|jpg|jpeg|gif|ico|svg)$ {
expires 1y;
add_header Cache-Control "public, immutable";
}
# HTML 文件不缓存
location ~* \.html$ {
expires -1;
add_header Cache-Control "no-cache, no-store, must-revalidate";
}
4. 预加载关键资源
在 index.html 中添加预加载:
<link rel="preload" href="/assets/main.js" as="script" />
<link rel="preload" href="/assets/main.css" as="style" />
1. 使用 Google Analytics
// 在 slides.md 的 frontmatter 中
---
ga: 'G-XXXXXXXXXX'
---
2. 使用 Vercel Analytics
如果使用 Vercel,可以启用内置分析:
// vercel.json
{
"analytics": {
"id": "your-analytics-id"
}
}
3. 自定义事件追踪
// 在 Slidev 组件中
import { useSlideContext } from '@slidev/client'
const { $slidev } = useSlideContext()
// 追踪幻灯片切换
$slidev.nav.on('changed', (no) => {
// 发送分析事件
gtag('event', 'slide_view', {
slide_number: no,
})
})
Slidev 的部署流程虽然看似简单,但涉及多个环节和平台选择。本文从基础的 SPA 构建开始,深入探讨了 PDF 生成、远程资源打包、多平台托管方案,以及 Docker 容器化部署。每个部署方案都有其适用场景:
无论选择哪种方案,都应该遵循最佳实践,进行充分的测试,并持续优化性能。随着 Slidev 生态的不断发展,部署方案也会越来越完善。希望本文能够帮助您顺利部署 Slidev 演示文稿,让您的精彩内容能够更好地分享给观众。
发表评论
请登录后发表评论
评论 (0)