Skip to content

Dev#15

Merged
ayusrjn merged 5 commits into
mainfrom
dev
Apr 15, 2026
Merged

Dev#15
ayusrjn merged 5 commits into
mainfrom
dev

Conversation

@ayusrjn
Copy link
Copy Markdown
Member

@ayusrjn ayusrjn commented Apr 12, 2026

Summary by CodeRabbit

Release Notes

  • New Features

    • Added task completion workflow with finish_task capability
    • Added todo management system with persistent file storage
  • Improvements

    • Enhanced error and interrupt handling with session summary display
    • Updated default AI model and expanded available model options
  • Documentation

    • Fixed image URLs in README for proper external access
  • Chores

    • Version bumped to 0.1.3

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Apr 12, 2026

📝 Walkthrough

Walkthrough

The pull request introduces a mandatory planning workflow using a persistent .agent/todo.md file, adds a finish_task tool for explicit task completion, strengthens the agent's system prompt with security guardrails, improves KeyboardInterrupt handling in the CLI, updates the default model configuration, and bumps the version to 0.1.3.

Changes

Cohort / File(s) Summary
Model Configuration & Version
lambda_agent/config.py, lambda_agent/cli_setup.py, pyproject.toml
Updated default MODEL_NAME from gemini-3.1-flash-lite-preview to gemini-3.1-pro-preview, expanded AVAILABLE_MODELS list with new Gemini and Gemma model identifiers, and bumped package version from 0.1.0 to 0.1.3.
Todo Management System
lambda_agent/todo.py
New module providing persistent .agent/todo.md file management with functions to read, write, update, and clear todo entries; includes managed header and optional section-based organization.
Tool System & Task Completion
lambda_agent/tools.py
Added finish_task() tool, integrated TODO_EXECUTORS and TODO_FUNCTIONS into tool registration, and extended get_workspace_summary() to include .agent/todo.md content in workspace context.
Agent System Prompt & Chat Control Flow
lambda_agent/agent.py
Enhanced system prompt with "SECURITY GUARDRAILS" section requiring refusal of system prompt disclosure and "MANDATORY PLANNING WORKFLOW" requiring .agent/todo.md maintenance; wrapped initial API call in try/except for error handling; removed max_tool_iterations guard logic; added early exit when finish_task tool is called; hid todo-management tools from user-facing display.
CLI Error Handling & User Experience
lambda_agent/main.py
Added inner try/except for KeyboardInterrupt during prompt entry with session summary display; refactored command execution exception handling to continue on cancellation rather than exit; added catch-all exception handler to prevent loop termination on unexpected errors.
Documentation
README.md
Updated embedded image URLs from relative local paths (images/logo.png, images/screen.png) to fully-qualified raw GitHub URLs.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

  • Dev #14: Modifies agent.py's system prompt and sub-agent guidance, updating tools.py to register executor/function mappings—directly related to this PR's tool system extensions and prompt changes.
  • Dev #13: Alters Agent.chat control flow and tool registration, adding persistent .agent tool integration—shares code-level connection through agent behavior and workspace tooling updates.
  • Dev #7: Introduces lambda_agent/tools.py and tool registry architecture—foundational to this PR's extensions of tool executors and function registration.

Poem

🐰 A bunny's task now clear and bright,
With todo lists and finish flights,
The agent plans with guardrails tight,
No prompts revealed—just what is right! ✨
Hop along, let planning lead the way!

