mirror of
https://github.com/windmill-labs/windmill.git
synced 2026-09-03 16:03:20 +00:00
+S3 Object editor bar
This commit is contained in:
@@ -29,6 +29,7 @@
|
||||
import {
|
||||
DiffIcon,
|
||||
DollarSign,
|
||||
File,
|
||||
History,
|
||||
Library,
|
||||
Link,
|
||||
@@ -38,7 +39,7 @@
|
||||
Save,
|
||||
Users
|
||||
} from 'lucide-svelte'
|
||||
import { capitalize, toCamel } from '$lib/utils'
|
||||
import { capitalize, formatS3Object, toCamel } from '$lib/utils'
|
||||
import type { Schema, SchemaProperty, SupportedLanguage } from '$lib/common'
|
||||
import ScriptVersionHistory from './ScriptVersionHistory.svelte'
|
||||
import ScriptGen from './copilot/ScriptGen.svelte'
|
||||
@@ -48,6 +49,7 @@
|
||||
import ResourceEditorDrawer from './ResourceEditorDrawer.svelte'
|
||||
import type { EditorBarUi } from './custom_ui'
|
||||
import EditorSettings from './EditorSettings.svelte'
|
||||
import S3FilePicker from './S3FilePicker.svelte'
|
||||
|
||||
interface Props {
|
||||
lang: SupportedLanguage | 'bunnative' | undefined
|
||||
@@ -109,6 +111,7 @@
|
||||
let resourceTypePicker: ItemPicker | undefined = $state()
|
||||
let variableEditor: VariableEditor | undefined = $state()
|
||||
let resourceEditor: ResourceEditorDrawer | undefined = $state()
|
||||
let s3FilePicker: S3FilePicker | undefined = $state()
|
||||
|
||||
let showContextVarPicker = $derived(
|
||||
[
|
||||
@@ -168,6 +171,8 @@
|
||||
].includes(lang ?? '')
|
||||
)
|
||||
|
||||
let showS3Picker = $derived(['duckdb'].includes(lang ?? ''))
|
||||
|
||||
let showResourceTypePicker = $derived(
|
||||
['typescript', 'javascript'].includes(scriptLangToEditorLang(lang)) ||
|
||||
lang === 'python3' ||
|
||||
@@ -582,8 +587,14 @@ JsonNode ${windmillPathToCamelCaseName(path)} = JsonNode.Parse(await client.GetS
|
||||
editor.insertAtCursor(`(Wmill.getResource("${path}"))`)
|
||||
// for related places search: ADD_NEW_LANG
|
||||
} else if (lang == 'duckdb') {
|
||||
let t = resType == 'postgresql' ? 'postgres' : resType
|
||||
editor.insertAtCursor(`ATTACH '$res:${path}' AS db (TYPE ${t});`)
|
||||
let t = { postgresql: 'postgres', mysql: 'mysql', bigquery: 'bigquery' }[resType]
|
||||
if (!t) {
|
||||
sendUserToast(`Resource type ${resType} is not supported in DuckDB`, true)
|
||||
editor.insertAtCursor(`'$res:${path}'`)
|
||||
return
|
||||
} else {
|
||||
editor.insertAtCursor(`ATTACH '$res:${path}' AS db (TYPE ${t});`)
|
||||
}
|
||||
}
|
||||
|
||||
sendUserToast(`${path} inserted at cursor`)
|
||||
@@ -630,6 +641,20 @@ JsonNode ${windmillPathToCamelCaseName(path)} = JsonNode.Parse(await client.GetS
|
||||
<ResourceEditorDrawer bind:this={resourceEditor} on:refresh={resourcePicker.openDrawer} />
|
||||
<VariableEditor bind:this={variableEditor} on:create={variablePicker.openDrawer} />
|
||||
|
||||
<S3FilePicker
|
||||
bind:this={s3FilePicker}
|
||||
readOnlyMode={false}
|
||||
on:selectAndClose={(s3obj) => {
|
||||
if (lang === 'duckdb') {
|
||||
let s = `'${formatS3Object(s3obj.detail)}'`
|
||||
if (s3obj.detail?.s3.endsWith('.json')) s = `read_json(${s})`
|
||||
if (s3obj.detail?.s3.endsWith('.csv')) s = `read_csv(${s})`
|
||||
if (s3obj.detail?.s3.endsWith('.parquet')) s = `read_parquet(${s})`
|
||||
editor?.insertAtCursor(s)
|
||||
}
|
||||
}}
|
||||
/>
|
||||
|
||||
<div class="flex justify-between items-center overflow-y-auto w-full p-0.5">
|
||||
<div class="flex items-center">
|
||||
<div
|
||||
@@ -686,6 +711,22 @@ JsonNode ${windmillPathToCamelCaseName(path)} = JsonNode.Parse(await client.GetS
|
||||
</Button>
|
||||
{/if}
|
||||
|
||||
{#if showS3Picker && customUi?.s3object != false}
|
||||
<Button
|
||||
aiId="editor-bar-add-s3-object"
|
||||
aiDescription="Add S3 Object"
|
||||
title="Add S3 object"
|
||||
color="light"
|
||||
on:click={() => s3FilePicker?.open()}
|
||||
size="xs"
|
||||
btnClasses="!font-medium text-tertiary"
|
||||
spacingSize="md"
|
||||
startIcon={{ icon: File }}
|
||||
{iconOnly}
|
||||
>+S3 Object
|
||||
</Button>
|
||||
{/if}
|
||||
|
||||
{#if showResourceTypePicker && customUi?.type != false}
|
||||
<Button
|
||||
aiId="editor-bar-add-resource-type"
|
||||
|
||||
@@ -72,6 +72,7 @@
|
||||
|
||||
let dispatch = createEventDispatcher<{
|
||||
close: { s3: string; storage: string | undefined } | undefined
|
||||
selectAndClose: { s3: string; storage: string | undefined }
|
||||
}>()
|
||||
|
||||
let drawer: Drawer | undefined = $state()
|
||||
@@ -423,6 +424,9 @@
|
||||
}
|
||||
|
||||
async function selectAndClose() {
|
||||
if (selectedFileKey?.s3) {
|
||||
dispatch('selectAndClose', { s3: selectedFileKey.s3, storage })
|
||||
}
|
||||
drawer?.closeDrawer?.()
|
||||
}
|
||||
|
||||
|
||||
@@ -65,6 +65,7 @@ export type EditorBarUi = {
|
||||
library?: boolean
|
||||
useVsCode?: boolean
|
||||
diffMode?: boolean
|
||||
s3object?: boolean
|
||||
}
|
||||
|
||||
export type EditableSchemaFormUi = {
|
||||
|
||||
@@ -1454,6 +1454,11 @@ export function parseS3Object(s3Object: S3Object): { s3: string; storage?: strin
|
||||
return { storage: match?.[1] || undefined, s3: match?.[2] ?? '' }
|
||||
}
|
||||
|
||||
export function formatS3Object(s3Object: S3Object): S3Uri {
|
||||
if (typeof s3Object === 'object') return `s3://${s3Object.storage ?? ''}/${s3Object.s3}`
|
||||
return s3Object
|
||||
}
|
||||
|
||||
export function isS3Uri(uri: string): uri is S3Uri {
|
||||
const match = uri.match(/^s3:\/\/([^/]*)\/(.*)$/)
|
||||
return !!match && match.length === 3
|
||||
|
||||
Reference in New Issue
Block a user