Pre-Action Grounding Guard
guardrail scans text for prompt-injection and loop_guard detects stuck loops —
but neither validates a coordinate action before it is dispatched. An agent loop
executes whatever the model returns with no bounds or target check, so a hallucinated
(9999, -5) click fires into nothing and a 5-pixel-off click misses the button.
validate_action adds the “detect misaligned actions before execution” guard: reject
clicks outside the screen and snap a near-miss coordinate onto the nearest known
element’s centre.
Pure-stdlib geometry over plain element dicts (x / y / width / height),
so it is fully unit-testable. Imports no PySide6.
Headless API
from je_auto_control import validate_action, snap_to_element, in_bounds
check = validate_action(model_action, screen_size=(1920, 1080), targets=elements)
if not check["ok"]:
print("rejected:", check["reason"]) # e.g. "out of bounds"
else:
x, y = check["snapped"] or (model_action["x"], model_action["y"])
click(x, y) # snapped onto the real button
in_bounds(x, y, screen_size) is the screen-bounds predicate; snap_to_element
returns the centre of the element at (or nearest within max_dist of) a point, or
None; validate_action combines them, returning {ok, reason, snapped} —
rejecting out-of-bounds coordinates and snapping near-misses when targets are
supplied. Actions without a coordinate always pass.
Executor command
AC_validate_action (action / screen / targets → {ok, reason,
snapped}; screen defaults to the live screen). It is exposed as the MCP tool
ac_validate_action and as a Script Builder command under Native UI.