Skip to content

feat: add BigBlueButton video integration#29483

Draft
rjnevins wants to merge 6 commits into
calcom:mainfrom
rjnevins:bounty/calcom-bigbluebutton-worktree
Draft

feat: add BigBlueButton video integration#29483
rjnevins wants to merge 6 commits into
calcom:mainfrom
rjnevins:bounty/calcom-bigbluebutton-worktree

Conversation

@rjnevins
Copy link
Copy Markdown

Summary

/claim #1985

Adds a BigBlueButton conferencing app integration for Cal.diy.

This implementation:

  • registers a new bigbluebutton app-store package and generated app maps
  • stores BigBlueButton server URL + shared secret in app keys
  • creates signed BigBlueButton create, join, and end API URLs
  • returns an attendee join URL for bookings and stores the moderator password for cancellation/end flow
  • hardens the install endpoint by validating teamId, sanitizing returnTo, selecting only credential IDs, and returning typed HTTP errors

Notes

BigBlueButton is stateless, so this creates meetings at booking time using the signed BBB API instead of trying to pre-schedule rooms inside BBB itself.

Validation

  • git diff --check origin/main..HEAD
  • npx --yes prettier --check packages/app-store/bigbluebutton/api/add.ts packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts

I attempted a full corepack yarn install to run broader checks, but the local runner ran out of disk space during package fetch (ENOSPC).

@github-actions
Copy link
Copy Markdown
Contributor

Welcome to Cal.diy, @rjnevins! Thanks for opening this pull request.

A few things to keep in mind:

  • This is Cal.diy, not Cal.com. Cal.diy is a community-driven, fully open-source fork of Cal.com licensed under MIT. Your changes here will be part of Cal.diy — they will not be deployed to the Cal.com production app.
  • Please review our Contributing Guidelines if you haven't already.
  • Make sure your PR title follows the Conventional Commits format.

A maintainer will review your PR soon. Thanks for contributing!

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 29, 2026

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: d63338ac-343d-4193-a868-7c771763d16c

📥 Commits

Reviewing files that changed from the base of the PR and between f719611 and cbba79f.

📒 Files selected for processing (2)
  • packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts
  • packages/app-store/bigbluebutton/zod.ts
🚧 Files skipped from review as they are similar to previous changes (1)
  • packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts

📝 Walkthrough

Walkthrough

This pull request adds BigBlueButton as a native video conferencing integration to Cal.com. The change includes Zod schemas for credential validation, app metadata with display and configuration properties, an installation API route to add the app as a team or user credential, a VideoApiAdapter implementation handling the complete BigBlueButton meeting lifecycle (create, delete, update), and registration within the app store infrastructure through generated files and seed scripts.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The pull request title clearly and concisely summarizes the main change: adding a BigBlueButton video integration to the Cal.com app store.
Description check ✅ Passed The pull request description is well-related to the changeset, providing clear summary of the BigBlueButton integration implementation, technical approach, and validation steps performed.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

