mirror of
https://github.com/windmill-labs/windmill.git
synced 2026-08-24 16:01:42 +00:00
fix: fix cyclical loop in apps
This commit is contained in:
@@ -511,26 +511,26 @@ pub async fn run_worker<R: rsmq_async::RsmqConnection + Send + Sync + Clone + 's
|
||||
(copy_cache_from_bucket_handle.is_none() || copy_cache_from_bucket_handle.as_ref().unwrap().is_finished()) {
|
||||
last_sync = Instant::now();
|
||||
|
||||
if (crate::global_cache::worker_s3_bucket_sync_enabled(&db).await) {
|
||||
if crate::global_cache::worker_s3_bucket_sync_enabled(&db).await {
|
||||
|
||||
tracing::debug!("CAN PULL LOCK START");
|
||||
let _lock = CAN_PULL.write().await;
|
||||
tracing::debug!("CAN PULL LOCK START");
|
||||
let _lock = CAN_PULL.write().await;
|
||||
|
||||
tracing::info!("Started syncing cache");
|
||||
// if num_workers > 1 {
|
||||
// create_barrier_for_all_workers(num_workers, sync_barrier.clone()).await;
|
||||
// }
|
||||
if let Err(e) = copy_cache_to_tmp_cache().await {
|
||||
tracing::error!("failed to copy cache to tmp cache: {}", e);
|
||||
} else {
|
||||
copy_cache_from_bucket_handle = Some(tokio::task::spawn(async move {
|
||||
if let Some(ref s) = S3_CACHE_BUCKET.clone() {
|
||||
if let Err(e) = cache_global(s, copy_tx).await {
|
||||
tracing::error!("failed to sync cache: {}", e);
|
||||
tracing::info!("Started syncing cache");
|
||||
// if num_workers > 1 {
|
||||
// create_barrier_for_all_workers(num_workers, sync_barrier.clone()).await;
|
||||
// }
|
||||
if let Err(e) = copy_cache_to_tmp_cache().await {
|
||||
tracing::error!("failed to copy cache to tmp cache: {}", e);
|
||||
} else {
|
||||
copy_cache_from_bucket_handle = Some(tokio::task::spawn(async move {
|
||||
if let Some(ref s) = S3_CACHE_BUCKET.clone() {
|
||||
if let Err(e) = cache_global(s, copy_tx).await {
|
||||
tracing::error!("failed to sync cache: {}", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}));
|
||||
}
|
||||
}));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -77,8 +77,11 @@
|
||||
const debounce_ms = 50
|
||||
|
||||
export async function computeExpr() {
|
||||
value = await evalExpr(lastInput as EvalAppInput)
|
||||
return value
|
||||
const nvalue = await evalExpr(lastInput as EvalAppInput)
|
||||
if (!deepEqual(nvalue, value)) {
|
||||
value = nvalue
|
||||
}
|
||||
return nvalue
|
||||
}
|
||||
|
||||
function debounce(cb: () => Promise<void>) {
|
||||
|
||||
@@ -423,6 +423,7 @@
|
||||
let p: Partial<CancelablePromise<void>> = new Promise<void>((resolve, reject) => {
|
||||
rejectCb = reject
|
||||
donePromise = resolve
|
||||
|
||||
executeComponent(true, inlineScript).catch(reject)
|
||||
})
|
||||
p.cancel = () => {
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
<script lang="ts">
|
||||
import Toggle from '$lib/components/Toggle.svelte'
|
||||
import { Button, Popup, SecondsInput } from '$lib/components/common'
|
||||
import { autoPlacement } from '@floating-ui/core'
|
||||
|
||||
export let cache_ttl: number | undefined
|
||||
</script>
|
||||
|
||||
<Popup
|
||||
floatingConfig={{
|
||||
middleware: [
|
||||
autoPlacement({
|
||||
allowedPlacements: ['bottom-start', 'bottom-end', 'top-start', 'top-end', 'top', 'bottom']
|
||||
})
|
||||
]
|
||||
}}
|
||||
>
|
||||
<svelte:fragment slot="button">
|
||||
<Button
|
||||
nonCaptureEvent={true}
|
||||
btnClasses={Boolean(cache_ttl)
|
||||
? 'bg-blue-100 text-blue-800 border border-blue-300 hover:bg-blue-200 dark:bg-frost-700 dark:text-frost-100 dark:border-frost-600'
|
||||
: 'bg-surface text-primay hover:bg-hover'}
|
||||
color="light"
|
||||
variant="border"
|
||||
size="xs">Cache</Button
|
||||
>
|
||||
</svelte:fragment>
|
||||
<div class="block text-primary">
|
||||
<Toggle
|
||||
checked={Boolean(cache_ttl)}
|
||||
on:change={() => {
|
||||
if (cache_ttl != undefined) {
|
||||
cache_ttl = undefined
|
||||
} else {
|
||||
cache_ttl = 600
|
||||
}
|
||||
}}
|
||||
options={{
|
||||
right: 'Cache the results for each possible inputs'
|
||||
}}
|
||||
/>
|
||||
<div class="mb-4">
|
||||
<span class="text-xs font-bold">How long to keep cache valid</span>
|
||||
|
||||
{#if cache_ttl}
|
||||
<SecondsInput bind:seconds={cache_ttl} />
|
||||
{:else}
|
||||
<SecondsInput disabled />
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
</Popup>
|
||||
+2
-57
@@ -20,10 +20,8 @@
|
||||
import { scriptLangToEditorLang } from '$lib/scripts'
|
||||
import ScriptGen from '$lib/components/codeGen/ScriptGen.svelte'
|
||||
import DiffEditor from '$lib/components/DiffEditor.svelte'
|
||||
import { autoPlacement } from '@floating-ui/core'
|
||||
import { Popup, SecondsInput } from '$lib/components/common'
|
||||
import Toggle from '$lib/components/Toggle.svelte'
|
||||
import { userStore } from '$lib/stores'
|
||||
import CacheTtlPopup from './CacheTtlPopup.svelte'
|
||||
|
||||
let inlineScriptEditorDrawer: InlineScriptEditorDrawer
|
||||
|
||||
@@ -190,60 +188,7 @@
|
||||
<Badge color="red" baseClass="!text-2xs">Invalid</Badge>
|
||||
{/if}
|
||||
{#if inlineScript}
|
||||
<Popup
|
||||
floatingConfig={{
|
||||
middleware: [
|
||||
autoPlacement({
|
||||
allowedPlacements: [
|
||||
'bottom-start',
|
||||
'bottom-end',
|
||||
'top-start',
|
||||
'top-end',
|
||||
'top',
|
||||
'bottom'
|
||||
]
|
||||
})
|
||||
]
|
||||
}}
|
||||
>
|
||||
<svelte:fragment slot="button">
|
||||
<Button
|
||||
nonCaptureEvent={true}
|
||||
btnClasses={Boolean(inlineScript.cache_ttl)
|
||||
? 'bg-blue-100 text-blue-800 border border-blue-300 hover:bg-blue-200 dark:bg-frost-700 dark:text-frost-100 dark:border-frost-600'
|
||||
: 'bg-surface text-primay hover:bg-hover'}
|
||||
color="light"
|
||||
variant="border"
|
||||
size="xs">Cache</Button
|
||||
>
|
||||
</svelte:fragment>
|
||||
<div class="block text-primary">
|
||||
<Toggle
|
||||
checked={Boolean(inlineScript.cache_ttl)}
|
||||
on:change={() => {
|
||||
if (inlineScript) {
|
||||
if (inlineScript.cache_ttl != undefined) {
|
||||
inlineScript.cache_ttl = undefined
|
||||
} else {
|
||||
inlineScript.cache_ttl = 600
|
||||
}
|
||||
}
|
||||
}}
|
||||
options={{
|
||||
right: 'Cache the results for each possible inputs'
|
||||
}}
|
||||
/>
|
||||
<div class="mb-4">
|
||||
<span class="text-xs font-bold">How long to keep cache valid</span>
|
||||
|
||||
{#if inlineScript.cache_ttl}
|
||||
<SecondsInput bind:seconds={inlineScript.cache_ttl} />
|
||||
{:else}
|
||||
<SecondsInput disabled />
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
</Popup>
|
||||
<CacheTtlPopup bind:cache_ttl={inlineScript.cache_ttl} />
|
||||
{/if}
|
||||
<ScriptGen
|
||||
lang={inlineScript?.language}
|
||||
|
||||
+33
-12
@@ -37,22 +37,33 @@
|
||||
|
||||
let drawerFlowViewer: Drawer
|
||||
let flowPath: string = ''
|
||||
let notFound = false
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
async function refreshScript(x: RunnableByPath) {
|
||||
let { schema } = await getScriptByPath(x.path)
|
||||
if (!deepEqual(x.schema, schema)) {
|
||||
x.schema = schema
|
||||
fields = computeFields(schema, false, fields)
|
||||
try {
|
||||
let { schema } = await getScriptByPath(x.path)
|
||||
if (!deepEqual(x.schema, schema)) {
|
||||
x.schema = schema
|
||||
fields = computeFields(schema, false, fields)
|
||||
}
|
||||
} catch (e) {
|
||||
notFound = true
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
|
||||
async function refreshFlow(x: RunnableByPath) {
|
||||
const { schema } = (await loadSchema($workspaceStore ?? '', x.path, 'flow')) ?? emptySchema()
|
||||
if (!deepEqual(x.schema, schema)) {
|
||||
x.schema = schema
|
||||
fields = computeFields(schema, false, fields)
|
||||
try {
|
||||
const { schema } = (await loadSchema($workspaceStore ?? '', x.path, 'flow')) ?? emptySchema()
|
||||
if (!deepEqual(x.schema, schema)) {
|
||||
x.schema = schema
|
||||
fields = computeFields(schema, false, fields)
|
||||
}
|
||||
} catch (e) {
|
||||
notFound = true
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -74,14 +85,20 @@
|
||||
})
|
||||
}
|
||||
|
||||
function refresh() {
|
||||
let lastRunnable: RunnableByPath | undefined = undefined
|
||||
function refresh(runnable) {
|
||||
if (deepEqual(runnable, lastRunnable)) {
|
||||
return
|
||||
}
|
||||
notFound = false
|
||||
if (runnable.runType == 'script') {
|
||||
refreshScript(runnable)
|
||||
} else if (runnable.runType == 'flow') {
|
||||
refreshFlow(runnable)
|
||||
}
|
||||
lastRunnable = runnable
|
||||
}
|
||||
$: runnable.runType && refresh()
|
||||
$: refresh(runnable)
|
||||
</script>
|
||||
|
||||
<Drawer bind:this={drawerFlowViewer} size="1200px">
|
||||
@@ -100,7 +117,7 @@
|
||||
startIcon={{ icon: faRefresh }}
|
||||
on:click={async () => {
|
||||
sendUserToast('Refreshing inputs')
|
||||
refresh()
|
||||
refresh(runnable)
|
||||
$stateId = $stateId + 1
|
||||
await tick()
|
||||
}}
|
||||
@@ -169,7 +186,11 @@
|
||||
</div>
|
||||
<div class="w-full">
|
||||
{#key $stateId}
|
||||
{#if runnable.runType == 'script' || runnable.runType == 'hubscript'}
|
||||
{#if notFound}
|
||||
<div class="text-red-400"
|
||||
>{runnable.runType} not found at {runnable.path} in workspace {$workspaceStore}</div
|
||||
>
|
||||
{:else if runnable.runType == 'script' || runnable.runType == 'hubscript'}
|
||||
<div class="border">
|
||||
<FlowModuleScript path={runnable.path} />
|
||||
</div>
|
||||
|
||||
@@ -11,17 +11,28 @@
|
||||
let code: string
|
||||
let language: SupportedLanguage
|
||||
|
||||
let notFound = false
|
||||
async function loadCode(path: string, hash: string | undefined) {
|
||||
const script = hash
|
||||
? await ScriptService.getScriptByHash({ workspace: $workspaceStore!, hash })
|
||||
: await getScriptByPath(path!)
|
||||
code = script.content
|
||||
language = script.language
|
||||
try {
|
||||
notFound = false
|
||||
const script = hash
|
||||
? await ScriptService.getScriptByHash({ workspace: $workspaceStore!, hash })
|
||||
: await getScriptByPath(path!)
|
||||
code = script.content
|
||||
language = script.language
|
||||
} catch (e) {
|
||||
notFound = true
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
|
||||
$: path && loadCode(path, hash)
|
||||
</script>
|
||||
|
||||
<div class="flex flex-col flex-1 h-full overflow-auto p-2">
|
||||
<HighlightCode {language} {code} />
|
||||
{#if notFound}
|
||||
<div class="text-red-400">script not found at {path} in workspace {$workspaceStore}</div>
|
||||
{:else}
|
||||
<HighlightCode {language} {code} />
|
||||
{/if}
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user