
Zoom Cobrowse Sdk
- 1.4k installs
- 23.1k repo stars
- Updated July 28, 2026
- anthropics/knowledge-work-plugins
zoom-cobrowse-sdk is an agent skill for reference skill for zoom cobrowse sdk. use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote.
About
The zoom-cobrowse-sdk skill is designed for reference skill for Zoom Cobrowse SDK. Use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote. Zoom Cobrowse SDK - Web Development Background reference for collaborative browsing on the web with Zoom Cobrowse SDK. Use this after the support workflow is clear and you need implementation detail. Invoke when the user asks about zoom cobrowse sdk or related SKILL.md workflows.
- Two Roles Pattern - Customer vs Agent architecture.
- Session Lifecycle - PIN generation, connection, reconnection.
- JWT Authentication - SDK Key vs API Key, role_type, claims.
- Distribution Methods - CDN vs npm (BYOP).
- Annotation Tools - Drawing, highlighting, pointer tools.
Zoom Cobrowse Sdk by the numbers
- 1,398 all-time installs (skills.sh)
- +81 installs in the week ending Jul 28, 2026 (Skillselion tracking)
- Ranked #272 of 1,896 Design & UI/UX skills by installs in the Skillselion catalog
- Security screen: MEDIUM risk (skills.sh audit)
- Data as of Jul 28, 2026 (Skillselion catalog sync)
zoom-cobrowse-sdk capabilities & compatibility
- Capabilities
- two roles pattern customer vs agent architectu · session lifecycle pin generation, connection, · jwt authentication sdk key vs api key, role_ty · distribution methods cdn vs npm (byop)
- Use cases
- frontend
What zoom-cobrowse-sdk says it does
Reference skill for Zoom Cobrowse SDK. Use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote assist
Reference skill for Zoom Cobrowse SDK. Use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy ma
npx skills add https://github.com/anthropics/knowledge-work-plugins --skill zoom-cobrowse-sdkAdd your badge
Show developers this skill is listed on Skillselion. Paste this into your README.
| Installs | 1.4k |
|---|---|
| repo stars | ★ 23.1k |
| Security audit | 2 / 3 scanners passed |
| Last updated | July 28, 2026 |
| Repository | anthropics/knowledge-work-plugins ↗ |
How do I reference skill for zoom cobrowse sdk. use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote?
Reference skill for Zoom Cobrowse SDK. Use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote.
Who is it for?
Developers using zoom cobrowse sdk workflows documented in SKILL.md.
Skip if: Skip when the task falls outside zoom-cobrowse-sdk scope or needs a different stack.
When should I use this skill?
User asks about zoom cobrowse sdk or related SKILL.md workflows.
What you get
Completed zoom-cobrowse-sdk workflow with documented commands, files, and expected deliverables.
- Cobrowse session integration
- role-separated JWT auth flow
Files
Zoom Cobrowse SDK - Web Development
Background reference for collaborative browsing on the web with Zoom Cobrowse SDK. Use this after the support workflow is clear and you need implementation detail.
Official Documentation: https://developers.zoom.us/docs/cobrowse-sdk/ API Reference: https://marketplacefront.zoom.us/sdk/cobrowse/ Quickstart Repository: https://github.com/zoom/CobrowseSDK-Quickstart Auth Endpoint Sample: https://github.com/zoom/cobrowsesdk-auth-endpoint-sample
Quick Links
New to Cobrowse SDK? Follow this path:
1. [Get Started Guide](get-started.md) - Complete setup from credentials to first session 2. [Session Lifecycle](concepts/session-lifecycle.md) - Understanding customer and agent flows 3. [JWT Authentication](concepts/jwt-authentication.md) - Token generation and security 4. [Customer Integration](examples/customer-integration.md) - Integrate SDK into your website 5. [Agent Integration](examples/agent-integration.md) - Set up agent portal (iframe or npm)
Core Concepts:
- [Two Roles Pattern](concepts/two-roles-pattern.md) - Customer vs Agent architecture
- [Session Lifecycle](concepts/session-lifecycle.md) - PIN generation, connection, reconnection
- [JWT Authentication](concepts/jwt-authentication.md) - SDK Key vs API Key, role_type, claims
- [Distribution Methods](concepts/distribution-methods.md) - CDN vs npm (BYOP)
Features:
- [Annotation Tools](examples/annotations.md) - Drawing, highlighting, pointer tools
- [Privacy Masking](examples/privacy-masking.md) - Hide sensitive fields from agents
- [Remote Assist](examples/remote-assist.md) - Agent can scroll customer's page
- [Multi-Tab Persistence](examples/multi-tab-persistence.md) - Session continues across tabs
- [BYOP Mode](examples/byop-custom-pin.md) - Bring Your Own PIN with npm integration
Troubleshooting:
- [Common Issues](troubleshooting/common-issues.md) - Quick diagnostics and solutions
- [Error Codes](troubleshooting/error-codes.md) - Complete error reference
- [CORS and CSP](troubleshooting/cors-csp.md) - Cross-origin and security policy configuration
- [Browser Compatibility](troubleshooting/browser-compatibility.md) - Supported browsers and limitations
- [5-Minute Runbook](RUNBOOK.md) - Fast preflight checks before deep debugging
Reference:
- [API Reference](references/api-reference.md) - Complete SDK methods and events
- [Settings Reference](references/settings-reference.md) - All initialization settings
- Integrated Index - see the section below in this file
SDK Overview
The Zoom Cobrowse SDK is a JavaScript library that provides:
- Real-Time Co-Browsing: Agent sees customer's browser activity live
- PIN-Based Sessions: Secure 6-digit PIN for customer-to-agent connection
- Annotation Tools: Drawing, highlighting, vanishing pen, rectangle, color picker
- Privacy Masking: CSS selector-based masking of sensitive form fields
- Remote Assist: Agent can scroll customer's page (with consent)
- Multi-Tab Persistence: Session continues when customer opens new tabs
- Auto-Reconnection: Session recovers from page refresh (2-minute window)
- Session Events: Real-time events for session state changes
- HTTPS Required: Secure connections (HTTP only works on loopback/local development hosts)
- No Plugins: Pure JavaScript, no browser extensions needed
Two Roles Architecture
Cobrowse has two distinct roles, each with different integration patterns:
| Role | role_type | Integration | JWT Required | Purpose |
|---|---|---|---|---|
| Customer | 1 | Website integration (CDN or npm) | Yes | User who shares their browser session |
| Agent | 2 | Iframe (CDN) or npm (BYOP only) | Yes | Support staff who views/assists customer |
Key Insight: Customer and agent use different integration methods but the same JWT authentication pattern.
Read This First (Critical)
For customer/agent demos, treat the PIN from customer SDK event pincode_updated as the only user-facing PIN.
- Show one clearly labeled value in UI (for example, Support PIN).
- Use that same PIN for agent join.
- Do not expose provisional/debug PINs from backend pre-start records to users.
If these rules are ignored, agent desk often fails with Pincode is not found / code 30308.
Typical Production Flow (Most Common)
This is the flow most teams implement first, and what users usually expect in demos:
1. Customer starts session first (role_type=1)
- Backend creates/records session
- Backend returns customer JWT
- Customer SDK starts and receives a PIN
2. Agent joins second (role_type=2)
- Agent enters customer PIN
- Backend validates PIN and session state
- Backend returns agent JWT
- Agent opens Zoom-hosted desk iframe (or custom npm agent UI in BYOP)
If a demo only has one generic "session" user, it is incomplete for real cobrowse operations.
Prerequisites
Platform Requirements
- Supported Browsers:
- Chrome 80+ ✓
- Firefox 78+ ✓
- Safari 14+ ✓
- Edge 80+ ✓
- Internet Explorer ✗ (not supported)
- Network Requirements:
- HTTPS required (HTTP works on loopback/local development hosts only)
- Allow cross-origin requests to
*.zoom.us - CSP headers must allow Zoom domains (see CORS and CSP guide)
- Third-Party Cookies:
- Must enable third-party cookies for refresh reconnection
- Privacy mode may limit certain features
Zoom Account Requirements
1. Zoom Workplace Account with SDK Universal Credit 2. Video SDK App created in Zoom Marketplace 3. Cobrowse SDK Credentials from the app's Cobrowse tab
Note: Cobrowse SDK is a feature of Video SDK (not a separate product).
Credentials Overview
You'll receive 4 credentials from Zoom Marketplace → Video SDK App → Cobrowse tab:
| Credential | Type | Used For | Exposure Safe? |
|---|---|---|---|
| SDK Key | Public | CDN URL, JWT app_key claim | ✓ Yes (client-side) |
| SDK Secret | Private | Sign JWTs | ✗ No (server-side only) |
| API Key | Private | REST API calls (optional) | ✗ No (server-side only) |
| API Secret | Private | REST API calls (optional) | ✗ No (server-side only) |
Critical: SDK Key is public (embedded in CDN URL), but SDK Secret must never be exposed client-side.
Quick Start
Step 1: Get SDK Credentials
1. Go to Zoom Marketplace 2. Open your Video SDK App (or create one) 3. Navigate to the Cobrowse tab 4. Copy your credentials:
- SDK Key
- SDK Secret
- API Key (optional)
- API Secret (optional)
Step 2: Set Up Token Server
Deploy a server-side endpoint to generate JWTs. Use the official sample:
git clone https://github.com/zoom/cobrowsesdk-auth-endpoint-sample.git
cd cobrowsesdk-auth-endpoint-sample
npm install
# Create .env file
cat > .env << EOF
ZOOM_SDK_KEY=your_sdk_key_here
ZOOM_SDK_SECRET=your_sdk_secret_here
PORT=4000
EOF
npm startToken endpoint:
// POST https://YOUR_TOKEN_SERVICE_BASE_URL
{
"role": 1, // 1 = customer, 2 = agent
"userId": "user123",
"userName": "John Doe"
}
// Response
{
"token": "eyJhbGciOiJIUzI1NiIs..."
}Step 3: Customer Side Integration (CDN)
<!DOCTYPE html>
<html>
<head>
<title>Customer - Cobrowse Demo</title>
<script type="module">
const ZOOM_SDK_KEY = 'YOUR_SDK_KEY';
// Load SDK from CDN
(function(r, a, b, f, c, d) {
r[f] = r[f] || { init: function() { r.ZoomCobrowseSDKInitArgs = arguments }};
var fragment = a.createDocumentFragment();
function loadJs(url) {
c = a.createElement(b);
d = a.getElementsByTagName(b)[0];
c["async"] = false;
c.src = url;
fragment.appendChild(c);
}
loadJs(`https://us01-zcb.zoom.us/static/resource/sdk/${ZOOM_SDK_KEY}/js/2.13.2`);
d.parentNode.insertBefore(fragment, d);
})(window, document, "script", "ZoomCobrowseSDK");
</script>
</head>
<body>
<h1>Customer Support</h1>
<button id="cobrowse-btn" disabled>Loading...</button>
<!-- Sensitive fields - will be masked from agent -->
<label>SSN: <input type="text" class="pii-mask" placeholder="XXX-XX-XXXX"></label>
<label>Credit Card: <input type="text" class="pii-mask" placeholder="XXXX-XXXX-XXXX-XXXX"></label>
<script type="module">
let sessionRef = null;
const settings = {
allowAgentAnnotation: true,
allowCustomerAnnotation: true,
piiMask: {
maskCssSelectors: ".pii-mask",
maskType: "custom_input"
}
};
ZoomCobrowseSDK.init(settings, function({ success, session, error }) {
if (success) {
sessionRef = session;
// Listen for PIN code
session.on("pincode_updated", (payload) => {
console.log("PIN Code:", payload.pincode);
// IMPORTANT: this is the PIN agent should use
alert(`Share this PIN with agent: ${payload.pincode}`);
});
// Listen for session events
session.on("session_started", () => console.log("Session started"));
session.on("agent_joined", () => console.log("Agent joined"));
session.on("agent_left", () => console.log("Agent left"));
session.on("session_ended", () => console.log("Session ended"));
document.getElementById("cobrowse-btn").disabled = false;
document.getElementById("cobrowse-btn").innerText = "Start Cobrowse Session";
} else {
console.error("SDK init failed:", error);
}
});
document.getElementById("cobrowse-btn").addEventListener("click", async () => {
// Fetch JWT from your server
const response = await fetch("https://YOUR_TOKEN_SERVICE_BASE_URL", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
role: 1,
userId: "customer_" + Date.now(),
userName: "Customer"
})
});
const { token } = await response.json();
// Start cobrowse session
sessionRef.start({ sdkToken: token });
});
</script>
</body>
</html>Step 4: Agent Side Integration (Iframe)
<!DOCTYPE html>
<html>
<head>
<title>Agent Portal</title>
</head>
<body>
<h1>Agent Portal</h1>
<iframe
id="agent-iframe"
width="1024"
height="768"
allow="autoplay *; camera *; microphone *; display-capture *; geolocation *;"
></iframe>
<script>
async function connectAgent() {
// Fetch JWT from your server
const response = await fetch("https://YOUR_TOKEN_SERVICE_BASE_URL", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
role: 2,
userId: "agent_" + Date.now(),
userName: "Support Agent"
})
});
const { token } = await response.json();
// Load Zoom agent portal
const iframe = document.getElementById("agent-iframe");
iframe.src = `https://us01-zcb.zoom.us/sdkapi/zcb/frame-templates/desk?access_token=${token}`;
}
connectAgent();
</script>
</body>
</html>Step 5: Test the Integration
1. Open two separate browsers (or incognito + normal) 2. Customer browser: Open customer page, click "Start Cobrowse Session" 3. Customer browser: Note the 6-digit PIN displayed 4. Agent browser: Open agent page, enter the PIN code 5. Both browsers: Session connects, agent can see customer's page 6. Test features: Annotations, data masking, remote assist
Key Features
1. Annotation Tools
Both customer and agent can draw on the shared screen:
const settings = {
allowAgentAnnotation: true, // Agent can draw
allowCustomerAnnotation: true // Customer can draw
};Available tools:
- Pen (persistent)
- Vanishing pen (disappears after 4 seconds)
- Rectangle
- Color picker
- Eraser
- Undo/Redo
2. Privacy Masking
Hide sensitive fields from agents using CSS selectors:
const settings = {
piiMask: {
maskType: "custom_input", // Mask specific fields
maskCssSelectors: ".pii-mask, #ssn", // CSS selectors
maskHTMLAttributes: "data-sensitive=true" // HTML attributes
}
};Supported masking:
- Text nodes ✓
- Form inputs ✓
- Select elements ✓
- Images ✗ (not supported)
- Links ✗ (not supported)
3. Remote Assist
Agent can scroll the customer's page:
const settings = {
remoteAssist: {
enable: true,
enableCustomerConsent: true, // Customer must approve
remoteAssistTypes: ['scroll_page'], // Only scroll supported
requireStopConfirmation: false // Confirmation when stopping
}
};4. Multi-Tab Session Persistence
Session continues when customer opens new tabs:
const settings = {
multiTabSessionPersistence: {
enable: true,
stateCookieKey: '$$ZCB_SESSION$$' // Cookie key (base64 encoded)
}
};Session Lifecycle
Customer Flow
1. Load SDK → CDN script loads ZoomCobrowseSDK 2. Initialize → ZoomCobrowseSDK.init(settings, callback) 3. Fetch JWT → Request token from your server (role_type=1) 4. Start Session → session.start({ sdkToken }) 5. PIN Generated → pincode_updated event fires 6. Share PIN → Customer gives 6-digit PIN to agent 7. Agent Joins → agent_joined event fires 8. Session Active → Real-time synchronization begins 9. End Session → session.end() or agent leaves
Agent Flow
1. Fetch JWT → Request token from your server (role_type=2) 2. Load Iframe → Point to Zoom agent portal with token 3. Enter PIN → Agent inputs customer's 6-digit PIN 4. Connect → session_joined event fires 5. View Session → Agent sees customer's browser 6. Use Tools → Annotations, remote assist, zoom 7. Leave Session → Click "Leave Cobrowse" button
Session Recovery (Auto-Reconnect)
When customer refreshes the page:
ZoomCobrowseSDK.init(settings, function({ success, session, error }) {
if (success) {
const sessionInfo = session.getSessionInfo();
// Check if session is recoverable
if (sessionInfo.sessionStatus === 'session_recoverable') {
session.join(); // Auto-rejoin previous session
} else {
// Start new session
session.start({ sdkToken });
}
}
});Recovery window: 2 minutes. After 2 minutes, session ends.
Critical Gotchas and Best Practices
⚠️ CRITICAL: SDK Secret Must Stay Server-Side
Problem: Developers often accidentally embed SDK Secret in frontend code.
Solution:
- ✓ SDK Key → Safe to expose (embedded in CDN URL)
- ✗ SDK Secret → Never expose (use for JWT signing server-side)
// ❌ WRONG - Secret exposed in frontend
const jwt = signJWT(payload, 'YOUR_SDK_SECRET'); // Security risk!
// ✅ CORRECT - Secret stays on server
const response = await fetch('/api/token', {
method: 'POST',
body: JSON.stringify({ role: 1, userId, userName })
});
const { token } = await response.json();SDK Key vs API Key (Different Purposes!)
| Credential | Used For | JWT Claim |
|---|---|---|
| SDK Key | CDN URL, JWT app_key | app_key: "SDK_KEY" |
| API Key | REST API calls (optional) | Not used in JWT |
Common mistake: Using API Key instead of SDK Key in JWT app_key claim.
Session Limits
| Limit | Value | What Happens |
|---|---|---|
| Customers per session | 1 | Error 1012: SESSION_CUSTOMER_COUNT_LIMIT |
| Agents per session | 5 | Error 1013: SESSION_AGENT_COUNT_LIMIT |
| Active sessions per browser | 1 | Error 1004: SESSION_COUNT_LIMIT |
| PIN code length | 10 chars max | Error 1008: SESSION_PIN_INVALID_FORMAT |
Session Timeout Behavior
| Event | Timeout | What Happens |
|---|---|---|
| Agent waiting for customer | 3 minutes | Session ends automatically |
| Page refresh reconnection | 2 minutes | Session ends if not reconnected |
| Reconnection attempts | 2 times max | Session ends after 2 failed attempts |
HTTPS Requirement
Problem: SDK doesn't load on HTTP sites.
Solution:
- Production: Use HTTPS ✓
- Development: Use a loopback host for local HTTP testing ✓
- Development: Use a local HTTPS endpoint with a trusted/self-signed cert if required ✓
Third-Party Cookies Required
Problem: Refresh reconnection doesn't work.
Solution: Enable third-party cookies in browser settings.
Affected scenarios:
- Browser privacy mode
- Safari with "Prevent cross-site tracking" enabled
- Chrome with "Block third-party cookies" enabled
Distribution Method Confusion
| Method | Use Case | Agent Integration | BYOP Required |
|---|---|---|---|
| CDN | Most use cases | Zoom-hosted iframe | No (auto PIN) |
| npm | Custom agent UI, full control | Custom npm integration | Yes (required) |
Key Insight: If you want npm integration, you must use BYOP (Bring Your Own PIN) mode.
Cross-Origin Iframe Handling
Problem: Cobrowse doesn't work in cross-origin iframes.
Solution: Inject SDK snippet into cross-origin iframes:
<script>
const ZOOM_SDK_KEY = "YOUR_SDK_KEY_HERE";
(function(r,a,b,f,c,d){r[f]=r[f]||{init:function(){r.ZoomCobrowseSDKInitArgs=arguments}};
var fragment=a.createDocumentFragment();function loadJs(url) {c=a.createElement(b);d=a.getElementsByTagName(b)[0];c.async=false;c.src=url;fragment.appendChild(c);};
loadJs('https://us01-zcb.zoom.us/static/resource/sdk/${ZOOM_SDK_KEY}/js');d.parentNode.insertBefore(fragment,d);})(window,document,'script','ZoomCobrowseSDK');
</script>Same-origin iframes: No extra setup needed.
Known Limitations
Synchronization Limits
Not synchronized:
- HTML5 Canvas elements
- WebGL content
- Audio and Video elements
- Shadow DOM
- PDF rendered with Canvas
- Web Components
Partially synchronized:
- Drop-down boxes (only selected result)
- Date pickers (only selected result)
- Color pickers (only selected result)
Rendering Limits
- High-resolution images may be compressed
- Different screen sizes may cause CSS media query differences
- Cross-origin images may not render (CORS restrictions)
- Cross-origin fonts may not render (CORS restrictions)
Masking Limits
Supported:
- Text nodes ✓
- Form inputs ✓
- Select elements ✓
Not supported:
<img>elements ✗- Links ✗
Complete Documentation Library
This skill includes comprehensive guides organized by category:
Core Concepts
- [Two Roles Pattern](concepts/two-roles-pattern.md) - Customer vs Agent architecture
- [Session Lifecycle](concepts/session-lifecycle.md) - Complete flow from start to end
- [JWT Authentication](concepts/jwt-authentication.md) - Token structure and signing
- [Distribution Methods](concepts/distribution-methods.md) - CDN vs npm (BYOP)
Examples
- [Customer Integration](examples/customer-integration.md) - Complete customer-side setup
- [Agent Integration](examples/agent-integration.md) - Iframe and npm agent setups
- [Annotations](examples/annotations.md) - Drawing tools configuration
- [Privacy Masking](examples/privacy-masking.md) - Field masking patterns
- [Remote Assist](examples/remote-assist.md) - Agent page control
- [Multi-Tab Persistence](examples/multi-tab-persistence.md) - Cross-tab sessions
- [BYOP Custom PIN](examples/byop-custom-pin.md) - Custom PIN codes
References
- [API Reference](references/api-reference.md) - Complete SDK methods and events
- [Settings Reference](references/settings-reference.md) - All initialization settings
- [Error Codes](references/error-codes.md) - Complete error reference
- [Session Events](references/session-events.md) - All event types
Troubleshooting
- [Common Issues](troubleshooting/common-issues.md) - Quick diagnostics
- [Error Codes](troubleshooting/error-codes.md) - Error code reference
- [CORS and CSP](troubleshooting/cors-csp.md) - Cross-origin configuration
- [Browser Compatibility](troubleshooting/browser-compatibility.md) - Browser support
Resources
- Official Docs: https://developers.zoom.us/docs/cobrowse-sdk/
- API Reference: https://marketplacefront.zoom.us/sdk/cobrowse/
- Quickstart Repo: https://github.com/zoom/CobrowseSDK-Quickstart
- Auth Endpoint Sample: https://github.com/zoom/cobrowsesdk-auth-endpoint-sample
- Dev Forum: https://devforum.zoom.us/
- Developer Blog: https://developers.zoom.us/blog/?category=zoom-cobrowse-sdk
---
Need help? Start with Integrated Index section below for complete navigation.
---
Integrated Index
_This section was migrated from SKILL.md._
Complete navigation guide for all Cobrowse SDK documentation.
Getting Started (Start Here!)
If you're new to Zoom Cobrowse SDK, follow this learning path:
1. [SKILL.md](SKILL.md) - Main overview and quick start 2. [5-Minute Runbook](RUNBOOK.md) - Preflight checks for common failures 3. [Get Started Guide](get-started.md) - Step-by-step setup from credentials to first session 4. [Session Lifecycle](concepts/session-lifecycle.md) - Understand the complete customer and agent flow 5. [Customer Integration](examples/customer-integration.md) - Integrate SDK into your website 6. [Agent Integration](examples/agent-integration.md) - Set up agent portal
Core Concepts
Foundational concepts you need to understand:
- [Two Roles Pattern](concepts/two-roles-pattern.md) - Customer (role_type=1) vs Agent (role_type=2) architecture
- [Session Lifecycle](concepts/session-lifecycle.md) - Complete flow: init → start → PIN → connect → end
- [JWT Authentication](concepts/jwt-authentication.md) - Token structure, signing, SDK Key vs API Key
- [Distribution Methods](concepts/distribution-methods.md) - CDN vs npm (BYOP mode)
Examples and Patterns
Complete working examples for common scenarios:
Session Management
- [Customer Integration](examples/customer-integration.md) - Complete customer-side implementation (CDN and npm)
- [Agent Integration](examples/agent-integration.md) - Iframe and npm agent setup patterns
- [Session Events](examples/session-events.md) - Handle all session lifecycle events
- [Auto-Reconnection](examples/auto-reconnection.md) - Page refresh and session recovery
Features
- [Annotation Tools](examples/annotations.md) - Enable drawing, highlighting, vanishing pen
- [Privacy Masking](examples/privacy-masking.md) - Mask sensitive fields with CSS selectors
- [Remote Assist](examples/remote-assist.md) - Agent can scroll customer's page
- [Multi-Tab Persistence](examples/multi-tab-persistence.md) - Session continues across browser tabs
- [BYOP Custom PIN](examples/byop-custom-pin.md) - Bring Your Own PIN with npm integration
References
Complete API and configuration references:
SDK Reference
- [API Reference](references/api-reference.md) - All SDK methods and interfaces
- ZoomCobrowseSDK.init()
- session.start()
- session.join()
- session.end()
- session.on()
- session.getSessionInfo()
- [Settings Reference](references/settings-reference.md) - All initialization settings
- allowAgentAnnotation
- allowCustomerAnnotation
- piiMask
- remoteAssist
- multiTabSessionPersistence
- [Session Events Reference](references/session-events.md) - All event types
- pincode_updated
- session_started
- session_ended
- agent_joined
- agent_left
- session_error
- session_reconnecting
- remote_assist_started
- remote_assist_stopped
Error Reference
- [Error Codes](references/error-codes.md) - Complete error code reference
- 1001-1017: Session errors
- 2001: Token errors
- 9999: Service errors
Official Documentation
- [Get Started](references/get-started.md) - Official get started documentation (crawled)
- [Features](references/features.md) - Official features documentation (crawled)
- [Authorization](references/authorization.md) - Official JWT authorization docs (crawled)
- [API Documentation](references/api.md) - Crawled API reference docs
Troubleshooting
Quick diagnostics and common issue resolution:
- [Common Issues](troubleshooting/common-issues.md) - Quick fixes for frequent problems
- SDK not loading
- Token generation fails
- Agent can't connect
- Fields not masked
- Session doesn't reconnect after refresh
- [Error Codes](troubleshooting/error-codes.md) - Error code lookup and solutions
- Session start/join failures (1001, 1011, 1016)
- Session limit errors (1002, 1004, 1012, 1013, 1015)
- PIN code errors (1006, 1008, 1009, 1010)
- Token errors (2001)
- [CORS and CSP](troubleshooting/cors-csp.md) - Cross-origin and Content Security Policy setup
- Access-Control-Allow-Origin headers
- Content-Security-Policy headers
- Cross-origin iframe handling
- Same-origin iframe handling
- [Browser Compatibility](troubleshooting/browser-compatibility.md) - Browser requirements and limitations
- Supported browsers (Chrome 80+, Firefox 78+, Safari 14+, Edge 80+)
- Internet Explorer not supported
- Privacy mode limitations
- Third-party cookie requirements
By Use Case
Find documentation by what you're trying to do:
I want to...
Set up cobrowse for the first time:
- Get Started Guide
- JWT Authentication
- Customer Integration
- Agent Integration
Add annotation tools:
- Annotation Tools Example
- [Settings Reference - allowAgentAnnotation](references/settings-reference.md#allowa gentannotation)
- Settings Reference - allowCustomerAnnotation
Hide sensitive data from agents:
- Privacy Masking Example
- Settings Reference - piiMask
Let agents control customer's page:
- Remote Assist Example
- Settings Reference - remoteAssist
Use custom PIN codes:
- BYOP Custom PIN Example
- JWT Authentication - enable_byop
Handle page refreshes:
- Auto-Reconnection Example
- Session Lifecycle - Recovery
Integrate with npm (not CDN):
- BYOP Custom PIN Example
- Distribution Methods
Debug session connection issues:
- Common Issues
- Error Codes
- Session Events - session_error
Configure CORS and CSP headers:
- CORS and CSP Guide
- Browser Compatibility
By Error Code
Quick lookup for error code solutions:
Session Errors
- 1001 (SESSION_START_FAILED) → Error Codes
- 1002 (SESSION_CONNECTING_IN_PROGRESS) → Error Codes
- 1004 (SESSION_COUNT_LIMIT) → Error Codes
- 1011 (SESSION_JOIN_FAILED) → Error Codes
- 1012 (SESSION_CUSTOMER_COUNT_LIMIT) → Error Codes
- 1013 (SESSION_AGENT_COUNT_LIMIT) → Error Codes
- 1015 (SESSION_DUPLICATE_USER) → Error Codes
- 1016 (NETWORK_ERROR) → Error Codes
- 1017 (SESSION_CANCELING_IN_PROGRESS) → Error Codes
PIN Errors
- 1006 (SESSION_JOIN_PIN_NOT_FOUND) → Error Codes
- 1008 (SESSION_PIN_INVALID_FORMAT) → Error Codes
- 1009 (SESSION_START_PIN_REQUIRED) → Error Codes
- 1010 (SESSION_START_PIN_CONFLICT) → Error Codes
Auth Errors
- 2001 (TOKEN_INVALID) → Error Codes
Service Errors
- 9999 (UNDEFINED) → Error Codes
Official Resources
External documentation and samples:
- Official Docs: https://developers.zoom.us/docs/cobrowse-sdk/
- API Reference: https://marketplacefront.zoom.us/sdk/cobrowse/
- Quickstart Repo: https://github.com/zoom/CobrowseSDK-Quickstart
- Auth Endpoint Sample: https://github.com/zoom/cobrowsesdk-auth-endpoint-sample
- Dev Forum: https://devforum.zoom.us/
- Developer Blog: https://developers.zoom.us/blog/?category=zoom-cobrowse-sdk
Documentation Structure
cobrowse-sdk/
├── SKILL.md # Main skill entry point
├── SKILL.md # This file - complete navigation
├── get-started.md # Step-by-step setup guide
│
├── concepts/ # Core concepts
│ ├── two-roles-pattern.md
│ ├── session-lifecycle.md
│ ├── jwt-authentication.md
│ └── distribution-methods.md
│
├── examples/ # Working examples
│ ├── customer-integration.md
│ ├── agent-integration.md
│ ├── annotations.md
│ ├── privacy-masking.md
│ ├── remote-assist.md
│ ├── multi-tab-persistence.md
│ ├── byop-custom-pin.md
│ ├── session-events.md
│ └── auto-reconnection.md
│
├── references/ # API and config references
│ ├── api-reference.md # SDK methods
│ ├── settings-reference.md # Init settings
│ ├── session-events.md # Event types
│ ├── error-codes.md # Error reference
│ ├── get-started.md # Official docs (crawled)
│ ├── features.md # Official docs (crawled)
│ ├── authorization.md # Official docs (crawled)
│ └── api.md # API docs (crawled)
│
└── troubleshooting/ # Problem resolution
├── common-issues.md
├── error-codes.md
├── cors-csp.md
└── browser-compatibility.mdSearch Tips
Find by keyword:
- "annotation" → Annotation Tools
- "mask" or "privacy" → Privacy Masking
- "PIN" or "custom PIN" → BYOP Custom PIN
- "JWT" or "token" → JWT Authentication
- "error" → Error Codes
- "CORS" or "CSP" → CORS and CSP
- "iframe" → Agent Integration
- "npm" → Distribution Methods, BYOP
- "refresh" or "reconnect" → Auto-Reconnection
- "agent" → Agent Integration, Two Roles Pattern
- "customer" → Customer Integration, Two Roles Pattern
---
Not finding what you need? Check the Official Documentation or ask on the Dev Forum.
Environment Variables
- See references/environment-variables.md for standardized
.envkeys and where to find each value.
Distribution Methods
Zoom Cobrowse supports CDN and npm-based integrations, depending on your architecture.
Choose based on:
- how much UI control you need,
- whether you host your own agent experience,
- your deployment and CSP constraints.
See:
- Get Started
- Features (official)
JWT Authentication
Generate Cobrowse JWTs server-side using your SDK key and SDK secret.
Guidelines:
- Never expose SDK secret client-side.
- Issue short-lived tokens.
- Generate different tokens for customer and agent roles.
See:
- Authorization (official)
- Get Started
Session Lifecycle
Typical flow:
1. Initialize SDK on customer and agent pages. 2. Generate role-specific JWT tokens. 3. Customer starts a session and receives a PIN. 4. Agent joins using the PIN. 5. Session events track connected/disconnected/end states.
See:
- Get Started
- Features (official)
Two Roles Pattern
Zoom Cobrowse uses two roles:
role_type=1: customer sessionrole_type=2: agent session
Use separate JWTs for each role and keep token generation on the server.
What Is Usually Created
In most real implementations, you create these objects in order:
1. Customer session record (server-side)
session_id- generated PIN
- status (
active/revoked) - expiry timestamp
2. Customer token (role_type=1)
- used by customer browser SDK to start/share session
3. Agent token (role_type=2)
- created after PIN validation
- used to load agent desk iframe or custom agent UI
PIN Source of Truth
In practice, the PIN you should hand to agents is the value emitted by customer SDK event:
session.on("pincode_updated", ...)
Do not rely on placeholder/provisional PIN values from pre-start backend records for user-facing flows. Always show one clearly labeled PIN in UI (for example, "Support PIN") and reuse that same value in agent links.
Recommended Endpoint Split
POST /api/customer/start-> create session + customer token + PINPOST /api/agent/connect-> validate PIN + issue agent tokenPOST /api/session/revoke-> end sessionGET /api/session/list-> operational visibility
See:
- Get Started
- Authorization (official)
Agent Integration
Agent integration joins an active customer session by PIN using an agent-role token.
See:
- Get Started
- Authorization (official)
Annotation Tools
Enable annotation settings during SDK initialization to allow drawing and highlighting.
See:
- Features (official)
- API (official)
Auto-Reconnection
Implement reconnection handlers for transient network interruptions and refresh scenarios.
See:
- Get Started
- Features (official)
BYOP Custom PIN
Bring Your Own PIN mode lets you control PIN generation/format in your own application flow.
See:
- Authorization (official)
- Get Started
Customer Integration
Customer-side integration should initialize the SDK, fetch a server-generated token, then start a session.
See:
- Get Started
- API (official)
Multi-Tab Persistence
Cobrowse sessions can continue across tabs when configured correctly and browser constraints are met.
See:
- Features (official)
- Get Started
Privacy Masking
Configure masking selectors for sensitive customer fields so agents cannot view protected values.
See:
- Features (official)
- Get Started
Remote Assist
Remote assist allows approved agent interactions (for example, scrolling) during active sessions.
See:
- Features (official)
- API (official)
Session Events
Use SDK session events to track lifecycle transitions and update your UI accordingly.
See:
- API (official)
- Features (official)
Get Started with Zoom Cobrowse SDK
Complete setup guide from credentials to your first cobrowse session.
Overview
In a cobrowse session, there are two roles:
- Customer (role_type=1) – Integrates the SDK into their website
- Agent (role_type=2) – Uses an embedded iframe to interact with the customer
This guide shows you how to set up a customer-initiated session (the most common pattern).
Step 1: Get SDK Credentials
Requirements
1. Zoom Workplace Account with SDK Universal Credit
- See Build platform - create or update account for details
2. Video SDK App in Zoom Marketplace
- Cobrowse SDK is a feature of Video SDK (not a separate product)
Get Your Credentials
1. Access your SDK account web portal:
- In your Zoom Workplace account, go to Advanced > Zoom CPaaS > Manage
2. Click Build App
3. Locate your SDK credentials in the Cobrowse tab
You'll receive 4 credentials:
| Credential | Type | Purpose |
|---|---|---|
| SDK Key | Public | Used in CDN URL and JWT app_key claim |
| SDK Secret | Private | Used to sign JWTs (server-side only) |
| API Key | Private | REST API authentication (optional) |
| API Secret | Private | REST API authentication (optional) |
Save these credentials securely - you'll need them in the next step.
Step 2: Generate JWT Tokens
Both customers and agents require JSON Web Tokens (JWTs) for authentication.
JWT Structure
All JWTs have the same header:
{
"alg": "HS256",
"typ": "JWT"
}The payload differs by role:
Customer JWT payload (role_type=1):
{
"user_id": "user1_customer",
"app_key": "YOUR_SDK_KEY",
"role_type": 1,
"user_name": "customer",
"exp": 1723103759,
"iat": 1723102859
}Agent JWT payload (role_type=2):
{
"user_id": "user2_agent",
"app_key": "YOUR_SDK_KEY",
"role_type": 2,
"user_name": "agent",
"exp": 1723103759,
"iat": 1723102859
}JWT Payload Fields
| Field | Required | Description |
|---|---|---|
app_key | Yes | Your Zoom SDK Key (not API Key) |
role_type | Yes | User role: 1 = customer, 2 = agent |
iat | Yes | Token issue timestamp (epoch) |
exp | Yes | Token expiration timestamp (epoch). Min: 30 minutes, Max: 48 hours |
user_id | Yes | Uniquely identifiable user ID |
user_name | Yes | User name (max 80 characters) |
enable_byop | Optional | Enable Bring Your Own PIN: 1 = yes, 0 or omit = no |
Sign the JWT
Sign the JWT with your SDK Secret (not API Secret):
HMACSHA256(
base64UrlEncode(header) + '.' + base64UrlEncode(payload),
ZOOM_SDK_SECRET
);Set Up a Token Server
CRITICAL: JWT signing must happen server-side to protect your SDK Secret.
Use the official auth endpoint sample:
# Clone the sample
git clone https://github.com/zoom/cobrowsesdk-auth-endpoint-sample.git
cd cobrowsesdk-auth-endpoint-sample
# Install dependencies
npm install
# Create .env file
cat > .env << EOF
ZOOM_SDK_KEY=your_sdk_key_here
ZOOM_SDK_SECRET=your_sdk_secret_here
PORT=4000
EOF
# Start the server
npm startThe server will run on the base URL you configure for your token service.
Token Request:
// POST https://YOUR_TOKEN_SERVICE_BASE_URL
{
"role": 1, // 1 = customer, 2 = agent
"userId": "user123",
"userName": "John Doe"
}
// Response
{
"token": "eyJhbGciOiJIUzI1NiIs..."
}See also: JWT Authentication Concept
Step 3: Integrate the Customer SDK
The customer integrates the Cobrowse SDK into their website using the CDN.
Critical PIN Rule
>
The PIN agents should use comes from customer SDK event pincode_updated.Do not show or rely on provisional PIN values from backend/session placeholders.
In UI, display one explicit value (for example, Support PIN) and pass only that to agent flow.
Load the SDK
Include the SDK snippet in the <head> tag of your HTML page:
<script type="module">
const ZOOM_SDK_KEY = 'YOUR_SDK_KEY';
(function (r, a, b, f, c, d) {
r[f] = r[f] || {
init: function () {
r.ZoomCobrowseSDKInitArgs = arguments;
},
};
var fragment = a.createDocumentFragment();
function loadJs(url) {
c = a.createElement(b);
d = a.getElementsByTagName(b)[0];
c.async = false;
c.src = url;
fragment.appendChild(c);
}
loadJs(
`https://us01-zcb.zoom.us/static/resource/sdk/${ZOOM_SDK_KEY}/js/2.13.2`
);
d.parentNode.insertBefore(fragment, d);
})(window, document, 'script', 'ZoomCobrowseSDK');
</script>SDK Version
Set the SDK VERSION using semantic versioning:
- Fixed version:
js/2.13.2- Use exact version 2.13.2 - Latest patch:
js/2.13.x- Use latest>=2.13.0 and <2.14.0
Current version: 2.13.2 (as of February 2026)
Initialize the SDK
const settings = {
allowCustomerAnnotation: true,
piiMask: { maskType: 'all_input' },
};
ZoomCobrowseSDK.init(settings, function ({ success, session, error }) {
if (success) {
console.log("SDK initialized successfully");
// session object is now available
} else {
console.error("SDK init failed:", error);
}
});Start a Session
// Fetch JWT from your server
const response = await fetch('https://YOUR_TOKEN_SERVICE_BASE_URL', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
role: 1,
userId: 'customer_' + Date.now(),
userName: 'Customer'
})
});
const { token } = await response.json();
// Start cobrowse session
session.start({ sdkToken: token });Complete Customer Example
<!DOCTYPE html>
<html>
<head>
<title>Customer - Cobrowse Support</title>
<script type="module">
const ZOOM_SDK_KEY = 'YOUR_SDK_KEY';
// Load SDK from CDN
(function(r, a, b, f, c, d) {
r[f] = r[f] || { init: function() { r.ZoomCobrowseSDKInitArgs = arguments }};
var fragment = a.createDocumentFragment();
function loadJs(url) {
c = a.createElement(b);
d = a.getElementsByTagName(b)[0];
c["async"] = false;
c.src = url;
fragment.appendChild(c);
}
loadJs(`https://us01-zcb.zoom.us/static/resource/sdk/${ZOOM_SDK_KEY}/js/2.13.2`);
d.parentNode.insertBefore(fragment, d);
})(window, document, "script", "ZoomCobrowseSDK");
</script>
</head>
<body>
<h1>Need Help?</h1>
<button id="cobrowse-btn" disabled>Loading...</button>
<div id="pin-display"></div>
<script type="module">
let sessionRef = null;
const settings = {
allowAgentAnnotation: true,
allowCustomerAnnotation: true,
piiMask: {
maskType: "custom_input",
maskCssSelectors: ".sensitive-field"
}
};
ZoomCobrowseSDK.init(settings, function({ success, session, error }) {
if (success) {
sessionRef = session;
// Listen for PIN code
session.on("pincode_updated", (payload) => {
console.log("PIN Code:", payload.pincode);
// This is the authoritative PIN for agent join
document.getElementById("pin-display").innerHTML =
`<p><strong>Your PIN:</strong> ${payload.pincode}</p>
<p>Share this with your support agent</p>`;
});
// Enable button
document.getElementById("cobrowse-btn").disabled = false;
document.getElementById("cobrowse-btn").innerText = "Start Support Session";
} else {
console.error("SDK init failed:", error);
}
});
// Handle button click
document.getElementById("cobrowse-btn").addEventListener("click", async () => {
try {
// Fetch JWT from your server
const response = await fetch("https://YOUR_TOKEN_SERVICE_BASE_URL", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
role: 1,
userId: "customer_" + Date.now(),
userName: "Customer"
})
});
const { token } = await response.json();
// Start session
sessionRef.start({ sdkToken: token });
} catch (error) {
console.error("Failed to start session:", error);
}
});
</script>
</body>
</html>Step 4: Use Zoom-Hosted Agent Portal
Agents connect to cobrowse sessions by embedding an iframe.
Agent Portal Iframe
<!DOCTYPE html>
<html>
<head>
<title>Agent Portal</title>
</head>
<body>
<h1>Agent Support Portal</h1>
<iframe
id="agent-iframe"
width="1024"
height="768"
src=""
allow="autoplay *; camera *; microphone *; display-capture *; geolocation *;"
></iframe>
<script>
async function connectAgent() {
try {
// Fetch JWT from your server
const response = await fetch("https://YOUR_TOKEN_SERVICE_BASE_URL", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
role: 2,
userId: "agent_" + Date.now(),
userName: "Support Agent"
})
});
const { token } = await response.json();
// Load Zoom agent portal with token
const iframe = document.getElementById("agent-iframe");
iframe.src = `https://us01-zcb.zoom.us/sdkapi/zcb/frame-templates/desk?access_token=${token}`;
} catch (error) {
console.error("Failed to connect agent:", error);
}
}
// Auto-connect on page load
connectAgent();
</script>
</body>
</html>Iframe Permissions
The allow attribute must include these permissions:
autoplay *- Auto-play mediacamera *- Camera accessmicrophone *- Microphone accessdisplay-capture *- Screen capturegeolocation *- Location services
Step 5: Test the Cobrowse SDK
Testing Steps
1. Open two browsers (or use incognito + normal mode):
- Browser A: Customer page
- Browser B: Agent page
2. Customer browser:
- Open customer page
- Click "Start Support Session" button
- Note the 6-digit PIN displayed
3. Agent browser:
- Open agent page
- Enter the PIN code in the iframe
4. Verify connection:
- Agent should now see the customer's browser
- Both sides should show "Connected" status
5. Test features:
- Annotations: Agent can draw on the screen
- Data masking: Masked fields show asterisks for agent
- Remote assist: Agent can scroll the page (if enabled)
6. End session:
- Either side can click "End Session" to terminate
Troubleshooting Test Issues
| Issue | Solution |
|---|---|
| SDK doesn't load | Verify SDK Key is correct in CDN URL |
| PIN not showing | Check browser console for errors |
| Agent can't connect | Verify PIN is correct and session is still active |
| Connection fails | Check HTTPS is being used (or a loopback host for development) |
Step 6: Add Features
Now that you have a working cobrowse session, add features:
Annotation Tools
Enable drawing tools for customer and/or agent:
const settings = {
allowAgentAnnotation: true, // Agent can draw
allowCustomerAnnotation: true // Customer can draw
};See: Annotation Tools Example
Data Masking
Hide sensitive fields from agents:
const settings = {
piiMask: {
maskType: 'custom_input',
maskCssSelectors: '.sensitive-field, #ssn, #credit-card',
maskHTMLAttributes: 'data-sensitive=true'
}
};See: Privacy Masking Example
Remote Assist
Allow agent to scroll the customer's page:
const settings = {
remoteAssist: {
enable: true,
enableCustomerConsent: true, // Customer must approve
remoteAssistTypes: ['scroll_page']
}
};See: Remote Assist Example
Bring Your Own PIN (BYOP)
Use custom PIN codes instead of auto-generated ones:
1. Enable BYOP in JWT payload:
{
"enable_byop": 1,
...
}2. Provide custom PIN when starting session:
session.start({
customPinCode: 'MYPIN123',
sdkToken: token
});See: BYOP Custom PIN Example
Next Steps
- Learn core concepts: Session Lifecycle
- Explore features: Complete documentation index
- Handle errors: Error Codes Reference
- Production checklist: CORS and CSP Configuration
PIN Code Access - Bring Your Own PIN (BYOP)
The Cobrowse SDK supports connecting agents and customers using a PIN code. In the simple example above, Zoom automatically generates a 6-digit PIN code displayed to the customer.
Auto-generated PIN flow: 1. Customer clicks "Start Support Session" 2. Zoom generates 6-digit PIN 3. Customer shares PIN with agent 4. Agent enters PIN to connect
Custom PIN flow (BYOP): 1. Your app generates custom PIN code (1-10 characters, letters/numbers) 2. Pass PIN when starting session: session.start({ customPinCode: 'MYPIN', sdkToken }) 3. Agent enters your custom PIN to connect
BYOP enables:
- Integration with existing support ticket systems
- Use of case/ticket IDs as PINs
- npm integration for custom agent UI
See: Bring Your Own PIN (BYOP) for complete guide.
Resources
- Official Docs: https://developers.zoom.us/docs/cobrowse-sdk/
- API Reference: https://marketplacefront.zoom.us/sdk/cobrowse/
- Quickstart Repo: https://github.com/zoom/CobrowseSDK-Quickstart
- Auth Endpoint Sample: https://github.com/zoom/cobrowsesdk-auth-endpoint-sample
- Dev Forum: https://devforum.zoom.us/
Common Questions
Q: Can I use HTTP instead of HTTPS? A: Only for loopback/local development. Production must use HTTPS.
Q: What's the difference between SDK Key and API Key? A: SDK Key is used in the CDN URL and JWT app_key claim. API Key is for optional REST API calls.
Q: Can multiple agents join the same session? A: Yes, up to 5 agents can join a single customer session.
Q: Does the customer need to install anything? A: No, it's pure JavaScript delivered via CDN. No plugins or extensions needed.
Q: What happens if the customer refreshes the page? A: The session will attempt to automatically reconnect within a 2-minute window.
Q: Can I customize the agent portal UI? A: Not with the iframe approach. For custom UI, use npm integration with BYOP mode.
Cobrowse SDK - API Reference
SDK methods and events.
Initialization
const cobrowse = new ZoomCobrowse(config);Config Options
| Option | Type | Description |
|---|---|---|
sdkKey | string | Your SDK Key |
token | string | JWT token |
features.annotations | boolean | Enable annotations |
masking.selectors | array | CSS selectors to mask |
byop.enabled | boolean | Use custom PINs |
byop.pin | string | Custom PIN value |
Methods
startSession()
Start a cobrowse session.
const session = await cobrowse.startSession();
// Returns: { pin: string, sessionId: string }endSession()
End the current session.
await cobrowse.endSession();pause()
Pause screen sharing.
cobrowse.pause();resume()
Resume screen sharing.
cobrowse.resume();Events
sessionStarted
cobrowse.on('sessionStarted', (session) => {
// session.pin - PIN for agent to join
// session.sessionId - Unique session ID
});agentJoined
cobrowse.on('agentJoined', (agent) => {
// agent.name - Agent display name
// agent.userId - Agent user ID
});agentLeft
cobrowse.on('agentLeft', (agent) => {
// Agent disconnected
});sessionEnded
cobrowse.on('sessionEnded', () => {
// Session terminated
});error
cobrowse.on('error', (error) => {
// error.code - Error code
// error.message - Error description
});Resources
- SDK Reference: https://developers.zoom.us/docs/cobrowse-sdk/sdk-reference/
API Reference
This local reference points to the official Cobrowse API docs.
- API (official)
API (Reference)
Canonical source:
- API (official)
Cobrowse SDK - Authorization
JWT authentication for Cobrowse sessions.
Overview
Both customers and agents require JWTs for authentication. Generate tokens server-side.
JWT Structure
Header
{
"alg": "HS256",
"typ": "JWT"
}Payload
| Claim | Type | Description |
|---|---|---|
user_id | string | Unique user identifier |
app_key | string | Your SDK Key |
role_type | number | 1 = customer, 2 = agent |
user_name | string | Display name |
iat | number | Issued at timestamp |
exp | number | Expiration timestamp |
Strict Claim Names (Important)
Cobrowse token validation is strict. Use these claim names exactly:
user_id(notuser_identity)app_keyrole_typeuser_nameiatexp
Avoid adding unrecognized custom claims unless Zoom docs explicitly support them for your SDK version. If you see Invalid token (code 124), validate claim names first.
Role Types
| Role | Value | Description |
|---|---|---|
| Customer | 1 | User sharing their browser |
| Agent | 2 | Support staff viewing session |
Customer Token Example
const customerPayload = {
user_id: "customer_123",
app_key: "YOUR_SDK_KEY",
role_type: 1,
user_name: "John Customer",
iat: Math.floor(Date.now() / 1000),
exp: Math.floor(Date.now() / 1000) + 3600
};
const token = jwt.sign(customerPayload, SDK_SECRET, { algorithm: 'HS256' });Agent Token Example
const agentPayload = {
user_id: "agent_456",
app_key: "YOUR_SDK_KEY",
role_type: 2,
user_name: "Support Agent",
iat: Math.floor(Date.now() / 1000),
exp: Math.floor(Date.now() / 1000) + 3600
};
const token = jwt.sign(agentPayload, SDK_SECRET, { algorithm: 'HS256' });Security
- Generate tokens server-side only
- Never expose SDK Secret in client code
- Use reasonable expiration times
Resources
- Auth docs: https://developers.zoom.us/docs/cobrowse-sdk/authorize/
Authorization (Reference)
Canonical source:
- Authorization (official)
Zoom Cobrowse SDK Environment Variables
Standard .env keys
| Variable | Required | Used for | Where to find |
|---|---|---|---|
ZOOM_SDK_KEY | Yes | SDK identity | Zoom Marketplace -> Cobrowse/Contact Center SDK app -> App Credentials |
ZOOM_SDK_SECRET | Yes | SDK auth signing | Zoom Marketplace -> Cobrowse/Contact Center SDK app -> App Credentials |
COBROWSE_BASE_URL | Optional | Regional/tenant SDK endpoint override | Cobrowse SDK documentation or tenant provisioning details |
Runtime-only values
ZOOM_COBROWSE_SESSION_TOKEN
If your implementation mints short-lived tokens, store them in memory/cache only.
Notes
- Keep
ZOOM_SDK_SECRETserver-side. - Some samples use aliases (
SDK_KEY,SDK_SECRET); normalize internally.
Error Codes
Use the official Cobrowse docs and API behavior notes for code-level troubleshooting.
- Get Started (official)
- API (official)
Cobrowse SDK - Features
Annotations, masking, and advanced features.
Overview
Cobrowse SDK includes features for privacy, collaboration, and customization.
Annotations
Agents can draw and highlight on the shared screen.
Enable Annotations
const cobrowse = new ZoomCobrowse({
sdkKey: SDK_KEY,
token: token,
features: {
annotations: true
}
});Annotation Tools
| Tool | Description |
|---|---|
| Pointer | Highlight cursor position |
| Draw | Freehand drawing |
| Highlight | Transparent highlight |
| Arrow | Point to elements |
Privacy Masking
Hide sensitive information from agents.
Mask Elements
<!-- Add data attribute to sensitive fields -->
<input type="text" data-cobrowse-mask="true" placeholder="SSN" />
<input type="password" data-cobrowse-mask="true" />
<div data-cobrowse-mask="true">Sensitive content</div>Mask by CSS Selector
const cobrowse = new ZoomCobrowse({
sdkKey: SDK_KEY,
token: token,
masking: {
selectors: [
'.sensitive-data',
'#credit-card-field',
'[data-private]'
]
}
});Bring Your Own PIN (BYOP)
Use your own PIN system instead of Zoom-generated PINs.
const cobrowse = new ZoomCobrowse({
sdkKey: SDK_KEY,
token: token,
byop: {
enabled: true,
pin: 'YOUR_CUSTOM_PIN'
}
});Session Control
End Session
cobrowse.endSession();Pause/Resume
cobrowse.pause();
cobrowse.resume();Events
cobrowse.on('sessionStarted', (session) => {
console.log('Session started:', session.pin);
});
cobrowse.on('agentJoined', (agent) => {
console.log('Agent joined:', agent.name);
});
cobrowse.on('sessionEnded', () => {
console.log('Session ended');
});Resources
- Features docs: https://developers.zoom.us/docs/cobrowse-sdk/add-features/
Features (Reference)
Canonical source:
- Features (official)
Cobrowse SDK - Get Started
Set up collaborative browsing on your website.
Overview
This guide walks through integrating the Cobrowse SDK for customer-initiated sessions.
Prerequisites
1. SDK Universal Credit on your Zoom account 2. SDK Key and Secret 3. Token server for JWT generation
Step 1: Get SDK Credentials
1. In Zoom Workplace, go to Advanced → Zoom CPaaS → Manage 2. Click Build App 3. Locate SDK Key and SDK Secret
Step 2: Set Up Token Server
Generate JWTs server-side to protect your SDK Secret.
const jwt = require('jsonwebtoken');
function generateCobrowseToken(userId, userName, roleType) {
const iat = Math.floor(Date.now() / 1000);
const exp = iat + 3600; // 1 hour
const payload = {
user_id: userId,
app_key: SDK_KEY,
role_type: roleType, // 1 = customer, 2 = agent
user_name: userName,
iat: iat,
exp: exp
};
return jwt.sign(payload, SDK_SECRET, { algorithm: 'HS256' });
}Step 3: Integrate Customer SDK
Add to your website:
<script src="https://cobrowse.zoom.us/sdk.js"></script>
<script>
async function startCobrowse() {
// Get token from your server
const token = await fetch('/api/cobrowse-token').then(r => r.json());
const cobrowse = new ZoomCobrowse({
sdkKey: 'YOUR_SDK_KEY',
token: token.jwt
});
const session = await cobrowse.startSession();
// Display PIN to customer
alert(`Your session PIN: ${session.pin}`);
}
</script>
<button onclick="startCobrowse()">Start Support Session</button>Step 4: Set Up Agent View
Agents join via iframe:
<iframe
src="https://cobrowse.zoom.us/agent?pin={PIN}"
allow="camera; microphone"
></iframe>Next Steps
- Configure privacy masking
- Set up annotations
- Implement Bring Your Own PIN
Resources
- Cobrowse docs: https://developers.zoom.us/docs/cobrowse-sdk/get-started/
Get Started (Reference)
Canonical source:
- Get Started (official)
Session Events Reference
Event names and payload behavior are covered in official Cobrowse API documentation.
- API (official)
Settings Reference
Initialization and runtime settings are documented in the official Cobrowse references.
- Features (official)
- API (official)
Cobrowse 5-Minute Preflight Runbook
Use this before deep debugging. It catches the most common Cobrowse failures quickly.
Skill Doc Standard Note
- Agent-skill standard entrypoint is
SKILL.md. - This runbook is an operational convention (recommended), not a required skill file.
SKILL.mdis also a navigation convention for larger skill docs.
1) Confirm Two-Role Model
- Customer role (
role_type=1) starts session. - Agent role (
role_type=2) joins session.
If your demo only has one generic role, expect broken join behavior.
2) Confirm PIN Source of Truth
- Use customer SDK event
pincode_updatedas the only user-facing PIN. - Agent must join with that same PIN.
- Do not show provisional/debug PIN values from backend records.
Common symptom if wrong: Pincode is not found / error 30308.
3) Confirm JWT Claims
- Sign JWT on backend only.
- Include required claim names exactly (for example
user_id, not custom aliases). - Use SDK Key for SDK token context; keep SDK Secret server-side.
If claim names are wrong, token is rejected before session logic.
4) Confirm Session Order
Recommended sequence: 1. Customer gets customer JWT and starts session. 2. PIN is generated on customer side (pincode_updated). 3. Agent gets agent JWT and joins with that PIN.
Starting agent flow before customer session is active often causes join failures.
5) Confirm Distribution Pattern
- CDN path: customer SDK + Zoom-hosted agent desk iframe.
- npm path: custom integration (BYOP mode required for custom PIN control).
If using npm agent integration without BYOP expectations, flow mismatches happen.
6) Confirm Browser and Security Constraints
- HTTPS required (except loopback/local dev).
- CSP/CORS must allow Zoom domains.
- Third-party cookie/privacy settings can affect reconnect behavior.
Do not treat extension/adblock warnings as root cause until API/session checks fail.
7) Quick Checks (Backend + UI)
- Backend config endpoint returns expected credential flags.
- Customer page shows a single Support PIN from SDK event.
- Agent page join uses same Support PIN and returns actionable response (not generic 404).
Copy/Paste Validation Commands
curl -sS -i "$COBROWSE_BASE_URL/customer"
curl -sS -i "$COBROWSE_BASE_URL/agent"
curl -sS -i "$COBROWSE_BASE_URL/api/config"Expected: customer/agent pages load and config endpoint returns valid JSON flags.
8) Fast Decision Tree
- Invalid token -> check JWT claim names and signing secret.
- Agent cannot find PIN -> wrong PIN source or wrong session order.
- Session drops on refresh -> check reconnection window and browser privacy/cookies.
- Works locally, fails prod -> check HTTPS, CSP/CORS, reverse proxy pathing.
Browser Compatibility
Validate your supported browser matrix and test privacy/cookie constraints that may affect sessions.
See:
- Features (official)
- Get Started
Common Issues
Quick diagnostics for Zoom CoBrowse SDK issues.
- Ensure SDK script/package is loaded.
- Verify role-specific JWT generation on server.
- Validate token expiry and clock skew.
- Confirm session PIN flow between customer and agent.
Docs Links / 404s
Symptom: Official doc links you found are stale or return 404.
Fix:
- Prefer the curated references under
references/(these are meant to stay stable even if external URLs drift). - If you need working code, start from official sample repos referenced by the skill, then adapt to your stack.
Confusing "Who Creates the Session?"
Symptom: You built an "agent creates session" endpoint, but the customer flow seems to actually start the share / generate the PIN.
Fix:
- Treat customer start/share as the action that creates the shareable context (PIN/session), then the agent joins using that PIN/session info.
- Keep your server responsibilities narrow: token minting, optional auditing, and routing; avoid inventing "session creation" semantics that the SDK already owns.
Two PIN Values (Most Common Integration Mistake)
Symptom: UI shows one PIN from backend/session record and another PIN from SDK event, agent gets Pin not found or Cobrowse code not found.
Fix:
- Treat
session.on("pincode_updated")as the authoritative support PIN for agent entry. - Display exactly one primary PIN in UI (label it clearly as "Support PIN").
- Do not surface provisional/debug PINs to users.
- When opening agent page with
?pin=..., prefer freshly generated links and avoid stale bookmarks.
Agent Desk Error 30308 (Pincode is not found)
Symptom: Zoom-hosted agent desk shows:
Cobrowse code not found- error code
30308
Fix:
- Ensure customer session is active and not expired before agent joins.
- Use the latest PIN emitted by
pincode_updated. - If your app restarts or uses in-memory state, persist session/PIN mapping or avoid strict local PIN gating for desk launch.
- Have agent re-enter a fresh PIN from a newly started customer session.
Plain HTML / Express Integration Friction
Symptom: Quickstarts assume Vite/modern build pipeline; your plain HTML/Express adaptation breaks.
Fix:
- Load the SDK exactly as the official snippet expects (script order matters).
- Avoid bundler-only patterns in plain HTML (ESM imports,
import.meta, etc.) unless you add a bundler.
See:
- Get Started
- Get Started (official)
CORS and CSP
For browser integrations:
- allow required Zoom domains in CSP,
- avoid blocking SDK/script origins,
- validate iframe embedding and cross-origin constraints.
See:
- Get Started
- Get Started (official)
Error Codes Troubleshooting
Use official API guidance and startup diagnostics to map error behavior.
See:
- Error Codes Reference
- API (official)
Related skills
Forks & variants (1)
Zoom Cobrowse Sdk has 1 known copy in the catalog totaling 13 installs. They canonicalize to this original listing.
- zoom - 13 installs
FAQ
What does zoom-cobrowse-sdk do?
Reference skill for Zoom Cobrowse SDK. Use after routing to a collaborative-support workflow when implementing browser co-browsing, annotation tools, privacy masking, remote.
When should I use zoom-cobrowse-sdk?
User asks about zoom cobrowse sdk or related SKILL.md workflows.
Is zoom-cobrowse-sdk safe to install?
Review the Security Audits panel on this page before installing in production.