Skip to content
This repository was archived by the owner on Mar 4, 2026. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,7 @@
# Copy to .env and fill values as needed.
OPENAI_API_KEY=
GITHUB_TOKEN=
CONTEXT7_URL=
CONTEXT7_API_KEY=
CONTEXT7_MODE=http
SIMULATION=true
33 changes: 33 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
name: CI

on:
push:
branches: [main]
pull_request:

jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Check out repository
uses: actions/checkout@v4

- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.11'
cache: 'pip'

- name: Install dependencies
run: |
python -m pip install --upgrade pip
python -m pip install -e ".[dev]"

- name: Lint
run: make lint

- name: Type check
run: make type

- name: Test
run: make test
50 changes: 41 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,17 @@ The Typer-based CLI exposes four top-level commands:
| `agent research "topic"` | Perform web research, summarise findings, and emit markdown + JSON artifacts. |
| `agent plan "goal"` | Generate a structured plan, Markdown brief, and Mermaid diagram artifacts. |
| `agent run "goal"` | Generate a plan, propose shell commands, and simulate or execute them with a run log. |
| `agent docs "library@version"` | Placeholder documentation retrieval workflow. |
| `agent docs "library@version"` | Retrieve documentation snapshots via Context7 MCP (requires configuration). |

Run `agent --help` or `agent <command> --help` for the latest options.
Run `agent --help` or `agent <command> --help` for the latest options. For a complete, real
example of the planning flow see [examples/nextauth_plan.md](examples/nextauth_plan.md).

### Example session

The acceptance test scenario, `agent plan "set up Next.js + NextAuth"`, produces a timestamped
artifact directory containing Markdown, JSON, and Mermaid files. A captured output is available in
[`examples/nextauth_plan.md`](examples/nextauth_plan.md) alongside the Mermaid definition so you can
render the SVG locally once `@mermaid-js/mermaid-cli` is installed.

## Research workflow

Expand Down Expand Up @@ -85,7 +93,7 @@ src/agentic_cli/
research_cmd.py # research workflow implementation
plan_cmd.py # planning workflow with artifact + Mermaid generation
run_cmd.py # plan-driven execution with simulation + logging
docs_cmd.py # MCP docs placeholder
docs_cmd.py # Context7 documentation capture command
runner/
agent.py # agent + tool dataclasses
policy.py # heuristic policy helper
Expand All @@ -99,9 +107,9 @@ src/agentic_cli/
web_search.py # search, fetch, chunk, summarise utilities
```

Tests live under `tests/` and cover the CLI scaffold, configuration parsing, runner behaviour, and
the research tooling (chunking, citation formatting, summarisation limits, GitHub ingestion), along
with the planning workflow.
Tests live under `tests/` and cover the CLI scaffold, configuration parsing, runner behaviour, the
research tooling (chunking, citation formatting, summarisation limits, GitHub ingestion), the
planning workflow, Context7 integration, and the shell simulator.

## Planning workflow

Expand Down Expand Up @@ -129,6 +137,24 @@ alongside the textual steps.
This flow gives you an end-to-end rehearsal of the plan before choosing to execute commands in your
environment.

## Documentation workflow (Context7)

The optional `agent docs` command integrates with the Context7 MCP service to capture structured
documentation for a package. To enable it:

1. Install Node.js 18+ and the Context7 CLI if you plan to run a local MCP server.
2. Set `CONTEXT7_URL` in your environment (e.g., `https://context7.your-domain/v1`).
3. Optionally set `CONTEXT7_API_KEY` when the service requires authentication.
4. Leave `CONTEXT7_MODE` at `http` for HTTP-based access (the default in `.env.example`).

Running `agent docs next-auth@5.0.0` writes a timestamped directory under `artifacts/` containing:

- `docs.json` — the structured payload from Context7 (library metadata + document entries).
- `docs.md` — a human-readable summary with titles, summaries, and source hints.

These artifacts can be referenced by subsequent `agent research` or `agent plan` runs to augment
their context with authoritative documentation.

## Runner Overview

The runner module introduces:
Expand All @@ -141,11 +167,17 @@ The runner module introduces:
simulation mode for shell commands, blocks denylisted patterns (e.g., `rm -rf`), logs progress via
`structlog`, and returns structured trace data for downstream formatting.

## Continuous integration

GitHub Actions runs `make lint`, `make type`, and `make test` on every push and pull request. The
workflow lives at [`.github/workflows/ci.yml`](.github/workflows/ci.yml) and ensures Ruff, Black,
MyPy, and pytest stay green across environments.

## Next Steps

Upcoming pull requests will integrate optional MCP Context7 documentation retrieval, add the
execution shell tooling to CI examples, and wire up continuous integration so linting, typing, and
tests run automatically for every change.
Future iterations will focus on swapping deterministic stubs for real LLM calls (once API keys are
configured), adding caching for repeated research runs, and enriching the runner policy with more
representative traces.

## Contributing

Expand Down
57 changes: 57 additions & 0 deletions examples/nextauth_plan.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
# Example: Planning Next.js + NextAuth

This snapshot was captured by running the planning workflow against the acceptance-criteria goal:

```bash
PYTHONPATH=src python -m agentic_cli.cli.app plan "set up Next.js + NextAuth"
```

Running the command created a timestamped directory under `artifacts/` (for example,
`artifacts/1758108975_plan/`) containing:

- `plan.md` — the human-friendly brief shown below.
- `plan.json` — the structured payload for downstream automations.
- `plan.mmd` — the Mermaid definition. If `mmdc` from `@mermaid-js/mermaid-cli` is installed, an SVG diagram is rendered alongside the `.mmd` file.

> ⏱️ Timestamps will differ on your machine because they are generated at runtime.

---

```markdown
# Plan: set up Next.js + NextAuth

_Generated: 2024-05-12T10:15:30.000000+00:00_

## Steps

1. **Clarify success criteria**
- Align on requirements, constraints, and definition of done for 'set up Next.js + NextAuth'.

2. **Prepare environment and resources**
- List tooling, credentials, and prerequisites needed to deliver Next.js + NextAuth.

3. **Implement Next.js + NextAuth**
- Build or configure Next.js + NextAuth in line with the project goals.

4. **Validate and document**
- Test outcomes, capture learnings, and document the process for 'set up Next.js + NextAuth'.

## Notes

Adjust sequencing as new information arrives; revisit the plan after each milestone.
```

And the corresponding Mermaid definition:

```mermaid
flowchart TD
step_1['Clarify success criteria']
step_2['Prepare environment and resources']
step_1 --> step_2
step_3['Implement Next.js + NextAuth']
step_2 --> step_3
step_4['Validate and document']
step_3 --> step_4
```

Render the diagram locally by installing Mermaid CLI (`npm install -g @mermaid-js/mermaid-cli`) and rerunning the command.
79 changes: 76 additions & 3 deletions src/agentic_cli/cli/docs_cmd.py
Original file line number Diff line number Diff line change
@@ -1,21 +1,94 @@
"""Placeholder documentation retrieval command module."""
"""Documentation retrieval command leveraging Context7 MCP integration."""

from __future__ import annotations

import structlog
import typer

from pathlib import Path

from agentic_cli.artifacts.manager import timestamped_dir, write_json, write_text
from agentic_cli.config import Settings, get_settings
from agentic_cli.mcp import Context7Client, Context7DocsResponse, Context7Error

logger = structlog.get_logger(__name__)

DEFAULT_DOC_LIMIT = 20

app = typer.Typer(
help="Fetch library docs via MCP Context7 (optional)", invoke_without_command=True
)


def run_docs(
package: str,
*,
limit: int = DEFAULT_DOC_LIMIT,
settings: Settings | None = None,
client: Context7Client | None = None,
) -> dict[str, str] | None:
"""Retrieve documentation for ``package`` and write artifacts."""

config = settings or get_settings()
if not config.context7_url:
typer.echo(
"Context7 MCP integration is not configured. Set CONTEXT7_URL to enable this command."
)
return None

if config.context7_mode and config.context7_mode.lower() not in {"http", "https"}:
typer.echo(
"Only HTTP Context7 integration is supported currently. "
"Set CONTEXT7_MODE=http to proceed."
)
return None

artifact_dir = timestamped_dir("docs")
own_client = client is None
if client is None:
client = Context7Client(config.context7_url, api_key=config.context7_api_key)

try:
response = client.fetch_docs(package, limit=limit)
except Context7Error as exc:
logger.bind(package=package).warning("docs.fetch_failed", error=str(exc))
typer.echo(f"Failed to retrieve documentation from Context7: {exc}")
return None
finally:
if own_client and client is not None:
client.close()

return _write_artifacts(response, artifact_dir)


def _write_artifacts(response: Context7DocsResponse, directory: Path) -> dict[str, str]:
docs_json = write_json(directory, "docs.json", response.to_json())
docs_markdown = write_text(directory, "docs.md", response.to_markdown())
logger.info(
"docs.artifacts_written",
package=response.package,
docs_json=str(docs_json),
docs_markdown=str(docs_markdown),
)
typer.echo(f"Documentation stored at {docs_json}")
return {"docs_json": str(docs_json), "docs_md": str(docs_markdown)}


@app.callback(invoke_without_command=True)
def docs(
ctx: typer.Context,
package: str = typer.Argument(..., help="Package spec e.g. name@version"),
limit: int = typer.Option(
DEFAULT_DOC_LIMIT,
"--limit",
"-l",
min=1,
max=50,
help="Maximum number of documentation entries to request.",
),
) -> None:
"""Stub documentation retrieval placeholder."""
"""Entry point for the ``agent docs`` command."""

if ctx.invoked_subcommand:
return
typer.echo(f"[docs] TODO: integrate with MCP Context7 to fetch documentation for '{package}'")
run_docs(package, limit=limit)
3 changes: 3 additions & 0 deletions src/agentic_cli/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,9 @@ class Settings(BaseModel):

openai_api_key: str | None = Field(default=None, alias="OPENAI_API_KEY")
github_token: str | None = Field(default=None, alias="GITHUB_TOKEN")
context7_url: str | None = Field(default=None, alias="CONTEXT7_URL")
context7_api_key: str | None = Field(default=None, alias="CONTEXT7_API_KEY")
context7_mode: str | None = Field(default=None, alias="CONTEXT7_MODE")
simulation: bool = Field(default=True, alias="SIMULATION")

model_config = {
Expand Down
19 changes: 19 additions & 0 deletions src/agentic_cli/mcp/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
"""MCP integration helpers for external documentation sources."""

from __future__ import annotations

from .context7 import (
Context7Client,
Context7Document,
Context7DocsResponse,
Context7Error,
Context7Library,
)

__all__ = [
"Context7Client",
"Context7Document",
"Context7DocsResponse",
"Context7Error",
"Context7Library",
]
Loading
Loading