From 40894a0771c07d39c66a00384116c9f4994b036f Mon Sep 17 00:00:00 2001 From: Claude Date: Sun, 4 Jan 2026 13:21:11 +0000 Subject: [PATCH 1/5] Improve node designer code editor UX - Add get_secret_value() autocomplete for SecretStr type after accessing .secret_value on SecretSelector components - Fix text selection highlighting to use distinct cyan color (accent) instead of similar light blue as active line - Fix arrow key navigation in autocomplete by adding completionKeymap while keeping custom Tab handling --- .../features/designer/editor/pythonEditor.vue | 5 +++-- .../composables/usePolarsAutocompletion.ts | 22 ++++++++++++++++++- .../src/renderer/styles/main.css | 7 ++++-- 3 files changed, 29 insertions(+), 5 deletions(-) diff --git a/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue b/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue index 4a42c9e67..b6cd55126 100644 --- a/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue +++ b/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue @@ -25,7 +25,7 @@ import { ref, shallowRef, defineExpose, watch } from "vue"; import { Codemirror } from "vue-codemirror"; import { python } from "@codemirror/lang-python"; import { oneDark } from "@codemirror/theme-one-dark"; -import { autocompletion, CompletionSource, acceptCompletion } from "@codemirror/autocomplete"; +import { autocompletion, completionKeymap, CompletionSource, acceptCompletion } from "@codemirror/autocomplete"; import { indentMore } from "@codemirror/commands"; import { polarsCompletionVals } from "./pythonEditor/polarsCompletions"; @@ -88,9 +88,10 @@ const extensions: Extension[] = [ EditorState.tabSize.of(4), autocompletion({ override: [polarsCompletions], - defaultKeymap: false, // Disable default keymap + defaultKeymap: false, // Disable default keymap to use custom tabKeymap closeOnBlur: false, }), + keymap.of(completionKeymap), tabKeymap, ]; diff --git a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts index 2baedb61b..5c0a4de42 100644 --- a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts +++ b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts @@ -5,7 +5,7 @@ import { EditorView, keymap } from '@codemirror/view'; import { EditorState, Extension } from '@codemirror/state'; import { python } from '@codemirror/lang-python'; import { oneDark } from '@codemirror/theme-one-dark'; -import { autocompletion, CompletionContext, CompletionResult, acceptCompletion } from '@codemirror/autocomplete'; +import { autocompletion, completionKeymap, CompletionContext, CompletionResult, acceptCompletion } from '@codemirror/autocomplete'; import { indentMore } from '@codemirror/commands'; import type { DesignerSection } from '../types'; import { toSnakeCase } from './useCodeGeneration'; @@ -147,6 +147,25 @@ export function usePolarsAutocompletion(getSections: () => DesignerSection[]) { const beforeCursor = context.state.doc.sliceString(0, context.pos); const sections = getSections(); + // Check for SecretStr method completion (after .secret_value.) + const secretStrMethodMatch = beforeCursor.match(/\.secret_value\.(\w*)$/); + if (secretStrMethodMatch) { + const typed = secretStrMethodMatch[1]; + return { + from: context.pos - typed.length, + options: [ + { + label: 'get_secret_value', + type: 'method', + info: 'Get the decrypted secret value as a string', + apply: 'get_secret_value()', + detail: 'SecretStr', + }, + ], + validFor: /^\w*$/, + }; + } + // Check for ".value" or ".secret_value" completion after a component field for (const section of sections) { const sectionName = section.name || toSnakeCase(section.title || 'section'); @@ -286,6 +305,7 @@ export function usePolarsAutocompletion(getSections: () => DesignerSection[]) { defaultKeymap: false, closeOnBlur: false, }), + keymap.of(completionKeymap), tabKeymap, ]; diff --git a/flowfile_frontend/src/renderer/styles/main.css b/flowfile_frontend/src/renderer/styles/main.css index 450228960..51131df75 100644 --- a/flowfile_frontend/src/renderer/styles/main.css +++ b/flowfile_frontend/src/renderer/styles/main.css @@ -506,9 +506,12 @@ button { background-color: var(--color-background-hover) !important; } -.cm-editor .cm-selectionBackground, +.cm-editor .cm-selectionBackground { + background-color: rgba(8, 145, 178, 0.15) !important; +} + .cm-editor.cm-focused .cm-selectionBackground { - background-color: var(--color-background-selected) !important; + background-color: rgba(8, 145, 178, 0.25) !important; } /* Placeholder styling */ From 13e52091328e085487b2e4773e25eedcaaeb8b92 Mon Sep 17 00:00:00 2001 From: Claude Date: Sun, 4 Jan 2026 13:55:09 +0000 Subject: [PATCH 2/5] Add help modal to process code editor - Create ProcessCodeHelpModal.vue with comprehensive documentation: - Overview of the process method - Method signature and inputs explanation - How to access settings from UI components - Working with SecretStr and get_secret_value() - Common Polars patterns (filter, select, add column, aggregate) - Keyboard shortcuts for the code editor - Add help button (?) to ProcessCodeEditor header - Help modal uses existing modal pattern and styling --- .../pages/nodeDesigner/ProcessCodeEditor.vue | 49 ++- .../nodeDesigner/ProcessCodeHelpModal.vue | 303 ++++++++++++++++++ 2 files changed, 349 insertions(+), 3 deletions(-) create mode 100644 flowfile_frontend/src/renderer/app/pages/nodeDesigner/ProcessCodeHelpModal.vue diff --git a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/ProcessCodeEditor.vue b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/ProcessCodeEditor.vue index 726d6b36c..c368b7ad8 100644 --- a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/ProcessCodeEditor.vue +++ b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/ProcessCodeEditor.vue @@ -1,6 +1,11 @@ From cfb028f2fd80fe55a2d126749a2ac143f7433b56 Mon Sep 17 00:00:00 2001 From: Claude Date: Sun, 4 Jan 2026 14:01:15 +0000 Subject: [PATCH 3/5] Fix code editor UX issues - Fix arrow key navigation in autocomplete by using defaultKeymap: true and Prec.highest for custom Tab handling - Add SecretStr variable detection: when a variable is typed as SecretStr (e.g., `my_var: SecretStr = ...`), typing `my_var.` suggests get_secret_value() - Make help button more prominent with accent color background and "Help" text --- .../features/designer/editor/pythonEditor.vue | 9 ++- .../pages/nodeDesigner/ProcessCodeEditor.vue | 21 ++++--- .../composables/usePolarsAutocompletion.ts | 56 ++++++++++++++----- 3 files changed, 57 insertions(+), 29 deletions(-) diff --git a/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue b/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue index b6cd55126..da76649e1 100644 --- a/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue +++ b/flowfile_frontend/src/renderer/app/features/designer/editor/pythonEditor.vue @@ -20,12 +20,12 @@ + + diff --git a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts index c19043f3d..03565e0d6 100644 --- a/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts +++ b/flowfile_frontend/src/renderer/app/pages/nodeDesigner/composables/usePolarsAutocompletion.ts @@ -6,7 +6,7 @@ import { EditorState, Extension, Prec } from '@codemirror/state'; import { python } from '@codemirror/lang-python'; import { oneDark } from '@codemirror/theme-one-dark'; import { autocompletion, completionKeymap, CompletionContext, CompletionResult, acceptCompletion } from '@codemirror/autocomplete'; -import { indentMore } from '@codemirror/commands'; +import { indentMore, indentLess } from '@codemirror/commands'; import type { DesignerSection } from '../types'; import { toSnakeCase } from './useCodeGeneration'; @@ -312,7 +312,7 @@ export function usePolarsAutocompletion(getSections: () => DesignerSection[]) { }; } - // Tab keymap for accepting completions + // Tab keymap for accepting completions and indentation const tabKeymap = keymap.of([ { key: 'Tab', @@ -323,6 +323,12 @@ export function usePolarsAutocompletion(getSections: () => DesignerSection[]) { return indentMore(view); }, }, + { + key: 'Shift-Tab', + run: (view: EditorView): boolean => { + return indentLess(view); + }, + }, ]); // CodeMirror extensions for editing