Skip to content

feat(map-ai): repair round for rejected ops, and accept dominant-baseline (PPT-2832) - #458

Merged
camreeves merged 3 commits into
masterfrom
fix/PPT-2832-dominant-baseline
Oct 21, 2026
Merged

camreeves merged 3 commits into
masterfrom
fix/PPT-2832-dominant-baseline

Conversation

@camreeves

@camreeves camreeves commented Oct 21, 2026 •

Copy link
Copy Markdown
Contributor

Two fixes from testing map editing on placeos-dev on 21 Oct, using five models.

1. Accept dominant-baseline on inserted text. GPT-6.1 sol adds dominant-baseline="middle" to every label it inserts, and the server rejected every one even though the positions were right: 4 of 4 labels, twice. The attribute is now on the allowlist, and its value must be one of the SVG 2 keywords or text-before-edge/text-after-edge. ops-schema.json is kept identical to the editor's copy.

2. One repair round inside the job. When the server rejects some of an answer's ops, the runner makes one more call. It sends the same request plus the previous ops (with their op-N ids) and the reason each was rejected, and asks for the whole proposal corrected. The second answer replaces the first only if it is complete, parses, keeps at least as many accepted ops, and has fewer rejected. If anything goes wrong with that call, the first answer stands. The job response gains repair: {rejected, remaining, used} (also in OPENAPI_DOC). It's one job and one unit of quota, and an answer that passes the first time costs nothing extra. MAP_AI_REPAIR=false turns it off.

3. The server now checks the editor's parent/after rule, so the repair round can see that mistake too. after must be a direct child of parent (the root when none is named), and a parent must be the root or a <g>. gpt-5.4-mini broke this with every label it inserted, and until now only the browser caught it. The check steps aside when the index cannot settle it: elements made earlier in the batch, an after deleted earlier in it (the editor then places the new element where the deleted one was), or a tree reshaped by reorder, group, ungroup or replace_element.

The browser still validates every op as before. The repair round only changes which answer reaches it.

Specs: spec/llm_prompt_spec.cr and spec/controllers/map_ai_spec.cr, 66 examples, 0 failures, run locally in the spec container. They cover:

  • the new check cases and the cases where it steps aside;
  • the repair prompt;
  • the repaired answer used, rejected, and not asked for.

Not yet measured with a live model: how often the second answer actually fixes things. I'll check on placeos-dev once this is deployed.

The editor side is PlaceOS/user-interfaces#600.

🤖 Generated with Claude Code

GPT-6.1 sol adds dominant-baseline="middle" to every label it inserts.
The server rejected the attribute, so each such insert failed even
though its position was right. Testing on placeos-dev on 21 Oct lost
4 of 4 labels on both runs.

The value is limited to the SVG 2 keywords plus text-before-edge and
text-after-edge. ops-schema.json stays identical to the editor's copy
in user-interfaces.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@github-actions github-actions Bot added the type: bug something isn't working label Oct 21, 2026
…s (PPT-2832)

When the server rejects some of an answer's ops, the runner now makes one
more call inside the same job. It sends the same request plus the answer's
ops and the reason for each rejection, and asks for the whole proposal
corrected. The second answer replaces the first only if it is complete,
parses, keeps at least as many accepted ops, and has fewer rejected. If
that call fails, the first answer stands. The job's `repair` field records
how many ops were rejected, how many remain and whether the answer was
replaced. MAP_AI_REPAIR=false turns it off.

The server now also checks the parent/after rule the editor applies:
`after` must be a direct child of `parent` (the root when none is named),
and a parent must be the root or a <g>. On placeos-dev, gpt-5.4-mini
broke this with every label it inserted, and only the browser caught it,
so no repair round could have fixed it. The check steps aside where the
index cannot settle it: elements made earlier in the batch, an `after`
deleted earlier in it, or a tree reshaped by reorder, group, ungroup or
replace_element.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@camreeves camreeves changed the title fix(map-ai): accept dominant-baseline on inserted text (PPT-2832) feat(map-ai): repair round for rejected ops, and accept dominant-baseline (PPT-2832) Oct 21, 2026
@github-actions github-actions Bot added type: bug something isn't working type: enhancement new feature or request and removed type: bug something isn't working labels Oct 21, 2026
…2832)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@camreeves
camreeves merged commit a91f6da into master Oct 21, 2026
11 checks passed
@camreeves
camreeves deleted the fix/PPT-2832-dominant-baseline branch October 21, 2026 02:15
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

type: enhancement new feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant