Workflow Assistant

A guided, visual process planner. Build (or load) a named sequence of SASpro commands arranged into one or more parallel lanes — main, starless, stars, merge, whatever structure the processing calls for — and step through them manually, one tool at a time. Each step opens its tool when you ask, with its captured preset pre-loaded if one was dragged in; marking a step complete adds a ✓ prefix and advances to the next. Comes with four canned workflows for common beginner paths (OSC, mono RGB, mono narrowband, Cosmic Clarity cleanup) and a compact mini-runner for executing a workflow without the full editing UI.

Workflow
Open Workflow Assistant. Either pick a canned workflow from the Add Canned Workflow menu or build your own: drag tools from the catalog on the left into any lane on the right, add lanes for parallel branches, drop in notes and split/merge markers to document the flow. Open Step (or double-click a step) launches that tool — with any captured preset pre-loaded. Mark Complete flags the step done and bolds the next one. Save stores the workflow as a named JSON file; the active workflow is autosaved on close and restored when you reopen the dialog. Run Workflow opens the compact mini-runner that shows the lanes without the editing controls.

Workflow Assistant complements Function Bundles rather than duplicating it. Function Bundles automate — a bundle runs its steps back-to-back, waiting on each one to complete before the next starts. Workflow Assistant guides — it shows what to do, in what order, with what settings, but each step waits for the user to actually open the tool and work it. The signature move is the multi-lane layout: horizontal lanes make the parallel structure of a complex workflow (process the starless masters down one lane, the stars-only masters down another, merge at the end) visible at a glance, with split and merge markers calling out exactly where branches diverge and reconverge. This is the training-wheels tool — it lets a beginner follow a trusted recipe step by step, and lets a mentor share a workflow (with specific tool settings baked in) that a student can walk through unassisted.

Contents
1. The workflow concept
2. The tool catalog
3. Lanes
4. Adding and editing steps
5. Step kinds
6. The step details panel
7. Running steps and progress
8. The mini runner
9. Load, save, and autosave
10. Canned workflows
11. Technical details

1. The workflow concept

A workflow is a named, ordered sequence of steps grouped into one or more lanes. A lane is a vertical column of steps that execute in order; multiple lanes side by side represent parallel branches of the processing. Every workflow has at least one lane (named main by default) and can grow to any number of lanes as the processing demands.

A step is either an action (runs a specific SASpro command when you tell it to), a note (📝 — instruction-only, nothing to launch), a split marker (⇢ — shows where processing branches into multiple lanes), or a merge marker (⇠ — shows where branches rejoin). Action steps can carry a preset — a captured dictionary of tool settings — so “run Statistical Stretch” can become “run Statistical Stretch with these specific settings loaded in the dialog.”

Steps can also declare named inputs and outputs for lineage. These are free-form string tags (starless, stars_only, rgb_stars, palette_starless, …) that show up in the step details panel to document how data flows across the lanes. The runner doesn't enforce them — they're documentation, not routing — but a lineage you can see is far easier to follow than one you have to reconstruct from memory.

The whole thing is a visible, editable, executable checklist. You open each step when you're ready, you mark it complete when the result is good, and the dialog remembers your progress and position across lanes until you reset.

2. The tool catalog

The left panel lists every SASpro command that's available as a draggable step source. Three categories of entries land here automatically:

Each entry carries the tool's icon, display text, and status tip for hover tooltips. The search box at the top filters by text and tooltip in real time — type a few letters and the tree collapses to matching leaves (categories with no visible children also hide).

Drag any entry out of the tree onto a lane list to add it as an action step; double-click a leaf to add it to the currently active lane without having to drag.

3. Lanes

Lane controls sit above the lane cards:

Each lane is a vertical card with a header label and a step list below. The lane area scrolls horizontally when there's more lane than fits, so a four-lane narrowband workflow sits comfortably in a 1400 px dialog.

Cross-lane selection is single-select across the whole dialog. Clicking a step in lane B clears the selection and current item in every other lane. This keeps “the current step” a single, unambiguous thing — Previous Step and Next Step walk a flat sequence across all lanes in order, and the step details panel always reflects exactly one step.

4. Adding and editing steps

Four ways to add an action step:

Dropping a Function Bundle payload onto a lane doesn't nest the bundle — it expands into one step per inner step. This matches how the shortcut canvas explodes bundles into their constituents, so a bundle built elsewhere can be used as a starter kit for a workflow.

Three ways to add a non-action step (notes, markers):

Editing a step (right-click on it, or use the toolbar buttons):

Reordering: drag a step within its lane or across to another lane. Qt's internal-move drag handles the heavy lifting; the workflow model is re-synced from the UI after every drop so the saved order matches what you see.

5. Step kinds

Four kinds, picked by the step's kind field:

KindPrefixPurposeOpens a tool?
action(none, or ◆ with preset)Runs a specific SASpro command when opened.Yes
note📝Instruction-only step. Carries a note describing what the user should do next.No
split⇢Visual branch marker. Documents where processing diverges into multiple lanes.No
merge⇠Visual merge marker. Documents where multiple lanes come back together.No

Note, split, and merge steps can still carry inputs and outputs annotations — the narrowband canned workflow uses split and merge markers to call out the branch and the rejoin, with named outputs on the split (starless, stars_only) and named inputs on the merge (starless_final, stars_final).

Opening a non-action step shows a brief information dialog that describes what kind of marker it is. In the mini runner, opening a note step shows the step's actual note text, so the mini runner can act as a “follow this instruction” prompt even for non-action steps.

6. The step details panel

Below the lanes sits a panel that shows the full details of whichever step is currently selected:

Everything is HTML-formatted inline, so the panel reads like a short field notebook entry rather than a static form.

7. Running steps and progress

Four buttons drive execution:

The runner does not wait for the tool you opened to finish. It launches the tool and returns immediately. This is deliberate — Workflow Assistant is a guided walkthrough, not an auto-runner. You open the tool, you do the work, you Mark Complete when you're happy with the result. If you want sequential auto-execution with per-step completion waits, use Function Bundles instead.

Completion state lives on each step as a Qt.UserRole + 7 flag — it's a session state, not saved into the workflow JSON. Reopening a saved workflow starts everything uncompleted; completion resets on New Workflow, on Load, on Clear Workflow, and on Reset Progress.

8. The mini runner

The Run Workflow button at the bottom of the dialog opens a Mini Workflow Dialog — a compact execution-only view of the current workflow. It shows the same lanes with the same steps, but strips the editing controls (no catalog panel, no lane management, no edit buttons). You get a title bar, the lanes themselves, the step details panel, and five buttons: Previous, Open Step, Mark Complete, Next, Reset Progress.

The mini runner's Mark Complete automatically moves to the next step. This makes it feel more like a wizard than an editor — open the tool, do the work, hit Mark Complete, the next step is already highlighted and ready.

The mini runner can also be launched directly without opening the full editor via show_mini_workflow_dialog(main):

Only one mini runner lives at a time — opening a new one closes any existing one, so you don't accumulate instances by accident.

9. Load, save, and autosave

Workflows save to the SASpro user data directory:

<user_data>/workflows/<name>.json

The user data directory is discovered via the main window's get_user_data_dir, _user_data_dir, or user_data_dir (whichever exists); if none is available, the fallback is ~/.setiastro/saspro/workflows/. The file is a UTF-8 JSON document with the full workflow definition — name, description, lanes, every step with its preset, I/O, note, kind, and label override.

Three save/load entry points:

Load silently migrates legacy schema v1 workflows (flat step list, no lanes) into the current v2 shape by moving every step into a single main lane. The migrated workflow saves back in v2 shape the next time you hit Save.

Autosave

Every close of the dialog writes the current workflow to _autosave_last_session.json in the workflows directory. Opening the dialog restores it on the next launch — but only if there's actually something to restore (non-empty step list, or a non-default name). An empty untitled autosave is treated as a no-op so you don't end up with a stale blank workflow greeting you every launch.

Autosave is deliberately silent (any exception is swallowed) so closing can never fail because of disk issues or permission problems.

10. Canned workflows

The Add Canned Workflow dropdown offers four ready-made templates. Picking one replaces the current workflow entirely.

All four canned workflows carry per-step notes describing what each step is for and why it's where it is. They're meant to be starting points — load one, rename it, add or remove steps as the data demands, and save under your own name.

11. Technical details

Internal mechanisms numbered continuing from the usage sections.

12. Data model and schema versions

A workflow is a WorkflowDefinition:

WorkflowDefinition = { "schema_version": 2, "name": "My Workflow", "description": "…", "lanes": [ "main", "starless", "stars", "merge" ], "steps": [ WorkflowStep, … ], } WorkflowStep = { "id": "a3f1b2c4d5e6", # uuid4 hex, first 12 chars "command_id": "stretch_statistical", "note": "Stretch to non-linear.", "enabled": true, "kind": "action", # action | note | split | merge "lane": "main", "inputs": [ "aligned" ], "outputs": [ "stretched" ], "preset": { … }, # captured tool settings "label_override": "", # user-renamed display label }

Schema v1 was a flat step list with no lanes or I/O. The loader detects v1 by the absence of a top-level lanes key and migrates by: dropping every step into a single main lane, synthesising fresh step ids, forcing kind = "action", dropping any inputs/outputs/presets (which v1 didn't support), and tagging the result schema_version = 1 so the next Save upgrades it in place.

13. Toolbar and script catalog discovery

The tool catalog is rebuilt every time the dialog opens via two scanners:

Categories are sorted by a three-tier key: a preferred order list first (Functions, Cosmic Clarity, Tools, Geometry, Star Stuff, Masks, What's In My…, Bundles, View, Scripts), then Scripts/* subcategories alphabetically, then everything else alphabetically. The search box filters by matching both the action text and its tooltip, case-insensitive.

14. MIME payload types and function-bundle expansion

The lane list accepts two MIME formats:

When the MIME_CMD payload has command_id == "function_bundle", the drop handler walks the inner steps array and adds one action step per element, each with its own command id and preset. This mirrors the shortcut canvas's own bundle-expansion behaviour (add_shortcut_from_payload / _add_shortcuts_from_steps) so the UX is consistent across drop targets.

15. Cross-lane single-selection coordination

Qt's QListWidget maintains independent selection state per widget — by default, selecting an item in lane B wouldn't clear the selection in lane A. Workflow Assistant forces single-selection across all lanes with a cross-list coordinator.

When any lane's selection changes, _on_any_step_selected walks every other lane list and clears its selection, current row, and current item — signals blocked during the clear so no recursive callbacks fire. It also clears the selection model's own cached selection and current index to be sure Qt doesn't restore the old state on a repaint.

The “current lane” is then set to the lane whose selection just changed, and both the step details panel and the lane visual refresh (bolding the current step, applying ✓ prefixes) run against the new unique selection.

16. Preset-aware label derivation

Dragging a preset-bearing shortcut tile into a workflow captures both the command id and the preset. Several commands dispatch to different underlying tools based on preset content — rcastro runs BXT/SXT/NXT depending on preset["product"]; cosmic_clarity runs Sharpen/Denoise/Both/Super-Res based on preset["mode"]; syqontools picks between Prism Denoise / Parallax / Starless on preset["family"]. A plain “RC-Astro” step label would be useless in those cases.

_derive_step_label handles these cases explicitly:

rcastro + product=bxt → "BlurXTerminator" cosmic_clarity + mode=sharpen → "Cosmic Clarity — Sharpen" syqontools + family=denoise → "SyQon — Prism Denoise" fx + effect=soft_glow → "FX — Soft Glow" remove_stars + tool=starnet → "Remove Stars — StarNet"

The derivation runs when a preset-bearing step is added and the drop didn't come with its own explicit name. The result goes into the step's label_override, so it survives save/load and shows up in both the main dialog and the mini runner. A user Rename still wins — manual overrides are preserved over derived ones.

17. Preset-seeded step opener

When Open Step runs on a preset-bearing action step, the runner tries _preset_opener_for_command(command_id) from setiastro.saspro.shortcuts first. This returns a callable (or None) that knows how to open the specific tool with the preset pre-loaded — typically by constructing the dialog, iterating the preset keys, and setting the matching widget state directly.

If a preset-bearing opener is registered, it's called with (main_window, preset_dict). If no opener is registered (or the import fails), the runner falls back to the plain-action path: find the QAction by command id and trigger() it, which opens the tool with its own default state. The user then has to re-apply their saved settings manually — the preset is still visible in the step details panel so they can read it off.

18. Autosave and session restore

Autosave triggers on closeEvent of the dialog — the current workflow is synced from the UI, name and description are refreshed from the editable fields, and the whole thing serialises to _autosave_last_session.json in the workflows directory. The autosave is wrapped in a bare try/except that swallows every exception; closing the dialog must never fail because of a save issue.

Session restore runs after dialog construction, in _restore_autosaved_session. The autosave file is read, parsed with WorkflowDefinition.from_dict, and the result is loaded only if it has substantive content — either a non-empty steps list or a non-default name. An untitled autosave with zero steps is treated as nothing to restore, which prevents a stale blank workflow from reappearing every launch.

The autosave file lives alongside named user workflows in the workflows directory but prefixed with an underscore to sort it out of the way of the Load dialog's typical browse order.

Credits

Workflow Assistant is a workflow / mentoring tool for SetiAstro Suite Pro by Franklin Marek. It builds on standard SASpro machinery: the toolbar & QAction system (every action auto-discoverable by command_id property), the ScriptManager registry (recursive script discovery), the SASpro shortcut MIME protocol (MIME_CMD) and the shortcut-canvas's preset-opener dispatch (_preset_opener_for_command, _open_preset_editor_for_command). The canned workflows are curated beginner recipes; the multi-lane visual layout, split/merge markers, and I/O lineage annotations are new design work for this tool. There are no external algorithmic references — this tool orchestrates SASpro's existing commands rather than introducing new image-processing primitives. Qt and PyQt6 provide the UI framework, drag-and-drop infrastructure, and JSON serialisation.