fix(code): allow /remember with args when no conversation history (#4418)

`/remember` now proceeds when context is provided as an argument, even
with no prior conversation history. Bare `/remember` with no history
still shows the existing "Nothing to remember yet" prompt.

---

Bare `/remember` with no conversation history shows an early-return
"Nothing to remember yet" message. That guard also blocked `/remember i
like blue` — even though the user supplied context to save, the command
never reached the skill.

Move argument extraction above the no-messages guard so the guard only
triggers when `/remember` is bare (no args) **and** there are no
conversation messages. With args, the command delegates to
`/skill:remember <args>` regardless of conversation state.
This commit is contained in:
Mason Daugherty
2026-07-01 20:39:07 -04:00
committed by GitHub
parent a52c18d3ef
commit 5df9c83b58
2 changed files with 41 additions and 4 deletions
+2 -2
View File
@@ -9331,7 +9331,8 @@ class DeepAgentsApp(App):
elif cmd == "/remember" or cmd.startswith("/remember "):
# Convenience alias for /skill:remember — shorter and discoverable
# before skill loading completes.
if not await self._has_conversation_messages():
args = command.strip()[len("/remember") :].strip()
if not args and not await self._has_conversation_messages():
await self._mount_message(UserMessage(command))
await self._mount_message(
AppMessage(
@@ -9340,7 +9341,6 @@ class DeepAgentsApp(App):
),
)
return
args = command.strip()[len("/remember") :].strip()
rewritten = f"/skill:remember {args}" if args else "/skill:remember"
await self._handle_skill_command(rewritten)
elif cmd == "/skill-creator" or cmd.startswith("/skill-creator "):
+39 -2
View File
@@ -13194,7 +13194,7 @@ class TestHasConversationMessages:
class TestRememberRequiresMessages:
"""Ensure /remember early-returns when no conversation exists."""
"""Ensure /remember early-returns only when bare and no conversation exists."""
async def test_remember_no_messages_shows_early_return(self) -> None:
"""/remember should mount an AppMessage and skip the skill."""
@@ -13202,13 +13202,17 @@ class TestRememberRequiresMessages:
async with app.run_test() as pilot:
await pilot.pause()
with patch.object(app, "_has_conversation_messages", return_value=False):
with (
patch.object(app, "_has_conversation_messages", return_value=False),
patch.object(app, "_handle_skill_command") as mock_skill,
):
await app._handle_command("/remember")
await pilot.pause()
msgs = app.query(AppMessage)
assert len(msgs) == 1
assert "Nothing to remember yet" in str(msgs[0]._content)
mock_skill.assert_not_called()
async def test_remember_with_messages_delegates_to_skill(self) -> None:
"""/remember should delegate to _handle_skill_command when messages exist."""
@@ -13225,6 +13229,39 @@ class TestRememberRequiresMessages:
mock_skill.assert_called_once_with("/skill:remember")
async def test_remember_with_args_no_messages_delegates_to_skill(self) -> None:
"""/remember with args proceeds even without conversation history."""
app = DeepAgentsApp()
async with app.run_test() as pilot:
await pilot.pause()
with (
patch.object(app, "_has_conversation_messages", return_value=False),
patch.object(app, "_handle_skill_command") as mock_skill,
):
await app._handle_command("/remember i like blue")
await pilot.pause()
mock_skill.assert_called_once_with("/skill:remember i like blue")
async def test_remember_blank_args_no_messages_shows_early_return(self) -> None:
"""/remember with whitespace-only args is treated as bare (early-return)."""
app = DeepAgentsApp()
async with app.run_test() as pilot:
await pilot.pause()
with (
patch.object(app, "_has_conversation_messages", return_value=False),
patch.object(app, "_handle_skill_command") as mock_skill,
):
await app._handle_command("/remember ")
await pilot.pause()
msgs = app.query(AppMessage)
assert len(msgs) == 1
assert "Nothing to remember yet" in str(msgs[0]._content)
mock_skill.assert_not_called()
class TestSwitchAgentGuards:
"""Guards in `_switch_agent` before the restart worker is launched."""