From c6c908c3c8fb827a225ecb4473e9a160fe5bd400 Mon Sep 17 00:00:00 2001 From: Diego Imbert Date: Tue, 1 Jul 2025 11:03:34 +0200 Subject: [PATCH] Highlight assets used in modules --- frontend/src/lib/components/Dev.svelte | 4 ++- .../src/lib/components/FlowBuilder.svelte | 4 ++- .../assets/AssetsDropdownButton.svelte | 31 ++++++++++++++----- frontend/src/lib/components/assets/lib.ts | 5 +++ .../flows/map/FlowModuleSchemaItem.svelte | 19 +++++++++--- frontend/src/lib/components/flows/types.ts | 2 ++ .../components/meltComponents/Popover.svelte | 3 ++ frontend/src/routes/flows/dev/+page.svelte | 4 ++- 8 files changed, 57 insertions(+), 15 deletions(-) diff --git a/frontend/src/lib/components/Dev.svelte b/frontend/src/lib/components/Dev.svelte index 0ee118010f..13bdc5d522 100644 --- a/frontend/src/lib/components/Dev.svelte +++ b/frontend/src/lib/components/Dev.svelte @@ -431,6 +431,7 @@ } const flowStateStore = writable({} as FlowState) + const selectedAssetStore = $state({ val: undefined }) const previewArgsStore = $state({ val: {} }) const scriptEditorDrawer = writable(undefined) @@ -469,7 +470,8 @@ editPanelSize: undefined, payloadData: undefined }), - currentEditor: writable(undefined) + currentEditor: writable(undefined), + selectedAssetStore }) setContext('PropPickerContext', { flowPropPickerConfig: writable(undefined), diff --git a/frontend/src/lib/components/FlowBuilder.svelte b/frontend/src/lib/components/FlowBuilder.svelte index dbeebfa6f7..61642ba056 100644 --- a/frontend/src/lib/components/FlowBuilder.svelte +++ b/frontend/src/lib/components/FlowBuilder.svelte @@ -565,6 +565,7 @@ } const previewArgsStore = $state({ val: initialArgs }) + const selectedAssetStore = $state({ val: undefined }) const scriptEditorDrawer = writable(undefined) const moving = writable<{ id: string } | undefined>(undefined) const history = initHistory(flowStore.val) @@ -603,7 +604,8 @@ customUi, insertButtonOpen, executionCount: writable(0), - flowInputEditorState: flowInputEditorStateStore + flowInputEditorState: flowInputEditorStateStore, + selectedAssetStore }) // Add triggers context store diff --git a/frontend/src/lib/components/assets/AssetsDropdownButton.svelte b/frontend/src/lib/components/assets/AssetsDropdownButton.svelte index e8c103cf12..fd1f45b9fb 100644 --- a/frontend/src/lib/components/assets/AssetsDropdownButton.svelte +++ b/frontend/src/lib/components/assets/AssetsDropdownButton.svelte @@ -8,7 +8,7 @@ import ExploreAssetButton, { assetCanBeExplored } from '../../../routes/(root)/(logged)/assets/ExploreAssetButton.svelte' - import { formatAsset, parseAsset } from './lib' + import { formatAsset, parseAsset, type Asset } from './lib' import DbManagerDrawer from '../DBManagerDrawer.svelte' import { untrack } from 'svelte' import { ResourceService } from '$lib/gen' @@ -16,17 +16,26 @@ import Button from '../common/button/Button.svelte' import Tooltip from '../meltComponents/Tooltip.svelte' import ResourceEditorDrawer from '../ResourceEditorDrawer.svelte' + import type { Placement } from '@floating-ui/core' let { assets: assetsUris, enableChangeAnimation = true, size = 'xs', - noBtnText = false + noBtnText = false, + outline = false, + popoverPlacement = 'bottom-end', + onHoverLi, + disableLiTooltip = false }: { assets: string[] enableChangeAnimation?: boolean size?: 'xs' | '3xs' noBtnText?: boolean + outline?: boolean + popoverPlacement?: Placement + disableLiTooltip?: boolean + onHoverLi?: (asset: Asset, eventType: 'enter' | 'leave') => void } = $props() const assets = $derived(assetsUris.map(parseAsset).filter((x) => !!x) ?? []) @@ -37,7 +46,6 @@ let dbManagerDrawer: DbManagerDrawer | undefined = $state() let resourceEditorDrawer: ResourceEditorDrawer | undefined = $state() let isOpen = $state(false) - let resourceDataCache: Record = $state({}) $effect(() => { @@ -73,18 +81,21 @@
{#each assets as asset} {#if asset} -
  • - +
  • onHoverLi?.(asset, 'enter')} + onmouseleave={() => onHoverLi?.(asset, 'leave')} + > + {formatAsset(asset)} {formatAsset(asset)} diff --git a/frontend/src/lib/components/assets/lib.ts b/frontend/src/lib/components/assets/lib.ts index 5f6aa94e1c..bf52a594c5 100644 --- a/frontend/src/lib/components/assets/lib.ts +++ b/frontend/src/lib/components/assets/lib.ts @@ -24,3 +24,8 @@ export function getAssetUsagePageUri(usage: ListAssetsResponse[number]['usages'] return `/flows/get/${usage.usage_path}` } } + +export function assetEquals(a: Asset | undefined, b: Asset | undefined): boolean { + if (!a || !b) return a === b + return a.kind === b.kind && a.path === b.path +} diff --git a/frontend/src/lib/components/flows/map/FlowModuleSchemaItem.svelte b/frontend/src/lib/components/flows/map/FlowModuleSchemaItem.svelte index 7934742c13..793b02ceb2 100644 --- a/frontend/src/lib/components/flows/map/FlowModuleSchemaItem.svelte +++ b/frontend/src/lib/components/flows/map/FlowModuleSchemaItem.svelte @@ -42,7 +42,7 @@ import ModuleTest from '$lib/components/ModuleTest.svelte' import { getStepHistoryLoaderContext } from '$lib/components/stepHistoryLoader.svelte' import AssetsDropdownButton from '$lib/components/assets/AssetsDropdownButton.svelte' - import { formatAsset } from '$lib/components/assets/lib' + import { assetEquals, formatAsset } from '$lib/components/assets/lib' interface Props { selected?: boolean @@ -115,7 +115,7 @@ const flowEditorContext = getContext('FlowEditorContext') const flowInputsStore = flowEditorContext?.flowInputsStore - + const selectedAssetStore = flowEditorContext?.selectedAssetStore const dispatch = createEventDispatcher() const propPickerContext = getContext('PropPickerContext') @@ -143,6 +143,7 @@ let flowStateStore = $derived(flowEditorContext?.flowStateStore) let assets = $derived(id ? $flowStateStore?.[id]?.assetsCache : undefined) + let containsSelectedAsset = $derived(assets?.some((a) => assetEquals(a, selectedAssetStore?.val))) let stepHistoryLoader = getStepHistoryLoaderContext() @@ -467,7 +468,10 @@ {#if !action}
    {#if deletable && (hover || selected) && outputPickerVisible}
    @@ -515,13 +519,20 @@ {/if}
    {/if} - {#if assets?.length && (hover || selected)} + {#if assets?.length && (hover || selected || containsSelectedAsset)}
    { + if (selectedAssetStore) + selectedAssetStore.val = eventType === 'enter' ? asset : undefined + }} />
    {/if} diff --git a/frontend/src/lib/components/flows/types.ts b/frontend/src/lib/components/flows/types.ts index 475ca10fc4..e8cc155827 100644 --- a/frontend/src/lib/components/flows/types.ts +++ b/frontend/src/lib/components/flows/types.ts @@ -8,6 +8,7 @@ import type Editor from '../Editor.svelte' import type SimpleEditor from '../SimpleEditor.svelte' import type { StateStore } from '$lib/utils' import type { TestSteps } from './testSteps.svelte' +import type { Asset } from '../assets/lib' export type FlowInput = Record< string, @@ -78,4 +79,5 @@ export type FlowEditorContext = { customUi: FlowBuilderWhitelabelCustomUi insertButtonOpen: Writable executionCount: Writable + selectedAssetStore: StateStore } diff --git a/frontend/src/lib/components/meltComponents/Popover.svelte b/frontend/src/lib/components/meltComponents/Popover.svelte index a197592902..f889836c61 100644 --- a/frontend/src/lib/components/meltComponents/Popover.svelte +++ b/frontend/src/lib/components/meltComponents/Popover.svelte @@ -17,6 +17,7 @@ import { Button } from '$lib/components/common' import DocLink from '$lib/components/apps/editor/settingsPanel/DocLink.svelte' import type { FloatingConfig } from '@melt-ui/svelte/internal/actions/floating' + import type { EscapeBehaviorType } from '@melt-ui/svelte/internal/actions' export let closeButton: boolean = false export let displayArrow: boolean = false @@ -35,6 +36,7 @@ export let disabled: boolean = false export let documentationLink: string | undefined = undefined export let disableFocusTrap: boolean = false + export let escapeBehavior: EscapeBehaviorType = 'close' let fullScreen = false const dispatch = createEventDispatcher() @@ -48,6 +50,7 @@ forceVisible: true, portal, disableFocusTrap, + escapeBehavior, onOpenChange: ({ curr, next }) => { if (curr != next) { dispatch('openChange', next) diff --git a/frontend/src/routes/flows/dev/+page.svelte b/frontend/src/routes/flows/dev/+page.svelte index 9c16ff9a66..4eac08ce40 100644 --- a/frontend/src/routes/flows/dev/+page.svelte +++ b/frontend/src/routes/flows/dev/+page.svelte @@ -68,6 +68,7 @@ let initialCode = JSON.stringify(flowStore, null, 4) const flowStateStore = writable({} as FlowState) + const selectedAssetStore = $state({ val: undefined }) const previewArgsStore = $state({ val: {} }) const scriptEditorDrawer = writable(undefined) @@ -106,7 +107,8 @@ editPanelSize: undefined, payloadData: undefined }), - currentEditor: writable(undefined) + currentEditor: writable(undefined), + selectedAssetStore }) setContext('PropPickerContext', { flowPropPickerConfig: writable(undefined),