mirror of
https://github.com/windmill-labs/windmill.git
synced 2026-08-21 16:02:28 +00:00
add debug Runs to apps
This commit is contained in:
@@ -1,7 +1,3 @@
|
||||
{
|
||||
auto_https off
|
||||
}
|
||||
|
||||
http://localhost {
|
||||
bind {$ADDRESS}
|
||||
reverse_proxy /api/* https://app.windmill.dev {
|
||||
|
||||
@@ -143,7 +143,7 @@
|
||||
}
|
||||
}
|
||||
|
||||
function format() {
|
||||
export function format() {
|
||||
if (editor) {
|
||||
code = getCode()
|
||||
editor.getAction('editor.action.formatDocument').run()
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
import { getScriptByPath, sendUserToast } from '$lib/utils'
|
||||
|
||||
import {
|
||||
faBroom,
|
||||
faCube,
|
||||
faDollarSign,
|
||||
faEye,
|
||||
@@ -307,6 +308,20 @@
|
||||
</span>
|
||||
</Button></div
|
||||
>
|
||||
<div>
|
||||
<Button
|
||||
btnClasses="!font-medium"
|
||||
size="xs"
|
||||
spacingSize="md"
|
||||
color="light"
|
||||
on:click={editor.format}
|
||||
startIcon={{ icon: faBroom }}
|
||||
>
|
||||
{#if !iconOnly}
|
||||
Format (Ctrl+S)
|
||||
{/if}
|
||||
</Button></div
|
||||
>
|
||||
</div>
|
||||
<div class="py-1">
|
||||
<div>
|
||||
|
||||
@@ -130,6 +130,15 @@
|
||||
}, 200)
|
||||
})
|
||||
|
||||
editor.onDidFocusEditorText(() => {
|
||||
dispatch('focus')
|
||||
|
||||
editor.addCommand(KeyMod.CtrlCmd | KeyCode.KeyS, function () {
|
||||
code = getCode()
|
||||
shouldBindKey && format && format()
|
||||
})
|
||||
})
|
||||
|
||||
if (autoHeight) {
|
||||
let ignoreEvent = false
|
||||
const updateHeight = () => {
|
||||
|
||||
@@ -16,11 +16,15 @@
|
||||
import RunnableWrapper from '../helpers/RunnableWrapper.svelte'
|
||||
import type { AppInput } from '../../inputType'
|
||||
import Scatter from 'svelte-chartjs/Scatter.svelte'
|
||||
import InputValue from '../helpers/InputValue.svelte'
|
||||
|
||||
export let id: string
|
||||
export let componentInput: AppInput | undefined
|
||||
export let configuration: Record<string, AppInput>
|
||||
|
||||
let zoomable = false
|
||||
let pannable = false
|
||||
|
||||
export const staticOutputs: string[] = ['loading', 'result']
|
||||
|
||||
ChartJS.register(
|
||||
@@ -35,28 +39,26 @@
|
||||
zoomPlugin
|
||||
)
|
||||
|
||||
const zoomOptions = {
|
||||
pan: {
|
||||
enabled: true
|
||||
},
|
||||
zoom: {
|
||||
drag: {
|
||||
enabled: false
|
||||
},
|
||||
wheel: {
|
||||
enabled: true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let result: { data: { x: any[]; y: string[] } } | undefined = undefined
|
||||
|
||||
const options = {
|
||||
$: options = {
|
||||
responsive: true,
|
||||
animation: false,
|
||||
maintainAspectRatio: false,
|
||||
plugins: {
|
||||
zoom: zoomOptions
|
||||
zoom: {
|
||||
pan: {
|
||||
enabled: pannable
|
||||
},
|
||||
zoom: {
|
||||
drag: {
|
||||
enabled: false
|
||||
},
|
||||
wheel: {
|
||||
enabled: zoomable
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -65,6 +67,9 @@
|
||||
}
|
||||
</script>
|
||||
|
||||
<InputValue {id} input={configuration.zoomable} bind:value={zoomable} />
|
||||
<InputValue {id} input={configuration.pannable} bind:value={pannable} />
|
||||
|
||||
<RunnableWrapper autoRefresh bind:componentInput {id} bind:result>
|
||||
{#if result}
|
||||
<Scatter {data} {options} />
|
||||
|
||||
@@ -28,6 +28,8 @@
|
||||
export const staticOutputs: string[] = ['loading', 'result']
|
||||
|
||||
let logarithmicScale = false
|
||||
let zoomable = false
|
||||
let pannable = false
|
||||
|
||||
ChartJS.register(
|
||||
Title,
|
||||
@@ -43,20 +45,6 @@
|
||||
LogarithmicScale
|
||||
)
|
||||
|
||||
const zoomOptions = {
|
||||
pan: {
|
||||
enabled: true
|
||||
},
|
||||
zoom: {
|
||||
drag: {
|
||||
enabled: false
|
||||
},
|
||||
wheel: {
|
||||
enabled: true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let result: { data: { x: any[]; y: string[] } } | undefined = undefined
|
||||
|
||||
$: options = {
|
||||
@@ -64,7 +52,19 @@
|
||||
animation: false,
|
||||
maintainAspectRatio: false,
|
||||
plugins: {
|
||||
zoom: zoomOptions
|
||||
zoom: {
|
||||
pan: {
|
||||
enabled: pannable
|
||||
},
|
||||
zoom: {
|
||||
drag: {
|
||||
enabled: false
|
||||
},
|
||||
wheel: {
|
||||
enabled: zoomable
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
scales: {
|
||||
x: {
|
||||
@@ -82,6 +82,8 @@
|
||||
</script>
|
||||
|
||||
<InputValue {id} input={configuration.logarithmicScale} bind:value={logarithmicScale} />
|
||||
<InputValue {id} input={configuration.zoomable} bind:value={zoomable} />
|
||||
<InputValue {id} input={configuration.pannable} bind:value={pannable} />
|
||||
|
||||
<RunnableWrapper autoRefresh bind:componentInput {id} bind:result>
|
||||
{#if result}
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
export let result: any = undefined
|
||||
export let forceSchemaDisplay: boolean = false
|
||||
|
||||
const { worldStore, runnableComponents, workspace, appPath, isEditor } =
|
||||
const { worldStore, runnableComponents, workspace, appPath, isEditor, jobs } =
|
||||
getContext<AppEditorContext>('AppEditorContext')
|
||||
|
||||
onMount(() => {
|
||||
@@ -180,7 +180,7 @@
|
||||
|
||||
outputs?.loading?.set(true)
|
||||
|
||||
await testJobLoader?.abstractRun(() => {
|
||||
let njob = await testJobLoader?.abstractRun(() => {
|
||||
const nonStaticRunnableInputs = {}
|
||||
const staticRunnableInputs = {}
|
||||
Object.keys(fields ?? {}).forEach((k) => {
|
||||
@@ -220,6 +220,9 @@
|
||||
requestBody
|
||||
})
|
||||
})
|
||||
if (njob) {
|
||||
$jobs = [...$jobs, { job: njob, component: id }]
|
||||
}
|
||||
}
|
||||
|
||||
export async function runComponent() {
|
||||
|
||||
@@ -68,7 +68,8 @@
|
||||
appPath: path,
|
||||
workspace: $workspaceStore ?? '',
|
||||
onchange: () => saveDraft(),
|
||||
isEditor: true
|
||||
isEditor: true,
|
||||
jobs: writable([])
|
||||
})
|
||||
|
||||
let timeout: NodeJS.Timeout | undefined = undefined
|
||||
@@ -120,7 +121,7 @@
|
||||
{#if previewing}
|
||||
<AppPreview
|
||||
workspace={$workspaceStore ?? ''}
|
||||
{summary}
|
||||
summary={$summaryStore}
|
||||
app={$appStore}
|
||||
appPath={path}
|
||||
{breakpoint}
|
||||
|
||||
@@ -1,30 +1,42 @@
|
||||
<script lang="ts">
|
||||
import { goto } from '$app/navigation'
|
||||
import { page } from '$app/stores'
|
||||
import { Alert, Drawer, DrawerContent } from '$lib/components/common'
|
||||
import { Alert, Badge, Drawer, DrawerContent } from '$lib/components/common'
|
||||
import Button from '$lib/components/common/button/Button.svelte'
|
||||
import { dirtyStore } from '$lib/components/common/confirmationModal/dirtyStore'
|
||||
import Skeleton from '$lib/components/common/skeleton/Skeleton.svelte'
|
||||
import ToggleButton from '$lib/components/common/toggleButton/ToggleButton.svelte'
|
||||
import ToggleButtonGroup from '$lib/components/common/toggleButton/ToggleButtonGroup.svelte'
|
||||
import DisplayResult from '$lib/components/DisplayResult.svelte'
|
||||
import FlowJobResult from '$lib/components/FlowJobResult.svelte'
|
||||
import FlowProgressBar from '$lib/components/flows/FlowProgressBar.svelte'
|
||||
import FlowStatusViewer from '$lib/components/FlowStatusViewer.svelte'
|
||||
import JobArgs from '$lib/components/JobArgs.svelte'
|
||||
import LogViewer from '$lib/components/LogViewer.svelte'
|
||||
import Path from '$lib/components/Path.svelte'
|
||||
import SplitPanesWrapper from '$lib/components/splitPanes/SplitPanesWrapper.svelte'
|
||||
import TestJobLoader from '$lib/components/TestJobLoader.svelte'
|
||||
import Toggle from '$lib/components/Toggle.svelte'
|
||||
import Tooltip from '$lib/components/Tooltip.svelte'
|
||||
import { AppService, Policy } from '$lib/gen'
|
||||
import { AppService, Job, Policy } from '$lib/gen'
|
||||
import { userStore, workspaceStore } from '$lib/stores'
|
||||
import { faClipboard, faExternalLink, faSave } from '@fortawesome/free-solid-svg-icons'
|
||||
import { faBug, faClipboard, faExternalLink, faSave } from '@fortawesome/free-solid-svg-icons'
|
||||
import {
|
||||
AlignHorizontalSpaceAround,
|
||||
Expand,
|
||||
Eye,
|
||||
Laptop2,
|
||||
Loader2,
|
||||
Pencil,
|
||||
Smartphone
|
||||
} from 'lucide-svelte'
|
||||
import { getContext } from 'svelte'
|
||||
import { Icon } from 'svelte-awesome'
|
||||
import { copyToClipboard, sendUserToast } from '../../../utils'
|
||||
import { Pane, Splitpanes } from 'svelte-splitpanes'
|
||||
import { classNames, copyToClipboard, sendUserToast } from '../../../utils'
|
||||
import type { AppComponent, AppEditorContext } from '../types'
|
||||
import AppExportButton from './AppExportButton.svelte'
|
||||
import PanelSection from './settingsPanel/common/PanelSection.svelte'
|
||||
|
||||
async function hash(message) {
|
||||
const msgUint8 = new TextEncoder().encode(message) // encode as (utf-8) Uint8Array
|
||||
@@ -36,7 +48,7 @@
|
||||
|
||||
export let policy: Policy
|
||||
|
||||
const { app, summary, mode, breakpoint, appPath } =
|
||||
const { app, summary, mode, breakpoint, appPath, jobs } =
|
||||
getContext<AppEditorContext>('AppEditorContext')
|
||||
const loading = {
|
||||
publish: false,
|
||||
@@ -47,6 +59,7 @@
|
||||
let pathError: string | undefined = undefined
|
||||
|
||||
let saveDrawerOpen = false
|
||||
let jobsDrawerOpen = false
|
||||
let publishDrawerOpen = false
|
||||
|
||||
function closeSaveDrawer() {
|
||||
@@ -144,8 +157,17 @@
|
||||
loading.save = false
|
||||
sendUserToast('App saved')
|
||||
}
|
||||
|
||||
let selectedJobId: string | undefined = undefined
|
||||
let testJobLoader: TestJobLoader
|
||||
let job: Job | undefined = undefined
|
||||
let testIsLoading = false
|
||||
|
||||
$: selectedJobId && testJobLoader?.watchJob(selectedJobId)
|
||||
</script>
|
||||
|
||||
<TestJobLoader bind:this={testJobLoader} bind:isLoading={testIsLoading} bind:job />
|
||||
|
||||
<Drawer bind:open={saveDrawerOpen} size="800px">
|
||||
<DrawerContent title="Create an App" on:close={() => closeSaveDrawer()}>
|
||||
<Path
|
||||
@@ -166,6 +188,91 @@
|
||||
</DrawerContent>
|
||||
</Drawer>
|
||||
|
||||
<Drawer bind:open={jobsDrawerOpen} size="900px">
|
||||
<DrawerContent noPadding title="Debug Runs" on:close={() => (jobsDrawerOpen = false)}>
|
||||
<Splitpanes class="!overflow-visible">
|
||||
<Pane size={25}>
|
||||
<PanelSection title="Past Runs" smallPadding>
|
||||
<div class="flex flex-col gap-2 w-full">
|
||||
{#if $jobs.length > 0}
|
||||
<div class="flex gap-2 flex-col ">
|
||||
{#each $jobs ?? [] as { job, component } (job)}
|
||||
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||
<div
|
||||
class="{classNames(
|
||||
'border flex gap-1 truncate justify-between flex-row w-full items-center p-2 rounded-md cursor-pointer hover:bg-blue-50 hover:text-blue-400',
|
||||
selectedJobId == job ? 'bg-blue-100 text-blue-600' : ''
|
||||
)},"
|
||||
on:click={() => (selectedJobId = job)}
|
||||
>
|
||||
<span class="text-xs truncate">{job}</span>
|
||||
<Badge color="dark-indigo">{component}</Badge>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
{:else}
|
||||
<div class="text-sm text-gray-500">No items</div>
|
||||
{/if}
|
||||
</div>
|
||||
</PanelSection>
|
||||
</Pane>
|
||||
<Pane size={75}>
|
||||
<div class="h-full w-full overflow-hidden">
|
||||
{#if selectedJobId}
|
||||
{#if !job}
|
||||
<Skeleton layout={[[40]]} />
|
||||
{:else}
|
||||
<div class="flex flex-col h-full w-full gap-4 mb-4">
|
||||
{#if job?.['running']}
|
||||
<div class="flex flex-row-reverse w-full"
|
||||
><Button
|
||||
color="red"
|
||||
variant="border"
|
||||
on:click={() => testJobLoader?.cancelJob()}>Cancel</Button
|
||||
>
|
||||
</div>
|
||||
{/if}
|
||||
<div class="p-2">
|
||||
<JobArgs args={job?.args} />
|
||||
</div>
|
||||
{#if job?.job_kind !== 'flow' && job?.job_kind !== 'flowpreview'}
|
||||
<Splitpanes horizontal class="grow border w-full">
|
||||
<Pane size={50} minSize={10}>
|
||||
<LogViewer content={job?.logs} isLoading={testIsLoading} />
|
||||
</Pane>
|
||||
<Pane size={50} minSize={10} class="text-sm text-gray-600">
|
||||
{#if job != undefined && 'result' in job && job.result != undefined}
|
||||
<pre class="overflow-x-auto break-words relative h-full px-2"
|
||||
><DisplayResult result={job.result} /></pre
|
||||
>
|
||||
{:else if testIsLoading}
|
||||
<div class="p-2"><Loader2 class="animate-spin" /> </div>
|
||||
{/if}
|
||||
</Pane>
|
||||
</Splitpanes>
|
||||
{:else}
|
||||
<div class="mt-10" />
|
||||
<FlowProgressBar {job} class="py-4" />
|
||||
<div class="w-full mt-10 mb-20">
|
||||
<FlowStatusViewer
|
||||
jobId={job.id}
|
||||
on:jobsLoaded={({ detail }) => {
|
||||
job = detail
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
{/if}
|
||||
{:else}
|
||||
<div class="text-sm p-2 text-gray-500">Select a job to see its details</div>
|
||||
{/if}
|
||||
</div>
|
||||
</Pane>
|
||||
</Splitpanes>
|
||||
</DrawerContent>
|
||||
</Drawer>
|
||||
|
||||
<Drawer bind:open={publishDrawerOpen} size="800px">
|
||||
<DrawerContent title="Publish an App" on:close={() => (publishDrawerOpen = false)}>
|
||||
{#if appPath == ''}
|
||||
@@ -267,6 +374,15 @@
|
||||
</span>
|
||||
</div>
|
||||
<div class="flex flex-row grow gap-4 justify-end ">
|
||||
<Button
|
||||
on:click={() => (jobsDrawerOpen = true)}
|
||||
color="light"
|
||||
size="xs"
|
||||
variant="border"
|
||||
startIcon={{ icon: faBug }}
|
||||
>
|
||||
Debug Runs
|
||||
</Button>
|
||||
<span class="hidden lg:block">
|
||||
<AppExportButton app={$app} />
|
||||
</span>
|
||||
|
||||
@@ -52,7 +52,8 @@
|
||||
appPath,
|
||||
workspace,
|
||||
onchange: undefined,
|
||||
isEditor
|
||||
isEditor,
|
||||
jobs: writable([])
|
||||
})
|
||||
|
||||
let mounted = false
|
||||
|
||||
@@ -127,7 +127,6 @@
|
||||
rowHeight={36}
|
||||
cols={columnConfiguration}
|
||||
fastStart={true}
|
||||
on:pointerup={({ detail }) => selectComponent(detail.id)}
|
||||
gap={[4, 2]}
|
||||
>
|
||||
{#each $lazyGrid as gridComponent (gridComponent.id)}
|
||||
@@ -148,11 +147,14 @@
|
||||
>
|
||||
{/if}
|
||||
<div
|
||||
on:pointerdown={() => {
|
||||
selectComponent(dataItem.data.id)
|
||||
}}
|
||||
class={classNames(
|
||||
'h-full w-full flex justify-center align-center items-center',
|
||||
gridComponent.data.card ? 'border border-gray-100' : ''
|
||||
)}
|
||||
on:click|preventDefault|capture|once
|
||||
on:click|preventDefault|capture|once|stopPropagation
|
||||
>
|
||||
<ComponentEditor
|
||||
{pointerdown}
|
||||
|
||||
@@ -332,7 +332,20 @@ const display: ComponentSet = {
|
||||
{
|
||||
id: 'scatterchartcomponent',
|
||||
type: 'scatterchartcomponent',
|
||||
configuration: {},
|
||||
configuration: {
|
||||
zoomable: {
|
||||
type: 'static',
|
||||
onlyStatic: true,
|
||||
fieldType: 'boolean',
|
||||
value: false
|
||||
},
|
||||
pannable: {
|
||||
type: 'static',
|
||||
onlyStatic: true,
|
||||
fieldType: 'boolean',
|
||||
value: false
|
||||
},
|
||||
},
|
||||
componentInput: {
|
||||
type: 'static',
|
||||
fieldType: 'array',
|
||||
@@ -367,7 +380,19 @@ const display: ComponentSet = {
|
||||
onlyStatic: true,
|
||||
fieldType: 'boolean',
|
||||
value: false
|
||||
}
|
||||
},
|
||||
zoomable: {
|
||||
type: 'static',
|
||||
onlyStatic: true,
|
||||
fieldType: 'boolean',
|
||||
value: false
|
||||
},
|
||||
pannable: {
|
||||
type: 'static',
|
||||
onlyStatic: true,
|
||||
fieldType: 'boolean',
|
||||
value: false
|
||||
},
|
||||
},
|
||||
componentInput: {
|
||||
type: 'static',
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<script lang="ts">
|
||||
import { classNames } from '$lib/utils'
|
||||
import { getContext } from 'svelte'
|
||||
import { key } from 'svelte-awesome/icons'
|
||||
import type { AppEditorContext } from '../../types'
|
||||
import { displayData } from '../../utils'
|
||||
import PanelSection from '../settingsPanel/common/PanelSection.svelte'
|
||||
@@ -85,16 +86,19 @@
|
||||
$connectingInput.hoveredComponent === componentId ? 'outline outline-blue-500' : ''
|
||||
)}
|
||||
>
|
||||
<!-- {#if $selectedComponent === componentId && $connectingInput?.opened}
|
||||
<div class="absolute top-0 left-0 w-full h-full bg-gray-500 bg-opacity-50 z-10" />
|
||||
{/if} -->
|
||||
<ComponentOutputViewer
|
||||
{outputs}
|
||||
{componentId}
|
||||
on:select={({ detail }) => {
|
||||
connectInput(componentId, detail)
|
||||
}}
|
||||
/>
|
||||
{#key $selectedComponent}
|
||||
{#key $connectingInput?.opened}
|
||||
<ComponentOutputViewer
|
||||
outputs={$connectingInput?.opened && $selectedComponent === componentId
|
||||
? ['search']
|
||||
: outputs}
|
||||
{componentId}
|
||||
on:select={({ detail }) => {
|
||||
connectInput(componentId, detail)
|
||||
}}
|
||||
/>
|
||||
{/key}
|
||||
{/key}
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
+11
-2
@@ -73,6 +73,16 @@
|
||||
</Badge>
|
||||
{/if}
|
||||
|
||||
<Button
|
||||
variant="border"
|
||||
size="xs"
|
||||
color="blue"
|
||||
on:click={async () => {
|
||||
editor.format()
|
||||
}}
|
||||
>
|
||||
Format <Tooltip>Ctrl+S</Tooltip>
|
||||
</Button>
|
||||
{#if id.startsWith('unused-')}
|
||||
<Button
|
||||
size="xs"
|
||||
@@ -87,7 +97,6 @@
|
||||
loading={runLoading}
|
||||
size="xs"
|
||||
color="blue"
|
||||
title="Cmd+Enter"
|
||||
on:click={async () => {
|
||||
runLoading = true
|
||||
await $runnableComponents[id]?.()
|
||||
@@ -95,7 +104,7 @@
|
||||
}}
|
||||
>
|
||||
Run <Tooltip
|
||||
>Cmd+Enter to run the script and see the result in the component directly</Tooltip
|
||||
>Ctrl+Enter to run the script and see the result in the component directly</Tooltip
|
||||
>
|
||||
</Button>
|
||||
{/if}
|
||||
|
||||
@@ -135,7 +135,7 @@ declare const ${k} = ${JSON.stringify(v)};
|
||||
<div class="border w-full">
|
||||
<PanelSection
|
||||
smallPadding
|
||||
title={`Runnable inputs (${
|
||||
title={`Runnable Inputs (${
|
||||
Object.keys(component.componentInput.fields ?? {}).length
|
||||
})`}
|
||||
>
|
||||
|
||||
@@ -10,6 +10,8 @@
|
||||
StaticAppInput,
|
||||
UserAppInput
|
||||
} from '../../inputType'
|
||||
import { getContext } from 'svelte'
|
||||
import type { AppEditorContext } from '../../types'
|
||||
|
||||
export let inputSpecs: Record<
|
||||
string,
|
||||
@@ -19,6 +21,8 @@
|
||||
export let staticOnly: boolean = false
|
||||
export let shouldCapitalize: boolean = true
|
||||
export let rowColumns = false
|
||||
|
||||
const { connectingInput } = getContext<AppEditorContext>('AppEditorContext')
|
||||
</script>
|
||||
|
||||
{#if inputSpecs}
|
||||
@@ -27,7 +31,7 @@
|
||||
{@const input = inputSpecs[inputSpecKey]}
|
||||
<div class="flex flex-col gap-1">
|
||||
<div class="flex justify-between items-end gap-1">
|
||||
<span class="text-xs font-semibold">
|
||||
<span class="text-sm font-semibold truncate">
|
||||
{shouldCapitalize ? capitalize(inputSpecKey) : inputSpecKey}
|
||||
</span>
|
||||
|
||||
@@ -39,7 +43,19 @@
|
||||
</Badge>
|
||||
|
||||
{#if !inputSpecs[inputSpecKey].onlyStatic}
|
||||
<ToggleButtonGroup bind:selected={inputSpecs[inputSpecKey].type}>
|
||||
<ToggleButtonGroup
|
||||
bind:selected={inputSpecs[inputSpecKey].type}
|
||||
on:selected={(e) => {
|
||||
console.log(inputSpecs[inputSpecKey])
|
||||
if (e.detail == 'connected' && !inputSpecs[inputSpecKey]['connection']) {
|
||||
$connectingInput = {
|
||||
opened: true,
|
||||
input: undefined,
|
||||
hoveredComponent: undefined
|
||||
}
|
||||
}
|
||||
}}
|
||||
>
|
||||
<ToggleButton
|
||||
title="Static"
|
||||
position="left"
|
||||
@@ -71,7 +87,7 @@
|
||||
/>
|
||||
{/if}
|
||||
<ToggleButton
|
||||
title="Connected"
|
||||
title="Connect"
|
||||
position="right"
|
||||
value="connected"
|
||||
startIcon={{ icon: faArrowRight }}
|
||||
|
||||
+2
-2
@@ -30,7 +30,7 @@
|
||||
|
||||
{#if componentInput.type === 'connected'}
|
||||
{#if componentInput.connection}
|
||||
<div class="flex justify-between w-full">
|
||||
<div class="flex justify-between w-full gap-1">
|
||||
<span class="text-xs">Status</span>
|
||||
<Badge color="green">Connected</Badge>
|
||||
</div>
|
||||
@@ -56,7 +56,7 @@
|
||||
Disconnect
|
||||
</Button>
|
||||
{:else}
|
||||
<div class="flex justify-between w-full">
|
||||
<div class="flex justify-between w-full gap-1">
|
||||
<span class="text-xs">Status</span>
|
||||
<Badge color="yellow">Not connected</Badge>
|
||||
</div>
|
||||
|
||||
@@ -145,7 +145,8 @@ export type AppEditorContext = {
|
||||
appPath: string,
|
||||
workspace: string,
|
||||
onchange: (() => void) | undefined,
|
||||
isEditor: boolean
|
||||
isEditor: boolean,
|
||||
jobs: Writable<{ job: string, component: string }[]>
|
||||
}
|
||||
|
||||
export type EditorMode = 'dnd' | 'preview'
|
||||
|
||||
Reference in New Issue
Block a user