Skip to content

chore: promote staging to staging-promote/fcb295ba-24607448875 (2026-04-18 20:30 UTC)#2657

Open
ironclaw-ci[bot] wants to merge 3 commits intostaging-promote/fcb295ba-24607448875from
staging-promote/11f00698-24612972670
Open

chore: promote staging to staging-promote/fcb295ba-24607448875 (2026-04-18 20:30 UTC)#2657
ironclaw-ci[bot] wants to merge 3 commits intostaging-promote/fcb295ba-24607448875from
staging-promote/11f00698-24612972670

Conversation

@ironclaw-ci
Copy link
Copy Markdown
Contributor

@ironclaw-ci ironclaw-ci bot commented Apr 18, 2026

Auto-promotion from staging CI

Batch range: a53eac5c2dec6b6cd5c08189086093fde64aa9cb..11f006987d29174db4df1515fd4e9f2c1a12eac9
Promotion branch: staging-promote/11f00698-24612972670
Base: staging-promote/fcb295ba-24607448875
Triggered by: Staging CI batch at 2026-04-18 20:30 UTC

Commits in this batch (121):

Current commits in this promotion (3)

Current base: staging-promote/fcb295ba-24607448875
Current head: staging-promote/11f00698-24612972670
Current range: origin/staging-promote/fcb295ba-24607448875..origin/staging-promote/11f00698-24612972670

Auto-updated by staging promotion metadata workflow

Waiting for gates:

  • Tests: pending
  • E2E: pending
  • Claude Code review: pending (will post comments on this PR)

Auto-created by staging-ci workflow

serrrfirat and others added 3 commits April 18, 2026 22:59
* fix(engine): allow completed event-driven missions to re-fire on new events

The /expected command returned "no self-improvement missions configured"
after the learning mission's first thread completed, because:

1. fire_on_system_event() only processed Active missions, skipping
   Completed ones. Event-driven missions should re-fire since each
   event is a fresh investigation.
2. fire_mission() rejected all terminal missions via is_terminal().
   Now Completed event-driven missions pass through.
3. threads_today counter never reset daily, permanently exhausting
   the daily budget after enough fires.
4. ensure_learning_missions was only called for the owner at init,
   so non-owner users never got learning missions.

Fixes: add is_event_driven() helper on Mission, allow Completed
event-driven missions in all three event-fire methods, add daily
reset for threads_today when last_fire_at is on a previous UTC day,
and call ensure_learning_missions in handle_expected before firing.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: make daily reset persist best-effort (iteration 1)

The daily threads_today reset used `?` to propagate store errors,
which would abort fire_mission on a transient store failure. Changed
to log-and-continue so the in-memory reset still allows the mission
to fire.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix: resolve CI failures

- reduce WASM startup registration arguments via a context struct for clippy
- restore post-install auth gate naming and stabilize config tests
- make telegram approval fixture optional in tests
- add safety annotations for existing staged slice/expect patterns

---------

Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…2656)

Closes #2626.

`tests/e2e/helpers.py` used `.tab-bar button[data-tab="{tab}"]` to locate
every main-nav tab button. Commit 5058a1c removed the duplicate
right-side `status-logs-btn` Jobs button that was resolving that selector
to two elements on staging, so `test_connection.py` passes again. The
underlying selector is still fragile: any future auxiliary button or
`_addWidgetTab`-injected tab that reuses a built-in `data-tab` id (even
accidentally, as #2353 did) will make the selector resolve to multiple
elements and trip Playwright strict mode the next CI run.

Harden the selector in place — the issue's suggested direction of
scoping to a more specific parent region — so the regression can't
repeat without a test-side opt-in:

- `.tab-bar > button`: direct child, skipping any hypothetical nested
  buttons (e.g. menu popovers).
- `:not(.status-logs-btn)`: excludes the right-side logs/docs cluster
  that uses the same `data-tab` hook for click routing.
- `:not(.tab-btn)`: excludes widget-injected tabs (see `_addWidgetTab`
  in `crates/ironclaw_gateway/static/app.js`), which always carry the
  `tab-btn` class and could in principle collide with a built-in id.

Verified against a synthetic DOM with three colliding `data-tab="jobs"`
buttons (original, status-logs-btn duplicate, widget-injected): the old
selector matches 3 and trips strict mode on `.click()`; the new
selector matches 1 and clicks cleanly. No production HTML change is
required — the acceptance criterion explicitly forbids one.

`pytest tests/e2e/scenarios/test_connection.py -v` → 3 passed.
* fix(engine): make FINAL/FINAL_VAR awaitable in CodeAct scripts

LLMs frequently emit `await FINAL(answer)` by analogy with async tool
calls. The handler returned `MontyObject::None` synchronously, so the
subsequent `await` raised `TypeError: 'NoneType' object can't be
awaited` and the answer was dropped on the floor.

Route FINAL and FINAL_VAR through the existing `pending_futures`
mechanism with a trivially-resolving task. `final_answer` is set the
moment the call arrives, so both `FINAL(x)` (coroutine discarded) and
`await FINAL(x)` (resolves to None) succeed. Two regression tests in
`scripting::tests` pin both forms.

* fix(engine): normalize typographic punctuation before skill activation

iOS, macOS, and most rich-text inputs autocorrect `I'm` (ASCII U+0027)
to `I'm` (curly U+2019). Skill activation patterns like
`(?i)I'm a (CEO|...)` are authored with ASCII punctuation, so the
curly form silently failed to match — `ceo-setup` and any other skill
with apostrophes in its regex never activated for autocorrected input.

Add `normalize_punctuation()` in `default.py` that folds 8 typographic
quote variants and the en/em dashes to ASCII before scoring runs.
Implemented with chained `.replace()` because Monty does not expose
`str.maketrans`/`.translate()`. Runs once per turn on the goal text;
user content is untouched everywhere else.

Two regression tests under `executor::orchestrator::tests` drive
`normalize_punctuation` and `select_skills` end-to-end with the exact
ceo-setup pattern and a curly-apostrophe goal.

* docs(codeact): note closure capture quirk and Rust regex limits

Two recurring CodeAct failures got their own paragraphs in the
preamble:

- Function closures defined in one ```repl``` block do not reliably
  capture names (modules, top-level vars) defined in earlier blocks,
  producing spurious `NameError`. Authors must keep the helper, its
  imports, and its call sites in the same block.

- The embedded `re` is the Rust `regex` crate, not CPython: positional-
  only flag args, no lookaround, no backreferences. Lead with string
  methods (`in`, `startswith`, `splitlines`) and only reach for `re`
  when truly needed.

Pure docs change.

* fix(engine): adapt FINAL-await tests to staging CodeExecutionResult API

Replace `had_error` field references with `failure.is_none()` to match
the staging struct where `had_error: bool` was replaced by
`failure: Option<CodeExecutionFailure>`.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix(engine): address gemini-code-assist review — normalize before extraction, seed explicit skills (#2531)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix(skills): remove useless .into_iter() to satisfy clippy (#2531)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix(clippy): collapse nested if blocks into match guards (#2531)

Fixes collapsible_match lints in ironclaw_tui::render and
ironclaw_engine::runtime::mission triggered by Rust 1.95.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix(clippy): resolve collapsible_match and unnecessary_sort_by lints (#2531)

Fix 5 collapsible_match lints (responses_api, cli/tool, rig_adapter,
setup/prompts) and 2 unnecessary_sort_by lints (glob_tool, grep_tool)
triggered by Rust 1.95 clippy. Also fix rustfmt formatting for match
guards in render.rs.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

* fix(clippy): group wasm startup channel registration context

---------

Co-authored-by: Illia Polosukhin <ilblackdragon@gmail.com>
Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@github-actions github-actions bot added size: XL 500+ changed lines scope: channel/cli TUI / CLI channel scope: pairing Pairing mode scope: docs Documentation risk: low Changes to docs, tests, or low-risk modules contributor: core 20+ merged PRs and removed size: XL 500+ changed lines labels Apr 18, 2026
@claude
Copy link
Copy Markdown

claude bot commented Apr 18, 2026

No issues found.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

contributor: core 20+ merged PRs risk: low Changes to docs, tests, or low-risk modules scope: channel/cli TUI / CLI channel scope: docs Documentation scope: pairing Pairing mode staging-promotion

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant