zoom-apps-sdk
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseZoom Apps SDK
Zoom Apps SDK
Background reference for web apps that run inside the Zoom client. Prefer first, then route here for Layers API, Collaborate Mode, in-client OAuth, and runtime constraints.
choose-zoom-approach适用于Zoom客户端内运行的Web应用的背景参考文档。建议先使用,之后可在此查阅Layers API、协作模式、客户端内OAuth及运行时约束相关内容。
choose-zoom-approachZoom Apps SDK
Zoom Apps SDK
Build web apps that run inside the Zoom client - meetings, webinars, main client, and Zoom Phone.
Official Documentation: https://developers.zoom.us/docs/zoom-apps/
SDK Reference: https://appssdk.zoom.us/
NPM Package: https://www.npmjs.com/package/@zoom/appssdk
构建可运行于Zoom客户端(会议、网络研讨会、主客户端及Zoom Phone)中的Web应用。
Quick Links
快速链接
New to Zoom Apps? Follow this path:
- Architecture - Frontend/backend pattern, embedded browser, deep linking
- Quick Start - Complete working Express + SDK app
- Running Contexts - Where your app runs (inMeeting, inMainClient, etc.)
- Zoom Apps vs Meeting SDK - Stop mixing app types
- In-Client OAuth - Seamless authorization with PKCE
- API Reference - 100+ SDK methods
- Integrated Index - see the section below in this file
- 5-Minute Runbook - Preflight checks before deep debugging
Reference:
- API Reference - All SDK methods by category
- Events Reference - All SDK event listeners
- Layers API - Immersive and camera mode rendering
- OAuth Reference - OAuth flows for Zoom Apps
- Zoom Mail - Mail plugin integration
Having issues?
- App won't load in Zoom → Check Domain Allowlist below
- SDK errors → Common Issues
- Local dev setup → Debugging Guide
- Version upgrade → Migration Guide
- Forum-derived FAQs → Forum Top Questions
Building immersive experiences?
- Layers Immersive Mode - Custom video layouts
- Camera Mode - Virtual camera overlays
Need help with OAuth? See the zoom-oauth skill for authentication flows.
首次接触Zoom Apps?请遵循以下路径:
- 架构 - 前端/后端模式、嵌入式浏览器、深度链接
- 快速开始 - 完整可运行的Express + SDK应用
- 运行上下文 - 应用运行位置(inMeeting、inMainClient等)
- Zoom Apps vs 会议SDK - 区分不同应用类型
- 客户端内OAuth - 基于PKCE的无缝授权
- API参考 - 100+ SDK方法
- 集成索引 - 见本文档下方对应章节
- 5分钟运行手册 - 深度调试前的预检检查
参考内容:
- API参考 - 按类别划分的所有SDK方法
- 事件参考 - 所有SDK事件监听器
- Layers API - 沉浸式及摄像头模式渲染
- OAuth参考 - Zoom Apps的OAuth流程
- Zoom Mail - 邮件插件集成
遇到问题?
- 应用无法在Zoom中加载 → 检查下方的域名白名单
- SDK错误 → 常见问题
- 本地开发设置 → 调试指南
- 版本升级 → 迁移指南
- 论坛常见问题 → 论坛热门问题
构建沉浸式体验?
- Layers沉浸式模式 - 自定义视频布局
- 摄像头模式 - 虚拟摄像头叠加层
需要OAuth相关帮助? 请查看**zoom-oauth**技能文档了解认证流程。
SDK Overview
SDK概述
The Zoom Apps SDK () provides JavaScript APIs for web apps running in Zoom's embedded browser:
@zoom/appssdk- Context APIs - Get meeting, user, and participant info
- Meeting Actions - Share app, invite participants, open URLs
- Authorization - In-Client OAuth with PKCE (no browser redirect)
- Layers API - Immersive video layouts and camera mode overlays
- Collaborate Mode - Shared app state across participants
- App Communication - Message passing between app instances (main client <-> meeting)
- Media Controls - Virtual backgrounds, camera listing, recording control
- UI Controls - Expand app, notifications, popout
- Events - React to meeting state, participants, sharing, and more
Zoom Apps SDK () 为运行在Zoom嵌入式浏览器中的Web应用提供JavaScript API:
@zoom/appssdk- 上下文API - 获取会议、用户及参会者信息
- 会议操作 - 分享应用、邀请参会者、打开URL
- 授权 - 基于PKCE的客户端内OAuth(无需浏览器重定向)
- Layers API - 沉浸式视频布局及摄像头模式叠加层
- 协作模式 - 跨参会者的共享应用状态
- 应用通信 - 应用实例间的消息传递(主客户端 <-> 会议)
- 媒体控制 - 虚拟背景、摄像头列表、录制控制
- UI控制 - 展开应用、通知、弹出窗口
- 事件 - 响应会议状态、参会者、共享等变化
Prerequisites
前置条件
- Zoom app configured as "Zoom App" type in Marketplace
- OAuth credentials (Client ID + Secret) with Zoom Apps scopes
- Web application (Node.js + Express recommended)
- Your domain whitelisted in Marketplace domain allowlist
- ngrok or HTTPS tunnel for local development
- Node.js 18+ (for the backend server)
- 在Marketplace中配置为**"Zoom App"**类型的应用
- 带有Zoom Apps权限范围的OAuth凭据(Client ID + Secret)
- Web应用(推荐使用Node.js + Express)
- 域名已在Marketplace域名白名单中
- 用于本地开发的ngrok或HTTPS隧道
- Node.js 18+(用于后端服务器)
Quick Start
快速开始
Option A: NPM (Recommended for frameworks)
选项A:NPM(框架推荐使用)
bash
npm install @zoom/appssdkjavascript
import zoomSdk from '@zoom/appssdk';
async function init() {
try {
const configResponse = await zoomSdk.config({
capabilities: [
'shareApp',
'getMeetingContext',
'getUserContext',
'openUrl'
],
version: '0.16'
});
console.log('Running context:', configResponse.runningContext);
// 'inMeeting' | 'inMainClient' | 'inWebinar' | 'inImmersive' | ...
const context = await zoomSdk.getMeetingContext();
console.log('Meeting ID:', context.meetingID);
} catch (error) {
console.error('Not running inside Zoom:', error.message);
showDemoMode();
}
}bash
npm install @zoom/appssdkjavascript
import zoomSdk from '@zoom/appssdk';
async function init() {
try {
const configResponse = await zoomSdk.config({
capabilities: [
'shareApp',
'getMeetingContext',
'getUserContext',
'openUrl'
],
version: '0.16'
});
console.log('Running context:', configResponse.runningContext);
// 'inMeeting' | 'inMainClient' | 'inWebinar' | 'inImmersive' | ...
const context = await zoomSdk.getMeetingContext();
console.log('Meeting ID:', context.meetingID);
} catch (error) {
console.error('Not running inside Zoom:', error.message);
showDemoMode();
}
}Option B: CDN (Vanilla JS)
选项B:CDN(原生JS使用)
html
<script src="https://appssdk.zoom.us/sdk.js"></script>
<script>
// CRITICAL: Do NOT declare "let zoomSdk" - the SDK defines window.zoomSdk globally
// Using "let zoomSdk = ..." causes: SyntaxError: redeclaration of non-configurable global property
let sdk = window.zoomSdk; // Use a different variable name
async function init() {
try {
const configResponse = await sdk.config({
capabilities: ['shareApp', 'getMeetingContext', 'getUserContext'],
version: '0.16'
});
console.log('Running context:', configResponse.runningContext);
} catch (error) {
console.error('Not running inside Zoom:', error.message);
showDemoMode();
}
}
function showDemoMode() {
document.body.innerHTML = '<h1>Preview Mode</h1><p>Open this app inside Zoom to use.</p>';
}
document.addEventListener('DOMContentLoaded', () => {
init();
setTimeout(() => { if (!sdk) showDemoMode(); }, 3000);
});
</script>html
<script src="https://appssdk.zoom.us/sdk.js"></script>
<script>
// 重要:请勿声明"let zoomSdk" - SDK已全局定义window.zoomSdk
// 使用"let zoomSdk = ..."会导致:SyntaxError: redeclaration of non-configurable global property
let sdk = window.zoomSdk; // 使用不同的变量名
async function init() {
try {
const configResponse = await sdk.config({
capabilities: ['shareApp', 'getMeetingContext', 'getUserContext'],
version: '0.16'
});
console.log('Running context:', configResponse.runningContext);
} catch (error) {
console.error('Not running inside Zoom:', error.message);
showDemoMode();
}
}
function showDemoMode() {
document.body.innerHTML = '<h1>预览模式</h1><p>请在Zoom客户端内打开此应用以使用全部功能。</p>';
}
document.addEventListener('DOMContentLoaded', () => {
init();
setTimeout(() => { if (!sdk) showDemoMode(); }, 3000);
});
</script>Critical: Global Variable Conflict
重要提示:全局变量冲突
The CDN script defines globally. Do NOT redeclare it:
window.zoomSdkjavascript
// WRONG - causes SyntaxError in Zoom's embedded browser
let zoomSdk = null;
zoomSdk = window.zoomSdk;
// CORRECT - use different variable name
let sdk = window.zoomSdk;
// ALSO CORRECT - NPM import (no conflict)
import zoomSdk from '@zoom/appssdk';This only applies to the CDN approach. The NPM import creates a module-scoped variable, no conflict.
CDN脚本会全局定义。请勿重新声明它:
window.zoomSdkjavascript
// 错误示例 - 在Zoom嵌入式浏览器中会导致SyntaxError
let zoomSdk = null;
zoomSdk = window.zoomSdk;
// 正确示例 - 使用不同的变量名
let sdk = window.zoomSdk;
// 同样正确 - NPM导入(无冲突)
import zoomSdk from '@zoom/appssdk';此问题仅存在于CDN引入方式。NPM导入会创建模块作用域变量,不会产生冲突。
Browser Preview / Demo Mode
浏览器预览/演示模式
The SDK only functions inside the Zoom client. When accessed in a regular browser:
- exists but
window.zoomSdkthrows an errorsdk.config() - Always implement try/catch with fallback UI
- Add timeout (3 seconds) in case SDK hangs
SDK仅在Zoom客户端内正常工作。在常规浏览器中访问时:
- 存在,但
window.zoomSdk会抛出错误sdk.config() - 务必实现try/catch并提供回退UI
- 添加超时(3秒)以防SDK加载卡顿
URL Whitelisting (Required)
URL白名单(必填)
Your app will NOT load in Zoom unless the domain is whitelisted.
- Go to Zoom Marketplace
- Open your app -> Feature tab
- Under Zoom App, find Add Allow List
- Add your domain (e.g., for production,
yourdomain.comfor dev)xxxxx.ngrok.io
Without this, the Zoom client shows a blank panel with no error message.
除非域名已在白名单中,否则您的应用无法在Zoom中加载。
- 访问Zoom Marketplace
- 打开您的应用 -> 功能标签页
- 在Zoom App下找到添加允许列表
- 添加您的域名(例如生产环境的,开发环境的
yourdomain.com)xxxxx.ngrok.io
如果未配置白名单,Zoom客户端会显示空白面板且无任何错误提示。
OAuth Scopes (Required)
OAuth权限范围(必填)
Capabilities require matching OAuth scopes enabled in Marketplace:
| Capability | Required Scope |
|---|---|
| |
| |
| |
| |
| |
| |
| |
| |
To add scopes: Marketplace -> Your App -> Scopes tab -> Add required scopes.
Missing scopes = capability fails silently or throws error. Users must re-authorize if you add new scopes.
使用对应功能需要在Marketplace中启用匹配的OAuth权限范围:
| 功能 | 所需权限范围 |
|---|---|
| |
| |
| |
| |
| |
| |
| |
| |
添加权限范围: Marketplace -> 您的应用 -> 权限范围标签页 -> 添加所需的权限范围。
缺少权限范围会导致功能静默失败或抛出错误。如果您添加了新的权限范围,用户必须重新授权应用。
Running Contexts
运行上下文
Your app runs in different surfaces within Zoom. The tells you where:
configResponse.runningContext| Context | Surface | Description |
|---|---|---|
| Meeting sidebar | Most common. Full meeting APIs available |
| Main client panel | Home tab. No meeting context APIs |
| Webinar sidebar | Host/panelist. Meeting + webinar APIs |
| Layers API | Full-screen custom rendering |
| Camera mode | Virtual camera overlay |
| Collaborate mode | Shared state context |
| Zoom Phone | Phone call app |
| Team Chat | Chat sidebar |
See Running Contexts for context-specific behavior and APIs.
您的应用可在Zoom内的不同场景中运行。会告知您当前的运行位置:
configResponse.runningContext| 上下文 | 场景 | 描述 |
|---|---|---|
| 会议侧边栏 | 最常见场景,支持所有会议API |
| 主客户端面板 | 首页标签页,无会议上下文API |
| 网络研讨会侧边栏 | 主持人/嘉宾可用,支持会议+网络研讨会API |
| Layers API | 全屏自定义渲染 |
| 摄像头模式 | 虚拟摄像头叠加层 |
| 协作模式 | 共享状态上下文 |
| Zoom Phone | 电话通话应用 |
| 团队聊天 | 聊天侧边栏 |
详情请查看**运行上下文**了解各上下文的特定行为及可用API。
SDK Initialization Pattern
SDK初始化模式
Every Zoom App starts with :
config()javascript
import zoomSdk from '@zoom/appssdk';
const configResponse = await zoomSdk.config({
capabilities: [
// List ALL APIs you will use
'getMeetingContext',
'getUserContext',
'shareApp',
'openUrl',
'authorize',
'onAuthorized'
],
version: '0.16'
});
// configResponse contains:
// {
// runningContext: 'inMeeting',
// clientVersion: '5.x.x',
// unsupportedApis: [] // APIs not supported in this client version
// }Rules:
- MUST be called before any other SDK method
config() - Only capabilities listed in are available
config() - Capabilities must match OAuth scopes in Marketplace
- Check for graceful degradation
unsupportedApis
每个Zoom App都需从开始:
config()javascript
import zoomSdk from '@zoom/appssdk';
const configResponse = await zoomSdk.config({
capabilities: [
// 列出所有您将使用的API
'getMeetingContext',
'getUserContext',
'shareApp',
'openUrl',
'authorize',
'onAuthorized'
],
version: '0.16'
});
// configResponse包含:
// {
// runningContext: 'inMeeting',
// clientVersion: '5.x.x',
// unsupportedApis: [] // 此客户端版本不支持的API
// }规则:
- 必须在调用任何其他SDK方法之前执行
config() - 仅中列出的功能可用
config() - 功能必须与Marketplace中的OAuth权限范围匹配
- 检查以实现优雅降级
unsupportedApis
In-Client OAuth (Summary)
客户端内OAuth(概述)
Best UX for authorization - no browser redirect:
javascript
// 1. Get code challenge from your backend
const { codeChallenge, state } = await fetch('/api/auth/challenge').then(r => r.json());
// 2. Trigger in-client authorization
await zoomSdk.authorize({ codeChallenge, state });
// 3. Listen for authorization result
zoomSdk.addEventListener('onAuthorized', async (event) => {
const { code, state } = event;
// 4. Send code to backend for token exchange
await fetch('/api/auth/token', {
method: 'POST',
body: JSON.stringify({ code, state })
});
});See In-Client OAuth Guide for complete implementation.
最佳授权体验 - 无需浏览器重定向:
javascript
// 1. 从后端获取code challenge
const { codeChallenge, state } = await fetch('/api/auth/challenge').then(r => r.json());
// 2. 触发客户端内授权
await zoomSdk.authorize({ codeChallenge, state });
// 3. 监听授权结果
zoomSdk.addEventListener('onAuthorized', async (event) => {
const { code, state } = event;
// 4. 将code发送至后端以交换令牌
await fetch('/api/auth/token', {
method: 'POST',
body: JSON.stringify({ code, state })
});
});完整实现请查看**客户端内OAuth指南**。
Layers API (Summary)
Layers API(概述)
Build immersive video layouts and camera overlays:
javascript
// Start immersive mode - replaces gallery view
await zoomSdk.runRenderingContext({ view: 'immersive' });
// Position participant video feeds
await zoomSdk.drawParticipant({
participantUUID: 'user-uuid',
x: 0, y: 0, width: 640, height: 480, zIndex: 1
});
// Add overlay images
await zoomSdk.drawImage({
imageData: canvas.toDataURL(),
x: 0, y: 0, width: 1280, height: 720, zIndex: 0
});
// Exit immersive mode
await zoomSdk.closeRenderingContext();See Layers Immersive and Camera Mode.
构建沉浸式视频布局及摄像头叠加层:
javascript
// 启动沉浸式模式 - 替换画廊视图
await zoomSdk.runRenderingContext({ view: 'immersive' });
// 定位参会者视频流
await zoomSdk.drawParticipant({
participantUUID: 'user-uuid',
x: 0, y: 0, width: 640, height: 480, zIndex: 1
});
// 添加叠加图片
await zoomSdk.drawImage({
imageData: canvas.toDataURL(),
x: 0, y: 0, width: 1280, height: 720, zIndex: 0
});
// 退出沉浸式模式
await zoomSdk.closeRenderingContext();详情请查看**Layers沉浸式模式和摄像头模式**。
Environment Variables
环境变量
| Variable | Description | Where to Find |
|---|---|---|
| App client ID | Marketplace -> App -> App Credentials |
| App client secret | Marketplace -> App -> App Credentials |
| OAuth redirect URL | Your server URL + |
| Cookie signing secret | Generate random string |
| Zoom host URL | |
| 变量 | 描述 | 获取位置 |
|---|---|---|
| 应用客户端ID | Marketplace -> 应用 -> 应用凭据 |
| 应用客户端密钥 | Marketplace -> 应用 -> 应用凭据 |
| OAuth重定向URL | 您的服务器URL + |
| Cookie签名密钥 | 生成随机字符串 |
| Zoom主机URL | |
Common APIs
常用API
| API | Description |
|---|---|
| Initialize SDK, request capabilities |
| Get meeting ID, topic, status |
| Get user name, role, participant ID |
| Get current running context |
| List participants |
| Share app screen with participants |
| Open URL in external browser |
| Invite users to open your app |
| Trigger In-Client OAuth |
| Connect to other app instances |
| Send message to connected instances |
| Start Layers API (immersive/camera) |
| Expand/collapse app panel |
| Show notification in Zoom |
| API | 描述 |
|---|---|
| 初始化SDK,请求所需功能 |
| 获取会议ID、主题、状态 |
| 获取用户名、角色、参会者ID |
| 获取当前运行上下文 |
| 列出参会者 |
| 向参会者共享应用屏幕 |
| 在外部浏览器中打开URL |
| 邀请用户打开您的应用 |
| 触发客户端内OAuth |
| 连接到其他应用实例 |
| 向已连接的实例发送消息 |
| 启动Layers API(沉浸式/摄像头模式) |
| 展开/折叠应用面板 |
| 在Zoom中显示通知 |
Complete Documentation Library
完整文档库
Core Concepts
核心概念
- Architecture - Frontend/backend pattern, embedded browser, deep linking, X-Zoom-App-Context
- Running Contexts - All contexts, context-specific APIs, multi-instance communication
- Security - OWASP headers, CSP, cookie security, PKCE, token storage
- 架构 - 前端/后端模式、嵌入式浏览器、深度链接、X-Zoom-App-Context
- 运行上下文 - 所有上下文、各上下文专属API、多实例通信
- 安全 - OWASP头、CSP、数据访问层
Complete Examples
完整示例
- Quick Start - Hello World Express + SDK app
- In-Client OAuth - PKCE authorization flow
- Layers Immersive - Custom video layouts
- Camera Mode - Virtual camera overlays
- Collaborate Mode - Shared state across participants
- Guest Mode - Unauthenticated/authenticated/authorized states
- Breakout Rooms - Room detection and cross-room state
- App Communication - connect + postMessage between instances
- 快速开始 - Hello World极简Express + SDK应用
- 客户端内OAuth - 基于PKCE的授权流程
- Layers沉浸式模式 - Layers API - 沉浸式模式(自定义布局)
- 摄像头模式 - Layers API - 摄像头模式(虚拟摄像头)
- 协作模式 - 协作模式(共享状态)
- 访客模式 - 访客模式(未认证->已授权状态)
- breakout rooms - 分组讨论室集成
- 应用通信 - connect + postMessage实例间通信
Troubleshooting
故障排除
- Common Issues - Quick diagnostics and error codes
- Debugging - Local dev, ngrok, browser preview
- Migration - SDK version upgrade notes
- 常见问题 - 快速诊断及错误代码
- 调试 - 本地开发设置、ngrok、浏览器预览
- 迁移 - SDK版本迁移说明
References
参考文档
- API Reference - All 100+ SDK methods
- Events Reference - All SDK event listeners
- Layers API Reference - Drawing and rendering methods
- OAuth Reference - OAuth flows for Zoom Apps
- Zoom Mail - Mail plugin integration
- API参考 - 全部100+ SDK方法
- 事件参考 - 所有SDK事件
- Layers API参考 - 绘图及渲染方法
- OAuth参考 - Zoom Apps的OAuth流程
- Zoom Mail参考 - Zoom Mail集成
Sample Repositories
示例仓库
Official (by Zoom)
官方(Zoom提供)
| Repository | Type | Last Updated | Status | SDK Version |
|---|---|---|---|---|
| zoomapps-sample-js | Hello World (Vanilla JS) | Dec 2025 | Active | ^0.16.26 |
| zoomapps-advancedsample-react | Advanced (React + Redis) | Oct 2025 | Active | 0.16.0 |
| zoomapps-customlayout-js | Layers API | Nov 2023 | Stale | ^0.16.8 |
| zoomapps-texteditor-vuejs | Collaborate (Vue + Y.js) | Oct 2023 | Stale | ^0.16.7 |
| zoomapps-serverless-vuejs | Serverless (Firebase) | Aug 2024 | Stale | ^0.16.21 |
| zoomapps-cameramode-vuejs | Camera Mode | - | - | - |
| zoomapps-workshop-sample | Workshop | - | - | - |
Recommended for new projects: Use version .
@zoom/appssdk^0.16.26| 仓库 | 类型 | 最后更新时间 | 状态 | SDK版本 |
|---|---|---|---|---|
| zoomapps-sample-js | Hello World(原生JS) | 2025年12月 | 活跃 | ^0.16.26 |
| zoomapps-advancedsample-react | 进阶示例(React + Redis) | 2025年10月 | 活跃 | 0.16.0 |
| zoomapps-customlayout-js | Layers API | 2023年11月 | 已停止维护 | ^0.16.8 |
| zoomapps-texteditor-vuejs | 协作示例(Vue + Y.js) | 2023年10月 | 已停止维护 | ^0.16.7 |
| zoomapps-serverless-vuejs | 无服务器示例(Firebase) | 2024年8月 | 已停止维护 | ^0.16.21 |
| zoomapps-cameramode-vuejs | 摄像头模式 | - | - | - |
| zoomapps-workshop-sample | 研讨会示例 | - | - | - |
新项目推荐: 使用版本。
@zoom/appssdk^0.16.26Community
社区贡献
| Type | Repository | Description |
|---|---|---|
| Library | harvard-edtech/zaccl | Zoom App Complete Connection Library |
Full list: See general/references/community-repos.md
| 类型 | 仓库 | 描述 |
|---|---|---|
| 库 | harvard-edtech/zaccl | Zoom App完整连接库 |
完整列表:请查看general/references/community-repos.md
Learning Path
学习路径
- Start: - Simplest, most up-to-date
zoomapps-sample-js - Advanced: - Comprehensive (In-Client OAuth, Guest Mode, Collaborate)
zoomapps-advancedsample-react - Specialized: Pick based on feature (Layers, Serverless, Camera Mode)
- 入门:- 最简、最新的示例
zoomapps-sample-js - 进阶:- 全面覆盖(客户端内OAuth、访客模式、协作模式)
zoomapps-advancedsample-react - 专项:根据所需功能选择对应示例(Layers、无服务器、摄像头模式)
Critical Gotchas (From Real Development)
关键注意事项(来自实际开发经验)
1. Global Variable Conflict
1. 全局变量冲突
The CDN script defines . Declaring in your code causes . Use or the NPM import.
window.zoomSdklet zoomSdkSyntaxError: redeclaration of non-configurable global propertylet sdk = window.zoomSdkCDN脚本会全局定义。在代码中声明会导致。请使用或NPM导入方式。
window.zoomSdklet zoomSdkSyntaxError: redeclaration of non-configurable global propertylet sdk = window.zoomSdk2. Domain Allowlist
2. 域名白名单
Your app URL must be in the Marketplace domain allowlist. Without it, Zoom shows a blank panel with no error. Also add and any CDN domains you use.
appssdk.zoom.us您的应用URL必须在Marketplace域名白名单中。如果未配置,Zoom会显示空白面板且无任何错误提示。同时需添加及您使用的所有CDN域名。
appssdk.zoom.us3. Capabilities Must Be Listed
3. 必须列出所有功能
Only APIs listed in are available. Calling an unlisted API throws an error. This is also true for event listeners.
config({ capabilities: [...] })仅中列出的API可用。调用未列出的API会抛出错误。事件监听器同样需要列出。
config({ capabilities: [...] })4. SDK Only Works Inside Zoom
4. SDK仅在Zoom客户端内工作
zoomSdk.config()javascript
try { await zoomSdk.config({...}); } catch { showBrowserPreview(); }zoomSdk.config()javascript
try { await zoomSdk.config({...}); } catch { showBrowserPreview(); }5. ngrok URL Changes
5. ngrok URL会变化
Free ngrok URLs change on restart. You must update 4 places in Marketplace: Home URL, Redirect URL, OAuth Allow List, Domain Allow List. Consider ngrok paid plan for stable subdomain.
免费版ngrok URL在重启后会改变。您必须在Marketplace的4个位置更新:主页URL、重定向URL、OAuth允许列表、域名允许列表。考虑使用ngrok付费方案以获取稳定子域名。
6. In-Client OAuth vs Web OAuth
6. 客户端内OAuth优于Web OAuth
Use (In-Client) for best UX - no browser redirect. Only fall back to web redirect for initial install from Marketplace.
zoomSdk.authorize()使用(客户端内)可获得最佳用户体验 - 无需浏览器重定向。仅在从Marketplace首次安装时才需要回退到Web重定向。
zoomSdk.authorize()7. Camera Mode CEF Race Condition
7. 摄像头模式存在CEF竞争条件
Camera mode uses CEF which takes time to initialize. / may fail if called too early. Implement retry with exponential backoff.
drawImagedrawWebView摄像头模式使用CEF,初始化需要时间。如果过早调用/可能会失败。请实现指数退避重试机制。
drawImagedrawWebView8. Cookie Configuration
8. Cookie配置
Zoom's embedded browser requires cookies with and . Without this, sessions break silently.
SameSite=NoneSecure=trueZoom嵌入式浏览器要求Cookie设置和。否则会话会静默失效。
SameSite=NoneSecure=true9. State Validation
9. 状态验证
Always validate the OAuth parameter to prevent CSRF attacks. Generate cryptographically random state, store it, and verify on callback.
state始终验证OAuth的参数以防止CSRF攻击。生成加密随机状态,存储并在回调时验证。
stateResources
资源
- Official docs: https://developers.zoom.us/docs/zoom-apps/
- SDK reference: https://appssdk.zoom.us/
- NPM package: https://www.npmjs.com/package/@zoom/appssdk
- Developer forum: https://devforum.zoom.us/
- GitHub SDK source: https://github.com/zoom/appssdk
Need help? Start with Integrated Index section below for complete navigation.
- 官方文档:https://developers.zoom.us/docs/zoom-apps/
- SDK参考:https://appssdk.zoom.us/
- NPM包:https://www.npmjs.com/package/@zoom/appssdk
- 开发者论坛:https://devforum.zoom.us/
- GitHub SDK源码:https://github.com/zoom/appssdk
需要帮助? 请查看下方的集成索引章节获取完整导航。
Integrated Index
集成索引
This section was migrated from .
SKILL.md此章节迁移自。
SKILL.mdQuick Start Path
快速开始路径
If you're new to Zoom Apps, follow this order:
-
Run preflight checks first -> RUNBOOK.md
-
Read the architecture -> concepts/architecture.md
- Frontend/backend pattern, embedded browser, deep linking
- Understand how Zoom loads and communicates with your app
-
Build your first app -> examples/quick-start.md
- Complete Express + SDK Hello World
- ngrok setup for local development
-
Understand running contexts -> concepts/running-contexts.md
- Where your app runs (inMeeting, inMainClient, inWebinar, etc.)
- Context-specific APIs and limitations
-
Implement OAuth -> examples/in-client-oauth.md
- In-Client OAuth with PKCE (best UX)
- Token exchange and storage
-
Add features -> references/apis.md
- 100+ SDK methods organized by category
- Code examples for each
-
Troubleshoot -> troubleshooting/common-issues.md
- Quick diagnostics for common problems
如果您是Zoom Apps新手,请按以下顺序操作:
-
先运行预检检查 -> RUNBOOK.md
-
阅读架构文档 -> concepts/architecture.md
- 前端/后端模式、嵌入式浏览器、OAuth流程
- 理解Zoom如何加载并与您的应用通信
-
构建您的第一个应用 -> examples/quick-start.md
- 完整的Express + SDK Hello World应用
- 本地开发的ngrok设置
-
了解运行上下文 -> concepts/running-contexts.md
- 应用运行位置(inMeeting、inMainClient、inWebinar等)
- 各上下文专属API及限制
-
实现OAuth -> examples/in-client-oauth.md
- 基于PKCE的客户端内OAuth(最佳体验)
- 令牌交换及存储
-
添加功能 -> references/apis.md
- 按类别划分的100+ SDK方法
- 每个方法的代码示例
-
故障排除 -> troubleshooting/common-issues.md
- 常见问题的快速诊断
Documentation Structure
文档结构
zoom-apps-sdk/
├── SKILL.md # Main skill overview
├── SKILL.md # This file - navigation guide
│
├── concepts/ # Core architectural patterns
│ ├── architecture.md # Frontend/backend, embedded browser, OAuth flow
│ ├── running-contexts.md # Where your app runs + context-specific APIs
│ └── security.md # OWASP headers, CSP, data access layers
│
├── examples/ # Complete working code
│ ├── quick-start.md # Hello World - minimal Express + SDK app
│ ├── in-client-oauth.md # In-Client OAuth with PKCE
│ ├── layers-immersive.md # Layers API - immersive mode (custom layouts)
│ ├── layers-camera.md # Layers API - camera mode (virtual camera)
│ ├── collaborate-mode.md # Collaborate mode (shared state)
│ ├── guest-mode.md # Guest mode (unauthenticated -> authorized)
│ ├── breakout-rooms.md # Breakout room integration
│ └── app-communication.md # connect + postMessage between instances
│
├── troubleshooting/ # Problem solving guides
│ ├── common-issues.md # Quick diagnostics, error codes
│ ├── debugging.md # Local dev setup, ngrok, browser preview
│ └── migration.md # SDK version migration notes
│
└── references/ # Reference documentation
├── apis.md # Complete API reference (100+ methods)
├── events.md # All SDK events
├── layers-api.md # Layers API detailed reference
├── oauth.md # OAuth flows for Zoom Apps
└── zmail-sdk.md # Zoom Mail integrationzoom-apps-sdk/
├── SKILL.md # 主技能概述
├── SKILL.md # 本文档 - 导航指南
│
├── concepts/ # 核心架构模式
│ ├── architecture.md # 前端/后端、嵌入式浏览器、OAuth流程
│ ├── running-contexts.md # 应用运行位置 + 各上下文专属API
│ └── security.md # OWASP头、CSP、数据访问层
│
├── examples/ # 完整可运行代码
│ ├── quick-start.md # Hello World - 极简Express + SDK应用
│ ├── in-client-oauth.md # 基于PKCE的客户端内OAuth
│ ├── layers-immersive.md # Layers API - 沉浸式模式(自定义布局)
│ ├── layers-camera.md # Layers API - 摄像头模式(虚拟摄像头)
│ ├── collaborate-mode.md # 协作模式(共享状态)
│ ├── guest-mode.md # 访客模式(未认证->已授权)
│ ├── breakout-rooms.md # 分组讨论室集成
│ └── app-communication.md # connect + postMessage实例间通信
│
├── troubleshooting/ # 问题解决指南
│ ├── common-issues.md # 快速诊断、错误代码
│ ├── debugging.md # 本地开发设置、ngrok、浏览器预览
│ └── migration.md # SDK版本迁移说明
│
└── references/ # 参考文档
├── apis.md # 完整API参考(100+方法)
├── events.md # 所有SDK事件
├── layers-api.md # Layers API详细参考
├── oauth.md # Zoom Apps的OAuth流程
└── zmail-sdk.md # Zoom Mail集成By Use Case
按使用场景分类
I want to build a basic Zoom App
我想构建基础Zoom App
- Architecture - Understand the pattern
- Quick Start - Build Hello World
- In-Client OAuth - Add authorization
- Security - Required headers
- 架构 - 理解基础模式
- 快速开始 - 构建Hello World
- 客户端内OAuth - 添加授权
- 安全 - 必需的HTTP头
I want immersive video layouts (Layers API)
我想构建沉浸式视频布局(Layers API)
- Layers Immersive - Custom video positions
- Layers API Reference - All drawing methods
- App Communication - Sync layout across participants
- Layers沉浸式模式 - 自定义视频位置
- Layers API参考 - 所有绘图方法
- 应用通信 - 跨参会者同步布局
I want a virtual camera overlay
我想构建虚拟摄像头叠加层
- Camera Mode - Camera mode rendering
- Layers API Reference - Drawing methods
- 摄像头模式 - 摄像头模式渲染
- Layers API参考 - 绘图方法
I want real-time collaboration
我想构建实时协作功能
- Collaborate Mode - Shared state APIs
- App Communication - Instance messaging
- 协作模式 - 共享状态API
- 应用通信 - 实例间消息传递
I want guest/anonymous access
我想支持访客/匿名访问
- Guest Mode - Three authorization states
- In-Client OAuth - promptAuthorize flow
- 访客模式 - 三种授权状态
- 客户端内OAuth - promptAuthorize流程
I want breakout room support
我想支持分组讨论室
- Breakout Rooms - Room detection and state sync
- 分组讨论室 - 房间检测及状态同步
I want to sync between main client and meeting
我想在主客户端和会议间同步数据
- App Communication - connect + postMessage
- Running Contexts - Multi-instance behavior
- 应用通信 - connect + postMessage
- 运行上下文 - 多实例行为
I want serverless deployment
我想进行无服务器部署
- Quick Start - Understand the base pattern first
- Sample: zoomapps-serverless-vuejs - Firebase pattern
- 快速开始 - 先理解基础模式
- 示例:zoomapps-serverless-vuejs - Firebase模式
I want to add Zoom Mail integration
我想集成Zoom Mail
- Zoom Mail Reference - REST API + mail plugins
- Zoom Mail参考 - REST API + 邮件插件
I'm getting errors
我遇到了错误
- Common Issues - Quick diagnostic table
- Debugging - Local dev setup, DevTools
- Migration - Version compatibility
- 常见问题 - 快速诊断表
- 调试指南 - 本地开发设置、开发者工具
- 迁移指南 - 版本兼容性
Most Critical Documents
最关键的文档
1. Architecture (FOUNDATION)
1. 架构(基础)
concepts/architecture.md
Understand how Zoom Apps work: Frontend in embedded browser, backend for OAuth/API, SDK as the bridge. Without this, nothing else makes sense.
concepts/architecture.md
理解Zoom Apps的工作原理:嵌入式浏览器中的前端、用于OAuth/API的后端、作为桥梁的SDK。不理解此内容,其他部分也难以掌握。
2. Quick Start (FIRST APP)
2. 快速开始(第一个应用)
examples/quick-start.md
Complete working code. Get something running before diving into advanced features.
examples/quick-start.md
完整可运行代码。在深入高级功能之前,先让一个简单应用跑起来。
3. Common Issues (MOST COMMON PROBLEMS)
3. 常见问题(最常见问题)
troubleshooting/common-issues.md
90% of Zoom Apps issues are: domain allowlist, global variable conflict, or missing capabilities.
troubleshooting/common-issues.md
90%的Zoom Apps问题都是:域名白名单、全局变量冲突或缺少功能声明。
Key Learnings
核心要点
Critical Discoveries:
关键发现:
-
Global Variable Conflict is the #1 Gotcha
- CDN script defines globally
window.zoomSdk - causes SyntaxError in Zoom's browser
let zoomSdk = ... - Use or NPM import
let sdk = window.zoomSdk
- CDN script defines
-
Domain Allowlist is Non-Negotiable
- App shows blank panel with zero error if domain not whitelisted
- Must include your domain AND AND any CDN domains
appssdk.zoom.us - ngrok URLs change on restart - must update Marketplace each time
-
config() Gates Everything
- Must be called first, must list all capabilities
- Unlisted capabilities throw errors
- Check for client version compatibility
unsupportedApis
-
In-Client OAuth > Web OAuth for UX
- keeps user in Zoom (no browser redirect)
authorize() - Web redirect only needed for initial Marketplace install
- Always implement PKCE (code_verifier + code_challenge)
-
Two App Instances Can Run Simultaneously
- Main client instance + meeting instance
- Use +
connect()to sync between thempostMessage() - Pre-meeting setup in main client, use in meeting
-
Camera Mode Has CEF Quirks
- CEF initialization takes time
- Draw calls may fail if too early
- Use retry with exponential backoff
-
Cookie Settings Matter
- +
SameSite=NonerequiredSecure=true - Without this, sessions silently fail in embedded browser
-
全局变量冲突是头号陷阱
- CDN脚本全局定义
window.zoomSdk - 会在Zoom浏览器中导致SyntaxError
let zoomSdk = ... - 使用或NPM导入
let sdk = window.zoomSdk
- CDN脚本全局定义
-
域名白名单必不可少
- 如果域名未在白名单中,应用会显示空白面板且无任何错误
- 必须包含您的域名、及所有CDN域名
appssdk.zoom.us - ngrok URL重启后会变化 - 每次都必须更新Marketplace
-
config()控制一切
- 必须首先调用,必须列出所有功能
- 未列出的功能会抛出错误
- 检查以确保客户端版本兼容性
unsupportedApis
-
客户端内OAuth的UX优于Web OAuth
- 让用户留在Zoom内(无需浏览器重定向)
authorize() - Web重定向仅在Marketplace首次安装时需要
- 始终实现PKCE(code_verifier + code_challenge)
-
应用可能同时运行两个实例
- 主客户端实例 + 会议实例
- 使用+
connect()同步两者postMessage() - 可在主客户端中进行会前设置,在会议中使用
-
摄像头模式存在CEF特性问题
- CEF初始化需要时间
- 过早调用绘图方法可能失败
- 使用指数退避重试机制
-
Cookie设置至关重要
- 必须设置+
SameSite=NoneSecure=true - 否则会话会在嵌入式浏览器中静默失效
- 必须设置
Quick Reference
快速参考
"App shows blank panel"
"应用显示空白面板"
-> Domain Allowlist - add domain to Marketplace
-> 域名白名单 - 在Marketplace中添加域名
"SyntaxError: redeclaration"
"SyntaxError: redeclaration"
-> Global Variable - use
let sdk = window.zoomSdk-> 全局变量 - 使用
let sdk = window.zoomSdk"config() throws error"
"config()抛出错误"
-> Browser Preview - SDK only works inside Zoom
-> 浏览器预览 - SDK仅在Zoom客户端内工作
"API call fails silently"
"API调用静默失败"
-> OAuth Scopes - add required scopes in Marketplace
-> OAuth权限范围 - 在Marketplace中添加所需权限范围
"How do I implement [feature]?"
"我想实现[功能]怎么办?"
-> API Reference - find the method, check capabilities needed
-> API参考 - 找到对应方法,检查所需功能
"How do I test locally?"
"我如何在本地测试?"
-> Debugging Guide - ngrok + Marketplace config
-> 调试指南 - ngrok + Marketplace配置
Document Version
文档版本
Based on @zoom/appssdk v0.16.x (latest: 0.16.26+)
Happy coding!
Start with Architecture to understand the pattern, then Quick Start to build your first app.
基于**@zoom/appssdk v0.16.x**(最新版本:0.16.26+)
祝您编码愉快!
先从架构开始理解基础模式,然后通过快速开始构建您的第一个应用。