ESLint skipped: no ESLint configuration detected in root package.json. To enable, add eslint to devDependencies.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/app-store/bigbluebutton/_metadata.ts`:
- Around line 17-22: Update the user-facing label in
packages/app-store/bigbluebutton/_metadata.ts to use a translation key instead
of the hardcoded string: replace appData.location.label = "BigBlueButton" with a
lookup of the i18n key (e.g., t('apps.bigbluebutton.label')) and add that
key/value to packages/i18n/locales/en/common.json (for example "apps": {
"bigbluebutton": { "label": "BigBlueButton" }}) so the string flows through the
app i18n system.

In `@packages/app-store/bigbluebutton/api/add.ts`:
- Around line 42-109: The handler in default export (handler) currently performs
credential creation for any HTTP method; add an early guard that only allows
POST: check req.method === "POST" at the top of handler and return
res.status(405).json({ message: "Method Not Allowed" }) (or similar) for other
methods to avoid side effects on GET; keep this check before any authentication,
teamId parsing, or calls to throwIfNotHaveAdminAccessToTeam, getTeamId,
prisma.credential.findFirst, and prisma.credential.create so mutations only
occur on POST.

In `@packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts`:
- Around line 106-117: The persisted join URL currently hardcodes
fullName="Guest" (see joinParams and the url built by buildApiUrl in
VideoApiAdapter.ts) which causes all attendees to appear as "Guest"; remove
fullName from the stored/signed join URL and instead generate/signed the final
join URL per-user using their real display name. Concretely: stop saving a
fully-signed URL that includes fullName in the return payload, change the stored
value to either a join URL template (no fullName) or store only
meetingID/password and the ability to call buildApiUrl on demand, and update
updateMeeting() to regenerate the join URL by calling buildApiUrl(apiUrl,
"join", joinParamsWithProvidedFullName, sharedSecret) when producing a
user-facing link so each attendee’s fullName is injected at join time rather
than reusing the original signed URL.
- Around line 54-57: getBigBlueButtonConfig currently fetches keys by
metadata.slug which ignores the credential this adapter instance was created
for; change it to read keys from the installed credential instead. Replace the
getAppKeysFromSlug(metadata.slug) call in getBigBlueButtonConfig with the call
that fetches keys for the adapter's installed credential (use the credential
identifier available on the adapter instance, e.g., installedCredential.id or
credential.id) and keep the result typed as BigBlueButtonKeys; make the same
replacement for the second occurrence mentioned (lines 71-77) so each adapter
uses its own credential's keys rather than the shared slug-based config.

In `@scripts/seed-app-store.ts`:
- Around line 167-170: Seed the BigBlueButton app only when both
BIGBLUEBUTTON_SERVER_URL and BIGBLUEBUTTON_SHARED_SECRET are set: wrap the
createApp("bigbluebutton", ...) call in a conditional that checks
process.env.BIGBLUEBUTTON_SERVER_URL and process.env.BIGBLUEBUTTON_SHARED_SECRET
are truthy, and skip creation (or log a message) otherwise; update the code
around the createApp invocation so the BigBlueButton entry is only created when
both environment variables exist.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 18fb82d0-f7f8-4ffb-8bb3-c8b0ae7ef3ba

📥 Commits

Reviewing files that changed from the base of the PR and between 180ede2 and fe8170c.

⛔ Files ignored due to path filters (1)
  • packages/app-store/bigbluebutton/static/icon.svg is excluded by !**/*.svg
📒 Files selected for processing (16)
  • packages/app-store/apps.keys-schemas.generated.ts
  • packages/app-store/apps.metadata.generated.ts
  • packages/app-store/apps.schemas.generated.ts
  • packages/app-store/apps.server.generated.ts
  • packages/app-store/bigbluebutton/DESCRIPTION.md
  • packages/app-store/bigbluebutton/_metadata.ts
  • packages/app-store/bigbluebutton/api/add.ts
  • packages/app-store/bigbluebutton/api/index.ts
  • packages/app-store/bigbluebutton/index.ts
  • packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts
  • packages/app-store/bigbluebutton/lib/index.ts
  • packages/app-store/bigbluebutton/package.json
  • packages/app-store/bigbluebutton/zod.ts
  • packages/app-store/bookerApps.metadata.generated.ts
  • packages/app-store/video.adapters.generated.ts
  • scripts/seed-app-store.ts

Comment on lines +17 to +22
appData: {
location: {
linkType: "dynamic",
type: "integrations:bigbluebutton",
label: "BigBlueButton",
},
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Localize the location label.

appData.location.label is a user-facing string, so hardcoding "BigBlueButton" here skips the app’s i18n flow. Please add it to packages/i18n/locales/en/common.json and reference the translated value instead.

As per coding guidelines, "**/*.{ts,tsx,jsx}: Add translations to packages/i18n/locales/en/common.json for all UI strings".

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/app-store/bigbluebutton/_metadata.ts` around lines 17 - 22, Update
the user-facing label in packages/app-store/bigbluebutton/_metadata.ts to use a
translation key instead of the hardcoded string: replace appData.location.label
= "BigBlueButton" with a lookup of the i18n key (e.g.,
t('apps.bigbluebutton.label')) and add that key/value to
packages/i18n/locales/en/common.json (for example "apps": { "bigbluebutton": {
"label": "BigBlueButton" }}) so the string flows through the app i18n system.

Comment thread packages/app-store/bigbluebutton/api/add.ts
Comment on lines +54 to +57
const getBigBlueButtonConfig = async () => {
const appKeys = (await getAppKeysFromSlug(
metadata.slug,
)) as BigBlueButtonKeys;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Read BigBlueButton keys from the installed credential, not from the app slug.

This adapter is created per credential, but getBigBlueButtonConfig() ignores that input and resolves keys by metadata.slug instead. For a non-global app, that collapses every install onto one shared config and can create/end meetings against the wrong BBB server or secret.

Also applies to: 71-77

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts` around lines 54 -
57, getBigBlueButtonConfig currently fetches keys by metadata.slug which ignores
the credential this adapter instance was created for; change it to read keys
from the installed credential instead. Replace the
getAppKeysFromSlug(metadata.slug) call in getBigBlueButtonConfig with the call
that fetches keys for the adapter's installed credential (use the credential
identifier available on the adapter instance, e.g., installedCredential.id or
credential.id) and keep the result typed as BigBlueButtonKeys; make the same
replacement for the second occurrence mentioned (lines 71-77) so each adapter
uses its own credential's keys rather than the shared slug-based config.

Comment thread packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts
Comment thread scripts/seed-app-store.ts Outdated
- Add POST-only method guard to add.ts handler (405 for other methods)
- Remove hardcoded fullName=Guest from stored join URL; updateMeeting now
  generates a per-attendee signed join URL using the real attendee name
- Guard bigbluebutton seed behind BIGBLUEBUTTON_SERVER_URL + BIGBLUEBUTTON_SHARED_SECRET env check
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts`:
- Around line 143-146: Replace the plain Error throw in VideoApiAdapter (the
branch checking meetingID and attendeePassword) with an ErrorWithCode so
structured error handling is preserved: import ErrorWithCode into
VideoApiAdapter.ts and change the throw to something like throw new
ErrorWithCode("BigBlueButton booking reference is missing meeting data",
"BAD_REQUEST") (or another appropriate error code), ensuring the same message is
used; update any surrounding code that expects Error to handle ErrorWithCode if
necessary.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: b58e4317-063e-4e16-a838-92d56d2a7971

📥 Commits

Reviewing files that changed from the base of the PR and between fe8170c and 1495b00.

📒 Files selected for processing (3)
  • packages/app-store/bigbluebutton/api/add.ts
  • packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts
  • scripts/seed-app-store.ts
🚧 Files skipped from review as they are similar to previous changes (2)
  • scripts/seed-app-store.ts
  • packages/app-store/bigbluebutton/api/add.ts

Comment thread packages/app-store/bigbluebutton/lib/VideoApiAdapter.ts
@bandhan-majumder
Copy link
Copy Markdown
Member

please attach a working demo in the description. making it draft til then.

@bandhan-majumder bandhan-majumder marked this pull request as draft June 2, 2026 12:53
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants