Repository navigation
feat(workflow): inputs checked at start (#3a) - #762
Merged
Merged
Conversation
…at start Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Add validator, min, max, after, before, values, expression, allowCustomValue, isRadio, autoSelectFirst and jsonSchema to Input so a Kestra flow round-trips verbatim, and stop warning not_honoured for them. FORM inputs and REUSABLE_INPUTS ref stay warned. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…odule `inputs_check::resolve` takes the flow's declared inputs and the posted object and returns the coerced object or the first error in declared order, with Kestra's message texts (spec D1-D5, D9, D10). Covers required, the empty-string rule, STRING/SECRET validator (fancy-regex, full match, backtrack limit), INT, FLOAT, BOOL (strict), DATETIME, DATE, TIME, DURATION, URI, EMAIL and SELECT. Collections, JSON/YAML/ION and dependsOn pass through until Task A3. Not wired into any start path yet. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…start Extend inputs_check: ARRAY and MULTISELECT parse each element with itemType and MULTISELECT checks every element against its values; JSON, YAML and ION are parsed; dependsOn inputs and condition decide which inputs are enabled (dependencies first, cycle-safe), through an InputRenderer the caller supplies; a SELECT/MULTISELECT expression gives the options and autoSelectFirst picks the first one. resolve_all lists every input's outcome for the validate endpoint. DATETIME, DATE, TIME and DURATION are now stored as posted, not in Java's normalised form. jsonSchema stays unchecked: no JSON Schema validator is in the dependency tree (spec D12), so its not_honoured warning is back and the treatment table measures it ignored. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Kestra's resolveInputs keeps the key with null; leaving it out fails
egret's strict renderer on {{ inputs.x }} once the start stores the
coerced object (valids/subflow-nullable-input-parent regressed).
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
start_execution_in_on runs inputs_check::resolve before secret_inputs::split (a SECRET validator sees the clear value) and stores the coerced object. A refusal is Error::InvalidInput (HTTP 400). Replays and Flow-trigger fires (flow_trigger_event_id set, born_failed included) are not checked, as Kestra. The Subflow child calls the same checker; a refusal fails the parent's run with 'subflow inputs: <message>'. Existing tests that posted undeclared keys or left a required input out now declare them. The start route's 400 description lists the new refusals; openapi.json and the client digest are regenerated. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
A3 measured JsonInput.jsonSchema `ignored` (spec D12: no JSON Schema validator) while models::Input still kept the key, so the flow schema no longer offered a field the model accepted and the_inputs_offer_exactly_the_fields_models_input_accepts failed. Take jsonSchema out of models::Input instead, like every other key egret ignores: the schema and the model agree again, the not_honoured warning naming package #3 stays (now pinned by a test), and the NO_EFFECT entry is no longer needed. Treatment counts are unchanged. The test's tail, which still asserted A1's keys were not offered, now asserts they are. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
Inputs package #3a (spec D11). At save and publish only (never the run gate), with Kestra's messages: - dependsOn naming an unknown input, and dependsOn cycles (FlowValidator.checkFlowInputsDependencyGraph, CycleDependency path); - defaults together with prefill (InputValidator); - a FILE default whose URI scheme is not file/nsfile, or that does not render or parse as a URI (FileInputValidator); - a STRING/SECRET validator that does not compile, with fancy-regex (RegexValidator: invalid pattern [<v>]). fancy-regex refuses the lone backslash of invalids/inputs-bad-validator-syntax as Java does. "defaults needs required: true" is deliberately not added (D11). Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…Start The oracle driver returns Ran::StartRefused for a start that fails with Error::InvalidInput instead of Broken. The ratchet matches it against a golden refused entry only through a Seam::Start group, comparing egret's lines with the 422 recorded in corpus.json as a multiset (Kestra reports in HashSet order) and requiring the group's prefix on every line. Banks invalids/inputs-with-multiple-constraint-violations (Seam::Start) and invalids/inputs-bad-validator-syntax (Seam::Save, input_validator_invalid); their STILL_OVER_ACCEPTED, UNATTRIBUTED and baseline rows are gone. Ratchet 301/50/52/2 -> 301/50/50/0; census unchanged (295 live, 25 validate-refused, 21 unknown type). handler-surface regenerated (ceiling 281 -> 283). Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…d roadmap row Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
… at save An INT/FLOAT/DURATION min or max, or a DATETIME/DATE/TIME after or before, that does not parse was accepted at save and then refused every start that gave the input a value, with a message that blamed the posted value. Kestra's bound fields are typed, so Jackson refuses such a flow when it reads it. Add the save-only finding `input_bound_invalid` (not the run gate), built on the same parsers the start check uses. A non-integral INT bound, which Jackson's ACCEPT_FLOAT_AS_INT would truncate, is refused instead (recorded divergence); the start check keeps failing closed on a stored one. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
… its meaning The start check wrapped the validator as `\A(?:v)\z` while save compiled `v` alone. An extended-mode `#` comment swallowed the wrapper's `)\z`, so `(?x) [a-z]+ # letters` saved clean and refused every start; and a stored `abc)|(?:.*` wrapped to a pattern that accepted every value. `inputs_check::anchored_validator` now compiles the pattern as written first (as Java does), then the anchored form, putting a newline before the closing `)\z` only when `v`'s last line holds a comment. Save and start both call it. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
… it once The start check stored a JSON input's parsed value, and the render's `with_declared_defaults` still read any string of a JSON input as JSON text. A JSON string posted as `"123"` was stored as the string 123 and rendered as the number 123 (likewise `"true"` and `"[1,2]"`), the double parse the run form's `wireValue` exists to avoid. A JSON input whose parsed value is a string is now stored as that string's JSON text: the render reads it back to the string, and a re-check stores the same thing again. Every other value is stored as parsed, so rows written before the check render as they did. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
The backfill create route checked only `required`, so a value every tick would refuse (an INT below its `min`, a schedule's `n: abc`) was accepted and the backfill ended at its first tick. Create now also runs `checked_inputs` on the schedule's inputs overlaid by the backfill's (the map each tick checks) and refuses with the start check's text. The existing object/FILE/templated/required checks and their messages are unchanged. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
…llow-ups Spec (EN+VI): D1 no longer mentions a clock; D7's idempotence sentence names the JSON-string storage that makes it hold; section 7 records the bound finding (and the ACCEPT_FLOAT_AS_INT divergence), the validator anchoring, the JSON-string storage, the backfill create check, and that YAML/ION text inputs of live flows now store and render as parsed objects; section 6 records review findings M3, M4, M5 and M8 as follow-ups. Plan (EN+VI): the SECRET-masking note for the validate endpoint under B1 and the stale DATETIME/DURATION note under A2. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
4 tasks done
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Roadmap package #3a: workflow inputs are checked when an execution starts, as Kestra does, instead of failing later at render.
inputs_check(required, empty-string rule, STRING/SECRETvalidatorvia fancy-regex, INT/FLOAT/BOOL, DATETIME/DATE/TIME/DURATION bounds, URI/EMAIL/JSON/YAML/ION, ARRAY/MULTISELECT, SELECTvalues,dependsOn,expression,autoSelectFirst) with Kestra's message texts.dependsOn,defaults+prefill, FILEdefaultsscheme, badvalidator, bad bound). Save/publish only; stored versions keep running.Seam::Start; banksinvalids/inputs-with-multiple-constraint-violationsandinvalids/inputs-bad-validator-syntax. Ratchet 301 / 52 / 52 / 0 -> 301 / 50 / 50 / 0.Divergences (all recorded in the spec): BOOL is strict, FLOAT refuses NaN/Infinity, status 400 not 422, Flow-trigger inputs unchecked, SELECT checks
valuesonly when required (Kestra's quirk),jsonSchemastill unchecked (no JSON Schema crate in the tree), non-integral INT bounds refused at save.Behaviour changes to note: an optional input nobody posts is stored as
null; undeclared keys are dropped; YAML/ION text inputs now render as parsed objects.Not in this PR (#3b): the
validateendpoint and the run form. No user-docs PR yet (notes ready foregret-data/docs).Test plan
cargo test -p egret-workflow(only the 7sql_starrocks_livefail: they need StarRocks)cargo test -p egret-config -p egret-server(drift tests)cargo fmt --check,cargo clippy -D warnings🤖 Generated with Claude Code