mirror of
https://github.com/Comfy-Org/ComfyUI_frontend.git
synced 2026-03-02 03:30:04 +00:00
Summary - Add comprehensive telemetry for key UI interactions using existing telemetry hooks (cloud-enabled, no-op in OSS): Sidebar and top-level - Node library button: `node_library` - Model library button: `model_library` - Workflows button: `workflows` - Assets/Media button: `assets` - Templates button: `templates` - Keyboard Shortcuts: `keyboard_shortcuts` - Console: `console` - Help Center: `help_center` - Settings (from Comfy logo menu): `settings_menu` Floating canvas menu - Minimap toggle: `minimap_toggle` - Hide links toggle: `hide_links` Run button and queue - Run button handle (drag): `run_button_handle` - Run mode selection: `run_instant`, `run_on_change` - Queue multiple: `queue_multiple` fires on each run when batch count > 1 (moved from batch-count-change to run-time, per guidance) Error dialogs - Close (X/mask/ESC): `error_dialog_close` via dialog onClose - Show report: `error_show_report` - Help fix this: `error_help_fix_this` - Find issues: `error_find_issues` Nodes / Subgraphs - Selection toolbox “Node info”: `node_info` - Enter subgraph (node header enter): `open_subgraph` - Subgraph breadcrumb navigation: `subgraph_breadcrumb_item` and `subgraph_breadcrumb_root` Settings / Credits / Search - Settings menu button (under Comfy logo): `settings_menu` - Purchase credits (Settings > Credits panel): tracked via existing `trackAddApiCreditButtonClicked` - Purchase credits (Avatar popover Top Up): tracked via existing `trackAddApiCreditButtonClicked` - Debounced search telemetry already present for node search and template filters; left as-is Notes and answers - Error dialog onClose: only fires when the dialog actually closes (X, mask, ESC, or programmatic close). “Show report” and “Help fix this” do not close the dialog; they each emit their own events. - Telemetry is behind the cloud provider; calls are optional (`useTelemetry()?.…`). OSS builds send nothing. Open questions / follow-ups - Primary Run button click: today cloud-only `trackRunButton` exists; we can also emit a UI-level `run` click (`UI_BUTTON_CLICKED` style) alongside it if desired. Confirm preference and I can add it. - Subgraph usage richness: if we want structured analytics (e.g., action, depth, subgraph id, node count), I can add a dedicated provider method and include richer metadata at enter/breadcrumb. - Optional parity: track the Comfy menu’s “Browse Templates” item in addition to the sidebar Templates button. Quality - Ran `pnpm lint:fix` and `pnpm typecheck`; both pass locally. Implementation details - All handlers refactored to named functions where needed; used `void` for intentionally unawaited async calls per lint rules. - Event names kept consistent in `button_id` strings; happy to align to a different naming scheme if you prefer. ┆Issue is synchronized with this [Notion page](https://www.notion.so/PR-6511-feat-telemetry-add-tracking-for-sidebar-run-menu-dialogs-subgraphs-settings-and-cre-29e6d73d365081a1b8b4fdfbbf40e18b) by [Unito](https://www.unito.io) --------- Co-authored-by: Christian Byrne <cbyrne@comfy.org> Co-authored-by: Claude <noreply@anthropic.com>
167 lines
4.2 KiB
Vue
167 lines
4.2 KiB
Vue
<!-- A popover that shows current user information and actions -->
|
|
<template>
|
|
<div class="current-user-popover w-72">
|
|
<!-- User Info Section -->
|
|
<div class="p-3">
|
|
<div class="flex flex-col items-center">
|
|
<UserAvatar
|
|
class="mb-3"
|
|
:photo-url="userPhotoUrl"
|
|
:pt:icon:class="{
|
|
'text-2xl!': !userPhotoUrl
|
|
}"
|
|
size="large"
|
|
/>
|
|
|
|
<!-- User Details -->
|
|
<h3 class="my-0 mb-1 truncate text-lg font-semibold">
|
|
{{ userDisplayName || $t('g.user') }}
|
|
</h3>
|
|
<p v-if="userEmail" class="my-0 truncate text-sm text-muted">
|
|
{{ userEmail }}
|
|
</p>
|
|
</div>
|
|
</div>
|
|
|
|
<div v-if="isActiveSubscription" class="flex items-center justify-between">
|
|
<div class="flex flex-col gap-1">
|
|
<UserCredit text-class="text-2xl" />
|
|
<Button
|
|
:label="$t('subscription.partnerNodesCredits')"
|
|
severity="secondary"
|
|
text
|
|
size="small"
|
|
class="pl-6 p-0 h-auto justify-start"
|
|
:pt="{
|
|
root: {
|
|
class: 'hover:bg-transparent active:bg-transparent'
|
|
}
|
|
}"
|
|
@click="handleOpenPartnerNodesInfo"
|
|
/>
|
|
</div>
|
|
<Button
|
|
:label="$t('credits.topUp.topUp')"
|
|
severity="secondary"
|
|
size="small"
|
|
@click="handleTopUp"
|
|
/>
|
|
</div>
|
|
<SubscribeButton
|
|
v-else
|
|
:label="$t('subscription.subscribeToComfyCloud')"
|
|
size="small"
|
|
variant="gradient"
|
|
@subscribed="handleSubscribed"
|
|
/>
|
|
|
|
<Divider class="my-2" />
|
|
|
|
<Button
|
|
class="justify-start"
|
|
:label="$t('userSettings.title')"
|
|
icon="pi pi-cog"
|
|
text
|
|
fluid
|
|
severity="secondary"
|
|
@click="handleOpenUserSettings"
|
|
/>
|
|
|
|
<Button
|
|
v-if="isActiveSubscription"
|
|
class="justify-start"
|
|
:label="$t(planSettingsLabel)"
|
|
icon="pi pi-receipt"
|
|
text
|
|
fluid
|
|
severity="secondary"
|
|
@click="handleOpenPlanAndCreditsSettings"
|
|
/>
|
|
|
|
<Divider class="my-2" />
|
|
|
|
<Button
|
|
class="justify-start"
|
|
:label="$t('auth.signOut.signOut')"
|
|
icon="pi pi-sign-out"
|
|
text
|
|
fluid
|
|
severity="secondary"
|
|
@click="handleLogout"
|
|
/>
|
|
</div>
|
|
</template>
|
|
|
|
<script setup lang="ts">
|
|
import Button from 'primevue/button'
|
|
import Divider from 'primevue/divider'
|
|
import { onMounted } from 'vue'
|
|
|
|
import UserAvatar from '@/components/common/UserAvatar.vue'
|
|
import UserCredit from '@/components/common/UserCredit.vue'
|
|
import { useCurrentUser } from '@/composables/auth/useCurrentUser'
|
|
import { useFirebaseAuthActions } from '@/composables/auth/useFirebaseAuthActions'
|
|
import SubscribeButton from '@/platform/cloud/subscription/components/SubscribeButton.vue'
|
|
import { useSubscription } from '@/platform/cloud/subscription/composables/useSubscription'
|
|
import { isCloud } from '@/platform/distribution/types'
|
|
import { useTelemetry } from '@/platform/telemetry'
|
|
import { useDialogService } from '@/services/dialogService'
|
|
|
|
const emit = defineEmits<{
|
|
close: []
|
|
}>()
|
|
|
|
const planSettingsLabel = isCloud
|
|
? 'settingsCategories.PlanCredits'
|
|
: 'settingsCategories.Credits'
|
|
|
|
const { userDisplayName, userEmail, userPhotoUrl, handleSignOut } =
|
|
useCurrentUser()
|
|
const authActions = useFirebaseAuthActions()
|
|
const dialogService = useDialogService()
|
|
const { isActiveSubscription, fetchStatus } = useSubscription()
|
|
|
|
const handleOpenUserSettings = () => {
|
|
dialogService.showSettingsDialog('user')
|
|
emit('close')
|
|
}
|
|
|
|
const handleOpenPlanAndCreditsSettings = () => {
|
|
if (isCloud) {
|
|
dialogService.showSettingsDialog('subscription')
|
|
} else {
|
|
dialogService.showSettingsDialog('credits')
|
|
}
|
|
|
|
emit('close')
|
|
}
|
|
|
|
const handleTopUp = () => {
|
|
// Track purchase credits entry from avatar popover
|
|
useTelemetry()?.trackAddApiCreditButtonClicked()
|
|
dialogService.showTopUpCreditsDialog()
|
|
emit('close')
|
|
}
|
|
|
|
const handleOpenPartnerNodesInfo = () => {
|
|
window.open(
|
|
'https://docs.comfy.org/tutorials/api-nodes/overview#api-nodes',
|
|
'_blank'
|
|
)
|
|
emit('close')
|
|
}
|
|
|
|
const handleLogout = async () => {
|
|
await handleSignOut()
|
|
emit('close')
|
|
}
|
|
|
|
const handleSubscribed = async () => {
|
|
await fetchStatus()
|
|
}
|
|
|
|
onMounted(() => {
|
|
void authActions.fetchBalance()
|
|
})
|
|
</script>
|