🚥 Pre-merge checks | ✅ 1 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 75.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Title check ❓ Inconclusive The title 'Dev' is vague and generic, providing no meaningful information about the actual changes in the pull request. Use a descriptive title that summarizes the main changes, such as 'Add todo management and finish_task workflow with security guardrails' or 'Update agent system prompts, add todo.md persistence, and improve error handling'.
✅ Passed checks (1 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch dev

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@lambda_agent/agent.py`:
- Around line 172-178: The loop that drives tool/model iterations (the while
True loop around send_message and finish_task) lacks a hard iteration cap, so
add a small max-iteration guard (e.g., MAX_TOOL_ITERS = 10) and increment an
iteration counter each pass; if the counter exceeds the cap return a clean
failure tuple (message and current turn_usage) instead of continuing. Update the
block that calls self.chat_session.send_message (and accumulates via
self._accumulate) to check the counter before each iteration and to abort with a
clear error when hit; apply the same MAX_TOOL_ITERS guard and abort behavior to
the other similar loop referenced around finish_task (the block at the other
location).

In `@lambda_agent/cli_setup.py`:
- Around line 20-23: The default model value is set to a paid tier; update the
default to a free-tier model in both the CLI setup and the config so new users
don't hit quota/auth failures: change the default_model variable in
lambda_agent/cli_setup.py (currently "gemini-3.1-pro-preview" referenced where
model_name is read) to "gemini-3.1-flash-lite-preview" (or
"gemini-3-flash-preview"), and make the matching change in
lambda_agent/config.py to ensure any CONFIG_DEFAULT_MODEL (or equivalent
default_model/defaults dict) uses the same free-tier model string.

In `@lambda_agent/config.py`:
- Around line 23-31: The Gemma model entries in AVAILABLE_MODELS are
incompatible with the Agent codepath that sends a separate system_instruction
and structured function schemas; either remove the "gemma-*" entries from
AVAILABLE_MODELS or gate them behind a capability check so the Agent uses an
alternate prompt-based adapter. Locate AVAILABLE_MODELS and remove
"gemma-4-26b-a4b-it" and "gemma-4-31b-it" or add a capability predicate (e.g.,
model_supports_system_instruction/model_supports_structured_tools) and update
Agent usage where it sends system_instruction and structured tool schemas to
skip or route Gemma models into a prompt-formatting adapter that embeds system
instructions and function call prompts into the user prompt instead.

In `@lambda_agent/todo.py`:
- Around line 37-47: The helpers call _ensure_todo() outside their try blocks,
so failures creating/seeding .agent/ bubble out; move the call to _ensure_todo()
inside the try for each public tool (read_todo, write_todo, update_todo,
clear_todo) so filesystem/setup errors are caught and you return the
error-string as intended; update the functions read_todo(), write_todo(),
update_todo(), and clear_todo() to call path = _ensure_todo() within their
existing try blocks and keep the existing exception handling that returns the
"Error ..." messages.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: fe3112df-bb8c-4204-9ca9-45f87e75251a

📥 Commits

Reviewing files that changed from the base of the PR and between 4d154c7 and 0245d32.

📒 Files selected for processing (8)
  • README.md
  • lambda_agent/agent.py
  • lambda_agent/cli_setup.py
  • lambda_agent/config.py
  • lambda_agent/main.py
  • lambda_agent/todo.py
  • lambda_agent/tools.py
  • pyproject.toml

Comment thread lambda_agent/agent.py
Comment on lines +172 to +178
try:
# Send the initial user message
with Spinner():
response = self.chat_session.send_message(payload)
turn_usage = turn_usage + self._accumulate(response)
except Exception as e:
return f"An error occurred while contacting the API: {str(e)}", turn_usage
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Keep a hard cap on tool iterations.

finish_task helps when the model behaves, but it's not a safety boundary. With no iteration limit around the while True loop, any bad tool/result cycle can keep spending tokens until the user manually interrupts the session. Please restore a small max-iteration guard and fail the turn cleanly when it's hit.

Suggested fix
         # Track tokens for this turn
         turn_usage = TokenUsage()
+        max_tool_iterations = 20
+        tool_iterations = 0
@@
         # The loop will continue as long as Gemini decides to call tools
         while True:
             try:
+                tool_iterations += 1
+                if tool_iterations > max_tool_iterations:
+                    return (
+                        "The agent exceeded the maximum number of tool iterations for one turn.",
+                        turn_usage,
+                    )
+
                 # 1. Check if the model returned a function_call
                 tool_calls = response.function_calls if response.function_calls else []

Also applies to: 257-259

🧰 Tools
🪛 Ruff (0.15.9)

[warning] 177-177: Do not catch blind exception: Exception

(BLE001)


[warning] 178-178: Use explicit conversion flag

Replace with conversion flag

(RUF010)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@lambda_agent/agent.py` around lines 172 - 178, The loop that drives
tool/model iterations (the while True loop around send_message and finish_task)
lacks a hard iteration cap, so add a small max-iteration guard (e.g.,
MAX_TOOL_ITERS = 10) and increment an iteration counter each pass; if the
counter exceeds the cap return a clean failure tuple (message and current
turn_usage) instead of continuing. Update the block that calls
self.chat_session.send_message (and accumulates via self._accumulate) to check
the counter before each iteration and to abort with a clear error when hit;
apply the same MAX_TOOL_ITERS guard and abort behavior to the other similar loop
referenced around finish_task (the block at the other location).

Comment thread lambda_agent/cli_setup.py
Comment on lines +20 to 23
default_model = "gemini-3.1-pro-preview"
model_name = input(f"Enter model name (default: {default_model}): ").strip()
if not model_name:
model_name = default_model
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🌐 Web query:

Does gemini-3.1-pro-preview have a free tier in the Gemini API, and which Gemini 3 text models do have a free tier?

💡 Result:

No, gemini-3.1-pro-preview does not have a free tier in the Gemini API; it is paid-only with input prices starting at $2.00 per 1M tokens. Gemini 3 text models with a free tier are: gemini-3.1-flash-lite-preview (free input/output tokens) and gemini-3-flash-preview (free tier access confirmed in multiple sources).

Citations:


🏁 Script executed:

cat -n lambda_agent/cli_setup.py | head -30

Repository: ayusrjn/lambda

Length of output: 1263


🏁 Script executed:

# Check for README or setup documentation references to free tier
rg -i "free\|api key" --max-count 5 -A 2

Repository: ayusrjn/lambda

Length of output: 40


🏁 Script executed:

# Check if there are other model defaults in the codebase
rg "gemini-3" lambda_agent/

Repository: ayusrjn/lambda

Length of output: 380


Change the default model to a free-tier option in both setup and config.

The setup flow explicitly tells users they can get an API key "for free" (line 12), but then defaults to gemini-3.1-pro-preview, which has no free tier and costs $2.00 per 1M input tokens. New users will hit auth/quota failures before changing anything. Update the default in lambda_agent/cli_setup.py (line 20) and lambda_agent/config.py to use gemini-3.1-flash-lite-preview or gemini-3-flash-preview, which both have free tier access.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@lambda_agent/cli_setup.py` around lines 20 - 23, The default model value is
set to a paid tier; update the default to a free-tier model in both the CLI
setup and the config so new users don't hit quota/auth failures: change the
default_model variable in lambda_agent/cli_setup.py (currently
"gemini-3.1-pro-preview" referenced where model_name is read) to
"gemini-3.1-flash-lite-preview" (or "gemini-3-flash-preview"), and make the
matching change in lambda_agent/config.py to ensure any CONFIG_DEFAULT_MODEL (or
equivalent default_model/defaults dict) uses the same free-tier model string.

Comment thread lambda_agent/config.py
Comment on lines 23 to +31
AVAILABLE_MODELS = [
"gemini-3.1-pro-preview",
"gemini-3-flash-preview",
"gemini-3.1-flash-lite-preview",
"gemini-2.5-pro",
"gemini-2.5-flash",
"gemini-3.1-pro-preview",
"gemini-2.5-pro-preview-05-06",
"gemini-2.0-flash",
"gemini-2.0-flash-lite",
"gemini-2.5-flash-lite",
"gemma-4-26b-a4b-it",
"gemma-4-31b-it",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🌐 Web query:

Do Gemma models in the Gemini API support a separate system_instruction role and structured Gemini function-calling tools, or do they require prompt-based formatting instead?

💡 Result:

Gemma models in the Gemini API do not support a separate system_instruction role; they require prompt-based formatting for system-level instructions. They also do not support structured Gemini function-calling tools (e.g., via tools parameter with automatic parsing); instead, function calling requires manual prompt-based formatting where tools are described in text and outputs are parsed from the model's free-form response.

Citations:


Remove Gemma models from AVAILABLE_MODELS or gate them behind capability checks.

The current Agent architecture passes system_instruction and structured Gemini tool schemas to all models in this list. Gemma models in the Gemini API do not support a separate system_instruction role and do not support structured function-calling tools—they require prompt-based formatting for both system instructions and function calls. This will cause runtime failures or silent capability loss for users selecting these models. Either remove the Gemma entries or ensure they are only accessible through a separate code path with appropriate adapter logic.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@lambda_agent/config.py` around lines 23 - 31, The Gemma model entries in
AVAILABLE_MODELS are incompatible with the Agent codepath that sends a separate
system_instruction and structured function schemas; either remove the "gemma-*"
entries from AVAILABLE_MODELS or gate them behind a capability check so the
Agent uses an alternate prompt-based adapter. Locate AVAILABLE_MODELS and remove
"gemma-4-26b-a4b-it" and "gemma-4-31b-it" or add a capability predicate (e.g.,
model_supports_system_instruction/model_supports_structured_tools) and update
Agent usage where it sends system_instruction and structured tool schemas to
skip or route Gemma models into a prompt-formatting adapter that embeds system
instructions and function call prompts into the user prompt instead.

Comment thread lambda_agent/todo.py
Comment on lines +37 to +47
def read_todo() -> str:
"""Reads the full contents of the Lambda todo file (.agent/todo.md).

Use this to recall your current task list and implementation plan.
"""
path = _ensure_todo()
try:
with open(path, "r", encoding="utf-8") as f:
return f.read()
except Exception as e:
return f"Error reading todo list: {e}"
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Move _ensure_todo() inside the public tools' error handling.

All four public todo tools call _ensure_todo() before entering their try blocks. If creating .agent/ or seeding todo.md fails, the tool raises out of the agent instead of returning the "Error ..." string promised by the API, which can abort the whole turn.

Suggested fix
 def read_todo() -> str:
     """Reads the full contents of the Lambda todo file (.agent/todo.md).
@@
-    path = _ensure_todo()
     try:
+        path = _ensure_todo()
         with open(path, "r", encoding="utf-8") as f:
             return f.read()
     except Exception as e:
         return f"Error reading todo list: {e}"

Apply the same pattern to write_todo(), update_todo(), and clear_todo().

Also applies to: 50-65, 68-107, 110-121

🧰 Tools
🪛 Ruff (0.15.9)

[warning] 46-46: Do not catch blind exception: Exception

(BLE001)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@lambda_agent/todo.py` around lines 37 - 47, The helpers call _ensure_todo()
outside their try blocks, so failures creating/seeding .agent/ bubble out; move
the call to _ensure_todo() inside the try for each public tool (read_todo,
write_todo, update_todo, clear_todo) so filesystem/setup errors are caught and
you return the error-string as intended; update the functions read_todo(),
write_todo(), update_todo(), and clear_todo() to call path = _ensure_todo()
within their existing try blocks and keep the existing exception handling that
returns the "Error ..." messages.

@ayusrjn ayusrjn merged commit f379205 into main Apr 15, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant