Skip to content

Add Desktop telemetry event sink#12802

Open
benceruleanlu wants to merge 8 commits into
mainfrom
bl/mar-240-frontend-event-sink
Open

Add Desktop telemetry event sink#12802
benceruleanlu wants to merge 8 commits into
mainfrom
bl/mar-240-frontend-event-sink

Conversation

@benceruleanlu

@benceruleanlu benceruleanlu commented Jun 11, 2026

Copy link
Copy Markdown
Member

Summary

  • initialize a Desktop-only telemetry provider in ComfyUI_frontend
  • forward existing typed telemetry events through window.__comfyDesktop2.Telemetry.capture using the existing event names
  • move the Desktop2 bridge typing to the shared ambient types and let run/execution telemetry fire when any provider is registered

Paired change

MAR-240

@coderabbitai

coderabbitai Bot commented Jun 11, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds desktop telemetry: bridge types, a DesktopTelemetryProvider with payload sanitization and many track* methods plus tests, a desktop-only initializer wired into startup, narrows the Desktop2 model-download bridge typing, and removes cloud-only telemetry guards so events emit for all distributions.

Changes

Desktop Telemetry Infrastructure

Layer / File(s) Summary
Type definitions and Desktop2 bridge contract
src/types/index.ts
Defines ComfyDesktop2Bridge and telemetry value types; augments globalThis.Window with optional __comfyDesktop2 and __comfyDesktop2Remote.
DesktopTelemetryProvider implementation
src/platform/telemetry/providers/desktop/DesktopTelemetryProvider.ts
Implements DesktopTelemetryProvider with property sanitization (primitives and primitive arrays only), capture() forwarding to window.__comfyDesktop2?.Telemetry?.capture, and many track* methods covering auth, subscriptions, checkout, topups, surveys, templates/workflows, navigation/search/UI, and execution lifecycle.
DesktopTelemetryProvider tests
src/platform/telemetry/providers/desktop/DesktopTelemetryProvider.test.ts
Vitest suite with mocks for app mode and execution context, validating forwarding, payload sanitization, GA4 naming, and safe no-bridge behavior.
Desktop telemetry initialization
src/platform/telemetry/initDesktopTelemetry.ts, src/main.ts
Adds initDesktopTelemetry() registering DesktopTelemetryProvider in the TelemetryRegistry and dynamically imports/invokes it during startup when __DISTRIBUTION__ === 'desktop'.
Remove isCloud gating from telemetry
src/scripts/ui.ts, src/stores/executionStore.ts
Removes isCloud guards so queue UI handlers and execution success/error handlers call telemetry methods unconditionally (shared-workflow attribution still gated by shareId).
Model download bridge typing
src/platform/missingModel/missingModelDownload.ts
Replaces local ambient typings with exported ComfyDesktop2Bridge, narrows startDesktop2ModelDownload to accept a downloadModel function, and extracts/passes only that function from window.__comfyDesktop2.
CI dist scan update
.github/workflows/ci-dist-telemetry-scan.yaml
Adds a dist scan step that ripgreps dist build artifacts for Desktop telemetry identifiers and fails the job if any matches are found.

Sequence Diagram(s)

sequenceDiagram
  participant AppCode as Application Code
  participant Provider as DesktopTelemetryProvider
  participant Sanitizer as Sanitize Properties
  participant DesktopHost as window.__comfyDesktop2.Telemetry
  
  AppCode->>Provider: trackRunButton() / trackWorkflowImported() / etc.
  Provider->>Sanitizer: filter properties to primitives/arrays
  Sanitizer-->>Provider: sanitized properties
  Provider->>DesktopHost: capture(eventName, sanitizedProperties)
  DesktopHost-->>Provider: (optional response)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

Suggested labels

Electron, area:testing, cloud/1.45

Suggested reviewers

  • christian-byrne
  • AustinMroz
  • comfyui-wiki

Poem

🐰 I hop and tap the telemetry tree,
I prune the props to primitives three,
Desktop hears each little click,
Clean and small — not messy or thick,
Hooray, the rabbit logs with glee!


Important

Pre-merge checks failed

Please resolve all errors before merging. Addressing warnings is optional.

❌ Failed checks (1 warning, 2 inconclusive)

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.
End-To-End Regression Coverage For Fixes ❓ Inconclusive Review context lacks commit subjects and a reliable base...head changed-file list (incl. any browser_tests changes), so bug-fix/E2E-test conditions can’t be evaluated. Share the PR’s full commit subjects and exact base...head changed-file list (especially any under browser_tests/), or add the missing PR-description justification for no E2E regression test.
Description check ❓ Inconclusive PR description provides summary and key objectives but lacks detail on changes, dependencies, and review focus areas as specified in template. Expand description to include detailed 'What' changes, dependency information, critical design decisions, and review focus areas per the template structure.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately describes the main change: adding a Desktop telemetry provider to forward events to the desktop bridge.
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.
Adr Compliance For Entity/Litegraph Changes ✅ Passed PR changed only telemetry/model/type files (per provided diff); no modifications under src/lib/litegraph/, src/ecs/, or graph entities, so ADR entity/litegraph checks are not applicable.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch bl/mar-240-frontend-event-sink

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.

@dosubot dosubot Bot added the size:L This PR changes 100-499 lines, ignoring generated files. label Jun 11, 2026
@github-actions

github-actions Bot commented Jun 11, 2026

Copy link
Copy Markdown

🎭 Playwright: ✅ 1667 passed, 0 failed · 3 flaky

📊 Browser Reports
  • chromium: View Report (✅ 1646 / ❌ 0 / ⚠️ 3 / ⏭️ 5)
  • chromium-2x: View Report (✅ 2 / ❌ 0 / ⚠️ 0 / ⏭️ 0)
  • chromium-0.5x: View Report (✅ 1 / ❌ 0 / ⚠️ 0 / ⏭️ 0)
  • mobile-chrome: View Report (✅ 18 / ❌ 0 / ⚠️ 0 / ⏭️ 0)

@github-actions

github-actions Bot commented Jun 11, 2026

Copy link
Copy Markdown

🎨 Storybook: ✅ Built — View Storybook

Details

⏰ Completed at: 06/12/2026, 06:21:14 PM UTC

Links

coderabbitai[bot]
coderabbitai Bot previously approved these changes Jun 11, 2026
@codecov

codecov Bot commented Jun 11, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 33.10345% with 97 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
...etry/providers/desktop/DesktopTelemetryProvider.ts 26.82% 90 Missing ⚠️
src/scripts/ui.ts 0.00% 4 Missing ⚠️
src/main.ts 0.00% 3 Missing ⚠️
@@             Coverage Diff             @@
##             main   #12802       +/-   ##
===========================================
- Coverage   76.57%   61.57%   -15.01%     
===========================================
  Files        1565     1456      -109     
  Lines      103439    75289    -28150     
  Branches    30579    21254     -9325     
===========================================
- Hits        79212    46360    -32852     
- Misses      23388    28575     +5187     
+ Partials      839      354      -485     
Flag Coverage Δ
e2e ?
unit 61.57% <33.10%> (-0.03%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
src/platform/missingModel/missingModelDownload.ts 97.87% <100.00%> (+18.85%) ⬆️
src/platform/telemetry/initDesktopTelemetry.ts 100.00% <100.00%> (ø)
src/stores/executionStore.ts 89.20% <100.00%> (-1.34%) ⬇️
src/main.ts 0.00% <0.00%> (-68.09%) ⬇️
src/scripts/ui.ts 35.84% <0.00%> (+0.26%) ⬆️
...etry/providers/desktop/DesktopTelemetryProvider.ts 26.82% <26.82%> (ø)

... and 1173 files with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

coderabbitai[bot]
coderabbitai Bot previously approved these changes Jun 12, 2026
coderabbitai[bot]
coderabbitai Bot previously approved these changes Jun 12, 2026
@socket-security

socket-security Bot commented Jun 12, 2026

Copy link
Copy Markdown

No dependency changes detected. Learn more about Socket for GitHub.

👍 No dependency changes detected in pull request

coderabbitai[bot]
coderabbitai Bot previously approved these changes Jun 12, 2026
@jaeone94

Copy link
Copy Markdown
Collaborator

I agree with the goal of routing Desktop-hosted frontend telemetry through the Desktop telemetry pipeline, but I’m concerned about extending window.__comfyDesktop2 before we decide whether it is an official Desktop/FE API surface.

The recent missing-model download work treated this bridge as a pragmatic escape hatch to get off DOM/aria scraping. In particular, Comfy-Desktop#1044 describes the Desktop injection path as a stopgap/backwards-compatibility safety net, and ComfyUI_frontend#12710 lists defining/documenting the FE/Desktop2 bridge contract as follow-up work.

This PR adds telemetry to the same surface. Telemetry is more cross-cutting than missing-model download capability, and once FE starts calling window.__comfyDesktop2.Telemetry.capture, this bridge effectively becomes a stable platform API whether or not we have said so explicitly.

I think we should clarify this before merging:

  • Is window.__comfyDesktop2 intended to be the official Desktop-to-hosted-FE capability bridge?
  • If yes, can we document that contract and add explicit capability detection/versioning, e.g. a capabilities.telemetry flag or equivalent?
  • Can the FE/Desktop bridge type live in a canonical/shared place rather than growing as ad hoc ambient globals?
  • Can the preload bridge remain fire-and-forget/safe if FE accidentally passes non-cloneable telemetry properties?
  • If this bridge is still considered temporary, I think telemetry should wait for the proper native/capability API rather than expanding this surface.

I’m not opposed to a preload-exposed Desktop capability API in principle. My concern is that this PR turns a temporary bridge into a de facto official API without making the ownership, compatibility, and privacy/safety contract explicit.

@christian-byrne christian-byrne left a comment

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.

I don't think desktop is a provider of tele.etry really. Can we just have posthog telemetry provider and have desktop opt in? Then we can remove the duplication. The global window bridge shouldn't exist either

@benceruleanlu

Copy link
Copy Markdown
Member Author

@jaeone94 There is a misunderstanding here.

The "stopgap" described in Comfy-Org/Comfy-Desktop#1044 is comfyContentScript.ts — the executeJavaScript-injected DOM scraper that intercepts download clicks for frontends that predate #12710. That's the backwards-compatibility safety net, and it's slated for deletion once the minimum shipped frontend calls the bridge directly.

window.__comfyDesktop2 is a different thing: it's a standard Electron preload surface, exposed via contextBridge.exposeInMainWorld in src/preload/comfyPreload.ts with every method delegating to ipcRenderer.invoke, attached to the ComfyUI view with contextIsolation: true. FE calling the bridge directly isn't an expansion of the stopgap — it's the replacement for it, per Comfy-Org/Comfy-Desktop#1044's own description.

On your specific questions:

Is window.__comfyDesktop2 the intended official bridge?

Yes. Desktop 2 deliberately ships the stock released frontend — no fork, no --front-end-version override; this has been a hard constraint since development started. A preload-exposed bridge is therefore the only mechanism Electron offers for Desktop capabilities in a hosted page, and it's the same pattern desktop v1 used with window.electronAPI. There is no more-native API to wait for — this is what the "proper native API" looks like. For background on the pattern: https://www.electronjs.org/docs/latest/tutorial/tutorial-preload

Capability detection/versioning: key presence is the capability flag. FE calls window.__comfyDesktop2?.Telemetry?.capture — old Desktop + new FE means the key is absent and FE no-ops; new Desktop + old FE means the key goes unused. A separate capabilities.telemetry flag would be a second source of truth for the same fact. If we ever need a breaking change, explicit versioning is worth adding then; additive optional keys don't require it.

Canonical typing: this PR already moves the bridge type out of the ad-hoc ambient declaration in missingModelDownload.ts into shared ambient types. If we want one definition both repos consume, the natural follow-up is a published types package (as v1 did with @comfyorg/comfyui-electron-types), though that's separate work.

Clone-safety: the FE provider filters properties to primitives and primitive arrays before invoking (toHostTelemetryProperties), and Comfy-Org/Comfy-Desktop#1069 scrubs again on the main side, so non-cloneable values are dropped rather than thrown. The capture call is sync fire-and-forget on the FE side.

On the bridge contract, yes this wasn't documented, I added it to the PR now.

@benceruleanlu

Copy link
Copy Markdown
Member Author

There is an interesting issue, however.

These two statements cannot be true at the same time:

  • There are no telemetry references in the local-git build of frontend
  • Desktop 2 has frontend telemetry, and does not use a desktop fork or DISTRIBUTION === 'desktop'

What we will have to concede here is that the gate on this desktop telemetry provider will hinge on window.__comfyDesktop2?.Telemetry, but that is a telemetry reference in local-git.

@benceruleanlu

Copy link
Copy Markdown
Member Author

@christian-byrne This is the MAR-240 direction (Jacob's EventSink proposal, confirmed with Deep): the frontend keeps the event layer, Desktop registers as the sink and relays to PostHog. Desktop is the relay because it already owns the PostHog client, the person/device identity, and the consent toggle — and the frontend it hosts is the stock build, which ships no telemetry SDK.

"Have desktop opt in" is how this works: Desktop opts in by exposing Telemetry on its preload bridge; the stock frontend feature-detects and forwards, and registers nothing otherwise. A PostHog provider in the FE would be the duplication — a second client with SDK + key in the page, and identity + consent would still have to be passed in through the bridge to land events under the same user.

The bridge is the only channel Electron offers a hosted page short of forking the frontend — same pattern v1 used with window.electronAPI. Its contract is now documented on ComfyDesktop2Bridge in src/types/index.ts.

Agreed the provider surface can be changed to a thin generic-capture refactor as a follow-up, if we want this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size:L This PR changes 100-499 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants