Skip to content

feat(apps): add chat-status-tags builtin — SDLC + health tagging for dashboard chats - #7877

Open
billygerhard wants to merge 1 commit into
kirodotdev:mainfrom
billygerhard:feat/self-tag-app
Open

feat(apps): add chat-status-tags builtin — SDLC + health tagging for dashboard chats#7877
billygerhard wants to merge 1 commit into
kirodotdev:mainfrom
billygerhard:feat/self-tag-app

Conversation

@billygerhard

@billygerhard billygerhard commented Sep 2, 2026

Copy link
Copy Markdown
Contributor

Problem / Motivation

Dashboard chat tags go stale on their own: a chat that finishes review sits tagged review forever, a chat killed by a network drop just stops with no signal, and a hung chat looks identical to a working one. Keeping tags truthful is manual toil today, and errored/hung chats are easy to miss entirely.

Why it matters

Users running many parallel agent chats (the core KiroCrew workflow) triage by the sidebar. Stale or missing status means real failures hide among healthy chats — network-killed work silently stops overnight, and done work looks perpetually in-review. Automatic, truthful tags turn the sidebar into a reliable operations board.

What changed (motivation → approach → change)

New builtin app chat-status-tags (default-disabled). Four cooperating pieces, each the cheapest mechanism that can do its job:

  • Self-tag skill — agents tag their own chat's SDLC phase (plannedtodoimplementationreviewdone) via a bundled tag.sh that resolves the slot from the injected session key and exits 0 gracefully outside dashboard contexts.
  • Health sweep (free, always on) — a 60s in-process loop (direct store access, no loopback HTTP) tags terminal-error chats error and running-but-stale chats stuck, clearing health tags on resume. Zero tokens.
  • Auto-resume (toggleable) — network-killed chats are continued automatically once connectivity has been stable for a full probe window, capped per failure episode. Auth failures and unknown errors are never auto-resumed.
  • Hourly reconciler (toggleable) — an LLM cron promotes reviewdone from the real state of the PRs a chat owns (from slot source links), via a new chat_status_tags_api MCP tool with a narrow 4-call allowlist — it cannot send chat messages or read chat detail. A PR closed without merging is explicitly not done.
  • App page — editable reconcile prompt (delivered as the cron job's own message), cron status row with a repair button, and cost-labeled toggles for the two credit-spending behaviors.

Reviewer notes: the reconciler needs an authenticated gh CLI and tool approval (the install default); with interactive approval it degrades to a no-op. One entry pruned from .github/black-baseline.txt (mcp_tools/apps.py graduated to black-clean).

Tests

  • ~160 app-scoped tests: loops (health classification, stuck detection, resume caps), routes (prompt GET/PUT, cron repair, settings), MCP tool allowlist (the 4 permitted calls and rejection of everything else), package registration regression tests, and a pin that the shipped cron message stays byte-identical to the default prompt.
  • Full backend suite: 81,071 passed; all 108 failures pre-existing on main, zero in paths this PR touches.
  • Full frontend suite: 27,725 passed / 0 failed; tsc, i18n-check, manifest-sync, black gate green.

Manual verification

Multi-day hands-on testing in a live gateway: a merged PR promoted its chat to done end-to-end; a closed-unmerged PR correctly left the tag unchanged; exercised the prompt editor (save/reset/default badge), the cron repair button, and both automation toggles.

Screenshots / video

chat-status-tags app page — editable reconcile prompt, cron status row with repair button, and automation toggles

The same image ships as the app-store asset (website/public/app-assets/chat-status-tags/).

Related Issues

None.

@billygerhard
billygerhard requested a review from a team September 2, 2026 14:21
@billygerhard
billygerhard requested a review from a team as a code owner September 2, 2026 14:21
@github-actions github-actions Bot added fork Pull request from a fork (external contributor) readiness: action required A blocking check or review needs attention labels Sep 2, 2026
@github-actions github-actions Bot added readiness: checking Automated validation is still running readiness: action required A blocking check or review needs attention and removed readiness: action required A blocking check or review needs attention readiness: checking Automated validation is still running labels Sep 2, 2026
@billygerhard
billygerhard force-pushed the feat/self-tag-app branch 2 times, most recently from 9c55d2b to 22e757e Compare September 2, 2026 15:42
@github-actions github-actions Bot added readiness: checking Automated validation is still running readiness: action required A blocking check or review needs attention and removed readiness: action required A blocking check or review needs attention readiness: checking Automated validation is still running labels Sep 2, 2026
@github-actions github-actions Bot added readiness: checking Automated validation is still running and removed readiness: action required A blocking check or review needs attention labels Sep 2, 2026
@github-actions

github-actions Bot commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

Design Review (Fable 5, fork) — 🔴 BLOCK (blocking)

Design-level review of 6a9b356d15cec0ff0ab9eaaf9979acf593f7bf40 via the fork AI-review pipeline — updated in place on each push. A BLOCK verdict blocks PR readiness; PASS/CONCERNS are advisory.

Design-Verdict: BLOCK

The repo's built-in app set is closed by a blocking governance rule; this ships a new builtin whose own README proves the mandated external-app shape is feasible.

Blockers

  • New builtin app violates the closed-set rule. The diff adds src/kiro_crew/apps/builtins/chat_status_tags/ with a new app.json → AUTOSDE's no-new-builtin-apps (blocking) and AGENTS.md say "the built-in set is closed, and new apps ship as external apps through the KiroCrewApps registry" → the app rides the wheel into every install, can only be disabled, never uninstalled, and couples its fix cadence to Kiro Crew releases. The README's own "Portability" section describes the external packaging ("replace store.py's in-process access with the cron ScriptContext HTTP transport… register the two loops as zero-token script crons"), so the alternative is concrete and acknowledged. Fix: publish through the KiroCrewApps registry per that plan, or record an explicit maintainer override on the PR.

Watch

  • chat_status_tags_api diverges from the ops_mission_control_api precedent it cites: ops paths root at the app's own _require_enabled-gated routes, but this tool roots at core /api/chat, so with the app disabled (the shipped default) every agent in every session can still read all slots' metadata and rewrite any slot's tags. Gate the handler on is_app_enabled.
  • store.py binds the loops to private gateway internals (state._slots, state._tags, reg._app, chat_runner._run_chat) with no contract — a dashboard refactor breaks health tagging silently; this coupling only exists because of the builtin shape.
  • Description says the self-tag skill uses "a bundled tag.sh"; the shipped skill is deliberately script-free (MCP-tool-driven). Update the description.

[DESIGN-REVIEWED] 6a9b356

@github-actions

github-actions Bot commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

First Principles Review (Fable 5, fork) — 🔴 BLOCK

Premise-level review of 6a9b356d15cec0ff0ab9eaaf9979acf593f7bf40 via the fork AI-review pipeline — why this exists and whether the shipped surface is the smallest honest version. Updated in place on each push. A BLOCK verdict blocks PR readiness; PASS/CONCERNS are advisory.

All lenses are run; the evidence is collected. Final review:

First-Principles-Verdict: BLOCK

The whole app is real and well-aimed, but it ships as a new builtin — the one publishing path this repo's own blocking rule closes.

What this change ships

Intent: keep dashboard chat tags truthful (SDLC phase + health) without manual toil. ADDITION.

  1. New "Chat Status Tags" builtin in the App Store (default-off) — duplicate of the KiroCrewApps registry path
  2. Agents self-tag their chat's SDLC phase via a new self-tag-chat skill — justified
  3. New chat_status_tags_api MCP tool, 4-call allowlist — justified (token mint is deny-ruled)
  4. 60-second health sweep tags chats stuck/network/error, self-clearing — justified
  5. Network-killed chats auto-resumed, capped, toggleable — justified
  6. Hourly LLM cron promotes review→done from real PR merge state — justified
  7. App page's editable reconcile prompt + restart-survival sync machinery — inherited, no named operator need
  8. Cron repair button and two automation toggles — justified
  9. Eight tags seeded into the user's shared tag vocabulary on enable — undeclared
  10. Config keys stuck_min / probe_hosts — undeclared

Blockers

New builtin app directory. AUTOSDE.yaml's no-new-builtin-apps (blocking: true): "The set of built-in apps is CLOSED. A new app ships as an EXTERNAL app published through the KiroCrewApps registry… FLAG any PR that adds a new app directory under src/kiro_crew/apps/builtins/ (a new app.json)." This PR adds exactly that, and the description records no maintainer override. The author's own README "Portability" section already maps the external packaging: keep logic.py byte-identical, swap store.py for the cron ScriptContext HTTP transport, register the loops as script crons. Subtraction: ship it through the registry; nothing else in the PR needs to change shape.

Watch

  • Description drifts from the diff: it claims self-tagging works "via a bundled tag.sh", but the shipped skill is script-free (test_skill_is_credential_free pins "The predecessor shipped a tag.sh") — and the claimed .github/black-baseline.txt prune is absent (grepped the patch: 0 matches).
  • The editable reconcile prompt (item 7) is "for flexibility": no reported operator need, yet it drives ~120 lines of settings.py, two routes, and sync_prompt_to_job re-applied at startup, repair, and toggle-on solely to survive the manifest cron rebuild.
  • SKILL.md tells agents tags feed the "Board view" — a surface AGENTS.md records as removed from this fork.

Subtractions

  • Drop the query field from chat_status_tags_api (validation.py _CST_QUERY_RE, schema in mcp_tools/apps.py): its own description says "No allowlisted GET currently needs one" — 0 of the 4 allowlisted calls use it — and the truncation hint pointing at "a limit query on the slot detail" names a path outside the allowlist.
  • Defer the prompt editor: delete the prompt half of settings.py, GET/PUT /reconcile-prompt, and sync_prompt_to_job + its three resync call sites; the manifest message is the prompt.

[FIRST-PRINCIPLES-REVIEWED] 6a9b356

@github-actions

github-actions Bot commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

UX Review (Fable 5, fork) — 🟡 CONCERNS

UX-level review of 6a9b356d15cec0ff0ab9eaaf9979acf593f7bf40 via the fork AI-review pipeline — updated in place on each push. A BLOCK verdict blocks PR readiness; PASS/CONCERNS are advisory.

UX-Verdict: CONCERNS

Enabling the app silently starts recurring model spend, and the cron-status row asserts a failure it can't actually see while greying out the only fix.

Watch

  • Both paid automations default ON with no pre-enable disclosure. _FLAG_DEFAULTS = {"reconciler_enabled": True, "auto_resume_enabled": True} plus "cron_expr": "23 * * * *", "enabled": true means enabling from the App Store immediately starts an hourly LLM job and credit-spending auto-resume; the cost is stated only in reconciler_help/auto_resume_help, which a user reads after enabling — manifest.configuration_1 and the description never mention spend. Once per install × unbounded ongoing cost × recurring forever. Fix: name the hourly model spend in apps.chatStatusTags.manifest.configuration_1, or ship reconciler_enabled: False.
  • "Job is missing" is shown when the state is unknown, and Repair is dead. _cron_status returns present: False, schedulerUnavailable: True when the scheduler is unreachable; the page then renders cron_missing — "The reconciler's scheduled job is missing — the prompt will not run until it is repaired." — while disabled={repairing || cron.schedulerUnavailable} greys out Repair schedule with no reason given. The user gets a definite diagnosis that may be false and a dead end. Fix: branch cron.schedulerUnavailable to the scheduler_unavailable string the page already owns; keep cron_missing for !cron.present.
  • Raw backend strings are the user-facing error copy. {query.error.message}, {saveMutation.error.message} and {repairMutation.error.message} print the server's error field verbatim — "cron service unavailable", "prompt exceeds 20000 characters", "could not persist settings", or HTTP 500 from parseError's fallback — untranslated in a 12-language dashboard, with no next step. The same 503 shows localized copy on the toggle but the dev string on Repair. Fix: map status → catalog keys in the two .error.message render sites as errorText() already does.

Suggestions

  • Rename reconciler_label "Hourly reconciler" → "Hourly pull-request check" and prompt_label "Reconcile prompt" → "Hourly check instructions"; drop unexpanded "SDLC" from highlight_1 and use_case_1 (store copy sells the app to people who don't have the code open).
  • AutomationSection's if (query.isError || !query.data) return null deletes both spend switches with no message when only /settings fails — render the card with toggle_error instead, since this is the one place a user can stop spend.
  • Ship hero-light.svg/hero-dark.svg and declare them in app.json as all 22 sibling builtins do; today useHeroArt falls back to screenshot-main.svg, whose hardcoded #0f1117 renders as a dark block on a light-theme store card — and that asset shows the Chats sidebar, not the "editable reconcile prompt, cron status row with repair button, and automation toggles" the PR description captions it with.

[UX-REVIEWED] 6a9b356

@github-actions

github-actions Bot commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

GPT 5.6 Review (fork) — 🔴 changes requested (blocking)

Reviewed 6a9b356d15cec0ff0ab9eaaf9979acf593f7bf40 via the fork AI-review pipeline; updated in place on each push.

BLOCKING -- src/kiro_crew/apps/builtins/chat_status_tags/app.json:2 -- New built-in app violates the closed built-in set

"name": "chat-status-tags",
New built-in manifest -> bundled into every wheel -> prohibited distribution path.
Anchor: no-new-builtin-apps
Fix: Remove the built-in and publish it through the KiroCrewApps registry.

BLOCKING -- src/kiro_crew/mcp_tools/apps.py:157 -- Global core tool bypasses cross-chat authorization

"name": "chat_status_tags_api",
External content in any chat -> globally advertised core tool -> internal-secret GET of all slots or PUT of another slot’s tags.
Anchor: backend-security-controls
Fix: Remove this tool’s descriptor, handler, and schema from kirocrew-core.

BLOCKING -- src/kiro_crew/apps/builtins/chat_status_tags/hooks.py:224 -- Truncated history grants a second resume budget

ep = logic.next_episode(episodes.get(key), anchor)
Three failed resumes -> six-message tail loses the original anchor -> attempts reset -> three extra Continue turns.
Anchor: residual/crash-data-loss-corruption
Fix: When anchor is empty, retain the existing episode instead of resetting it.

BLOCKING -- src/kiro_crew/apps/builtins/chat_status_tags/hooks.py:245 -- Resume state performs filesystem I/O on the event loop (origin: validation)

episodes = _load_episodes(ctx)
_save_episodes(ctx, episodes)
Accumulated episode state -> minute loop directly reads/writes the file -> gateway event loop stalls on filesystem latency.
Anchor: no-blocking-call-on-event-loop
Fix: Run both calls through await asyncio.to_thread(...).

[BLOCK-MERGE] 6a9b356
[GPT-REVIEWED] 6a9b356

@github-actions

github-actions Bot commented Sep 3, 2026

Copy link
Copy Markdown
Contributor

Opus 4.8 Review (fork) — 🔴 changes requested (blocking)

Reviewed 6a9b356d15cec0ff0ab9eaaf9979acf593f7bf40 via the fork AI-review pipeline; updated in place on each push.

Only Candidate 1 is grounded. The MCP-tool reach (C2), hardcoded probes (C3), and reconcile-prompt (C4) are design/hardening opinions with the candidates' own low/medium confidence and no re-derivable concrete wrong outcome — C2 mirrors the existing ops_mission_control_api pattern with a frozen 4-call allowlist and redaction; C3 fails safe; C4 is speculative and gated by the shipped deny rules. None clears 80.

Candidate 1 is a clean, blocking AUTOSDE violation: a new app.json under src/kiro_crew/apps/builtins/ matches the blocking: true no-new-builtin-apps rule, and the fix (don't add the built-in) lives entirely in this diff.

BLOCKING — the PR adds a new built-in app, which the no-new-builtin-apps blocking rule forbids.

[BLOCK-MERGE] 6a9b356
BLOCKING — src/kiro_crew/apps/builtins/chat_status_tags/app.json:170
"name": "chat-status-tags", (new file, new directory src/kiro_crew/apps/builtins/chat_status_tags/)
New app directory + app.json under src/kiro_crew/apps/builtins/** → matches the base-snapshot no-new-builtin-apps rule (blocking: true) → a new built-in rides the wheel, growing every install and coupling the app's fix cadence to Kiro Crew releases; the built-in set is closed.
Fix: Publish Chat Status Tags as an external app through the KiroCrewApps registry instead of adding it under apps/builtins/; remove the new built-in directory from this diff.

[OPUS-REVIEWED] 6a9b356

@github-actions github-actions Bot added readiness: action required A blocking check or review needs attention and removed readiness: checking Automated validation is still running labels Sep 3, 2026
@billygerhard
billygerhard force-pushed the feat/self-tag-app branch 2 times, most recently from 5687ac9 to 64322e5 Compare September 3, 2026 00:43
@billygerhard

Copy link
Copy Markdown
Contributor Author

Addressed the review findings in 64322e59b (still one squashed commit):

GPT 5.6 + Opus findings fixed:

  • Token mint in bundled scriptstag.sh and untag_on_resume.sh are removed entirely. The self-tag skill is now a script-free, tool-driven procedure through chat_status_tags_api (the gateway holds the credential; nothing mints, prints, or handles a token). A new test pins the skill directory to SKILL.md only and greps it credential-free. The resume-clear script was redundant anyway — the 60s health sweep already clears health tags on recovery.
  • Resume cap reset (found by both reviewers) — episodes are now keyed on a failure anchor (the newest message that is neither an error card nor an injected resume turn) instead of the volatile last_ts, so attempts accumulate across resume cycles and the per-episode cap actually binds. Regression test drives a full failed-resume cycle and asserts the anchor holds, plus a real recovery re-keying it.
  • Health sweep clobbering concurrent tag edits — the write is now merge_slot_tags: the managed-subset merge runs against the live tag list inside the tags write lock, so a user edit landing between the sweep's read and its write is preserved. The exact-replace store write was removed (no callers). Tests cover live-merge, no-op, and missing-slot.
  • Swallowed toggle persistence failureset_flags now propagates the write failure; the route returns 500 settings_write_failed and rolls the cron mutation back, so stored flags and live automation can never silently diverge. Route test pins the 500 + rollback order.
  • Malformed stuck_min killing the health loop — parsed inside a guard now; degrades to the default with a warning. Test feeds "30m" and asserts the loop survives.
  • Case-collision KeyError in tag seeding (Opus) — the vocabulary map is keyed by name.strip().lower() on both scan and create read-back. Test seeds a pre-existing "Network" tag and asserts the sweep resolves it.
  • Temp-dir leaks in tests — every mkdtemp now registers addCleanup(shutil.rmtree, ...) immediately.
  • Stale allowlist comment in validation.py — updated to the four-call, no-detail reality.

Fork workflow guard — the PR no longer touches .github/ at all: instead of pruning the black baseline, mcp_tools/apps.py is now purely additive over upstream (its pre-existing formatting untouched), so the baseline stays as-is.

On the chat_status_tags_api ownership finding (GPT, not changed): the tool follows the same pattern as the shipped ops_mission_control_api — a globally-advertised, gateway-credentialed tool whose entire authorization surface is a frozen (method, path) allowlist defined next to its schema. Opus's validation pass reached the same conclusion ("mirrors the shipped governance pattern; could not re-derive that an ordinary session reaches it"). Its widest capability is replacing one slot's tag list with ids that must already exist in the vocabulary — it cannot read messages, send messages, or create chats. Happy to tighten further if a maintainer prefers a different gate.

@github-actions github-actions Bot added readiness: checking Automated validation is still running and removed readiness: action required A blocking check or review needs attention labels Sep 3, 2026
@github-actions github-actions Bot added readiness: action required A blocking check or review needs attention readiness: checking Automated validation is still running and removed readiness: checking Automated validation is still running readiness: action required A blocking check or review needs attention labels Sep 3, 2026
@github-actions github-actions Bot added readiness: action required A blocking check or review needs attention readiness: checking Automated validation is still running and removed readiness: checking Automated validation is still running readiness: action required A blocking check or review needs attention labels Sep 3, 2026
…dashboard chats

Adds a builtin app that keeps dashboard chat tags truthful end to end:

- Self-tag skill: agents tag their own chat's SDLC phase (planned/todo/
  implementation/review/done) at each transition via a bundled tag.sh.
- Zero-token health sweep (always on): a 60s in-process loop tags chats
  that hit a terminal error card or hang (running with stale activity),
  and clears health tags when a chat resumes.
- Auto-resume (toggleable): network-killed chats are continued
  automatically once connectivity is stable, capped per episode; auth
  and unknown errors are never auto-resumed.
- Hourly reconciler (toggleable): an LLM cron promotes review -> done
  from the real state of the PRs a chat owns, via a new
  chat_status_tags_api MCP tool with a 4-call read/tag allowlist (it
  cannot send messages or read chat detail). Closed-without-merge is
  explicitly not done.
- App page: editable reconcile prompt (delivered as the cron job's own
  message), cron status row with a repair button, and cost-labeled
  toggles for the two credit-spending behaviors.

Testing: full backend + frontend gate floor, ~160 app tests, and
multi-day hands-on testing in a live gateway including a merged-PR ->
done promotion and a closed-unmerged PR correctly left untouched.

Signed-off-by: Billy Gerhard <billygerhard@gmail.com>
@github-actions github-actions Bot added readiness: action required A blocking check or review needs attention readiness: checking Automated validation is still running and removed readiness: checking Automated validation is still running readiness: action required A blocking check or review needs attention labels Sep 3, 2026
@bolichen97

Copy link
Copy Markdown
Collaborator

Open PR relationship audit

This is a consolidated, point-in-time code-level audit note. It compares complete merge-base diffs and current/merged code; it does not treat a shared topic as duplication or partial coverage as completion.

Relationship findings

  • PR #7669 is OVERLAPPING relative to this PR. The goals differ or the implementations can complement each other; this is not a duplicate claim. Recommended action for PR #7669: KEEP. Different goals with a real interaction worth naming once both exist: 7877 could eventually drop its poll loop in favour of this event, and its own writes will fire it. Files: src/kiro_crew/apps/builtins/chat_status_tags/store.py.
  • PR #7779 is OVERLAPPING relative to this PR. The goals differ or the implementations can complement each other; this is not a duplicate claim. Recommended action for PR #7779: MERGE_DISCUSSION. Two competing designs for one capability. A maintainer should pick the canonical agent tag-write path; if 7779 lands, 7877's self-tag-chat skill and the PUT /slots/{slot}/tags entry in its allowlist should be re-pointed at chat_tag so the app keeps only what is genuinely its own (health sweep, auto-resume, reconciler, app page). Files: src/kiro_crew/apps/builtins/chat_status_tags/skills/self-tag-chat/SKILL.md, src/kiro_crew/validation.py.

No PR, Issue, label, branch, or review state was changed by the relationship-note portion of this audit.

@github-actions github-actions Bot added the merge conflict Branch has merge conflicts with its base — author must resolve before merge label Sep 7, 2026
@bolichen97

Copy link
Copy Markdown
Collaborator

@billygerhard Thanks for this. Nothing on main implements any part of chat-status-tags, so this is not redundant work. What it does share with two other open PRs is the built-in registration seam and one governance decision behind all three.

#8064 (Kiro Crew Guide, @buluoray) edits the same five places this PR does: src/kiro_crew/apps/builtins/__init__.py, website/src/apps/builtinIcons.tsx, website/src/apps/builtinRegistry.ts, website/src/components/appstore/appManifest.ts and the locale catalogs. The behaviour does not overlap at all (a troubleshooting knowledge base versus chat SDLC and health tagging); the collision is one-line adjacency in BUILTIN_NAMES plus the registry and manifest maps.

#8463 (AgentCore Observatory, @warren830) is the same shape again on src/kiro_crew/apps/builtins/__init__.py, website/src/apps/builtinRegistry.ts, website/src/components/appstore/appManifest.ts and the locale files, with no shared behaviour either.

All three add a new directory under src/kiro_crew/apps/builtins/, which the blocking no-new-builtin-apps rule in AUTOSDE.yaml forbids. So what gates them is a single maintainer decision, not a merge order: either a recorded /ai-review override or re-scoping each app to the external KiroCrewApps registry. Our suggestion is to keep the three PRs independent, settle that decision first, then land whichever is ready and let the others rebase, since the textual conflicts are mechanical.

Two things specific to this PR: its agent tag-write path overlaps #7779, which needs its own reconciliation, and it is 635 commits behind with a merge conflict, so a rebase is needed regardless. Audited at 6a9b356.

Posted from the 2026-09-08 open-PR relationship audit (read-only, one auditor per PR); reply here if any of this is wrong.

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

Labels

fork Pull request from a fork (external contributor) merge conflict Branch has merge conflicts with its base — author must resolve before merge readiness: action required A blocking check or review needs attention

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants