To review a Python pull request with Atlas, get the diff and then leave the diff. Atlas fetches the branch and produces the patch with bash, because Atlas reads git branches, status, and diffs and exposes status, diff, diffRaw, and commits over the same git data. Atlas then reads the changed .py files in full with read rather than only the hunks, so the context outside the diff is visible: the decorator above the changed function, the class attribute it mutates, the module-level constant it depends on. For every changed function signature, Atlas runs the lsp tool's findReferences operation to check callers the diff never touched, which is the single most common source of bugs a line-by-line Python review misses. Atlas greps for patterns the change should have updated but did not, runs pytest through bash, and reports findings as a todowrite list ordered by severity. uv resolves the environment, and ruff format settles the style questions so the review can be about behavior.
How does Atlas get a Python pull request diff?
Atlas fetches the branch and produces the diff with bash. Atlas reads git branches, status, and diffs, and its VCS layer exposes status, diff, diffRaw, and commits over the same git data, so in 2026 a Python PR review starts from the raw patch and the list of changed .py files rather than a web UI.
Starting from the raw patch matters because the reviewable unit in Python is rarely the hunk. A three-line change to a function body in src/billing/invoice.py may be correct in isolation and wrong in context, because the module imports a mutable default from src/billing/config.py or because a @dataclass above it makes the new field positional. Atlas produces the changed file list and the raw patch with bash, then treats that as an index into the codebase, not as the review itself. Atlas can also stage and create commits on your behalf, so the review can end in a commit rather than a copy-paste. The diff tells Atlas where to look. The files tell Atlas what is actually true.
Why read the whole Python file instead of just the diff hunks?
Atlas reads the changed files in full with read, not just the hunks, so context outside the diff is visible. In Python that context is decisive: a decorator, a metaclass, a module-level singleton, a mutable default argument, or an __init__.py side effect can all invert the meaning of a 2-line change that looks obviously correct in a hunk.
Python hides behavior above and below the cursor. A hunk that adds a parameter to a function is fine until you see the @lru_cache decorator three lines above it, which now caches on the new argument. A hunk that appends to a list is fine until you see that the list is a default argument shared across every call. A hunk that changes a return type is fine until you see the @property that consumes it. Atlas reads the whole .py file, and because Atlas indexes code by AST declarations using tree-sitter, not blind line windows, the retrieval around the change is by declaration rather than by arbitrary offset. Reading the full file is how a careful Python reviewer works, and it is how Atlas works.
How do you check that a Python signature change did not break callers?
For every changed function signature, Atlas runs the lsp tool's findReferences operation to check callers the diff never touched. Python has no compiler to catch a caller passing 3 positional arguments to a function that now takes 4, so findReferences is the only way to enumerate them before pytest finds one at runtime.
This is the highest-value step in a Python PR review, because Python's dynamism means a signature change fails at call time, not at build time. A PR that renames a keyword argument in src/api/handlers.py will pass every test that does not happen to exercise that path, then raise TypeError in production. Atlas runs the lsp tool's findReferences on each changed signature, gets the caller list from the language server, and reads those callers even though the diff never touched them. Where the caller is dynamic, for example a getattr dispatch or a Django URL string, findReferences cannot see it, and that is precisely when Atlas falls back to grep.
What should you grep for when reviewing a Python PR?
Atlas greps for the patterns the change should have updated but did not: old constant names, stale copies, feature flags. In a 2026 Python repo that means checking whether a renamed setting still appears in settings.py, in a .env.example, in a conftest.py fixture, or in a migration under migrations/ that the PR forgot.
The incomplete change is the classic Python PR bug, and grep is how you find it. A PR that adds a new field to a Pydantic model should have updated the corresponding response schema, the test fixtures in tests/conftest.py, and the Alembic migration. A PR that renames a feature flag should have updated every reference, including the one in a string passed to a settings lookup. Atlas searches code with hybrid semantic and keyword retrieval fused by reciprocal rank fusion, so codebase_search can also surface the places where the same concept is implemented under a different name, which is where the stale copies hide.
How does Atlas report Python PR review findings?
Atlas runs the tests with bash and reports findings as a todowrite list ordered by severity. A 2026 Python review ends with pytest green or red, ruff format clean or dirty, and a ranked list where a missing caller update sits above a naming nit, so the PR author knows what actually blocks the merge.
The ordered todowrite list is what turns a review into something actionable. Atlas runs pytest through the bash tool, and if the output is large, bash truncates it and saves the complete log to a file whose path it reports, so triage happens against the whole run. uv resolves the environment so pytest runs against the PR's actual dependencies rather than a stale virtualenv. ruff format tells you whether the style questions are already settled by tooling, which lets the human part of the review be about behavior. Every Atlas tool call is permission-gated against allow, ask, and deny rules before it runs, so a review session that only reads and greps can be permissioned to do exactly that and nothing more.
Step by step
- 01Run atlas in a repo with a pyproject.toml or requirements.txt so Atlas can read your package layout, virtualenv, and installed dependencies.
- 02Fetch the branch and produce the diff with bash; Atlas's VCS layer exposes status, diff, diffRaw, and commits over the same git data.
- 03Read the changed .py files in full with read, not just the hunks, so decorators, module-level constants, and mutable defaults outside the diff are visible.
- 04For every changed function signature, run the lsp tool's findReferences operation to check callers the diff never touched, since Python raises TypeError at call time rather than at build time.
- 05Grep for the patterns the change should have updated but did not: old constant names, stale copies, feature flags, conftest.py fixtures, and migrations.
- 06Sync the environment with uv so the review runs against the PR's actual dependencies.
- 07Run pytest with the bash tool and read the failures; if the output is truncated, read the saved log file whose path bash reports.
- 08Run ruff format to settle style questions with tooling, then report findings as a todowrite list ordered by severity.
Frequently asked questions
- how to use an AI agent to review a Python pull request
- Have Atlas produce the diff with bash, read the changed .py files in full with read, run the lsp tool's findReferences on every changed signature, grep for stale copies, run pytest, and report findings as a todowrite list ordered by severity.
- why is reading the whole file better than reading the diff in Python
- Python hides behavior above and below the cursor. A hunk adding a parameter looks correct until you see the @lru_cache decorator above it. Atlas reads the changed files in full with read, not just the hunks, so context outside the diff is visible.
- how do I find callers a Python PR forgot to update
- Run Atlas's lsp tool findReferences operation on every changed function signature. Python has no compiler to catch a caller passing the wrong argument count, so enumerating callers before pytest hits one at runtime is the only reliable check.
- can Atlas run pytest as part of a code review
- Yes. Atlas runs pytest through the bash tool. If the output exceeds the truncation limit, bash saves the complete log to a file and reports the path, so triage happens against the whole run rather than a lossy tail.
- does Atlas work with uv and pyproject.toml
- Yes. Run atlas in a repo with a pyproject.toml or requirements.txt and Atlas reads your package layout, virtualenv, and installed dependencies. uv resolves the environment so pytest runs against the PR's actual dependencies.
- how do I stop an AI reviewer from editing my code
- Every Atlas tool call is permission-gated against allow, ask, and deny rules before it runs. A review session can be permissioned to read, grep, and run bash only, so Atlas can inspect the Python PR without any ability to write to it.
- what should a Python code review check that a linter cannot
- Callers the diff never touched, stale copies of a renamed constant, and the decorators and mutable defaults surrounding a changed function. ruff format settles style, so the human and the agent can both spend their attention on behavior.
Try Atlas in your terminal
The terminal-native AI coding agent. Free core, single binary.
Install AtlasRelated guides
Review a Pull Request with Atlas (2026 Workflow)
How to review a pull request with Atlas in 2026: bash produces the raw patch, read pulls whole files, the lsp tool's findReferences checks callers the diff never shows.
Atlas for Python in 2026
Atlas is a terminal-native AI coding agent for Python in 2026. Run it in a repo with a pyproject.toml or requirements.txt and review every diff before it lands.
Diagnose a Hanging or Long-Running Command in Python with Atlas (2026)
Is your Python command slow or blocked on stdin? In 2026 Atlas races every bash command against a timeout and its shell_metadata tells you which, so pytest and uv stop hanging.
Extract a Shared Helper From Duplicated Code in Python with Atlas (2026)
Duplication in Python is semantic, not textual. Atlas finds near-duplicate logic with codebase_search in 2026, collapses it with apply_patch, and proves it with pytest.
Trace a Runtime Bug from a Python Stack Trace with Atlas in 2026
Go from a Python traceback to the responsible line in 2026 with no debugger attached: Atlas reads each frame at its offset, greps for the message, and walks callers with lsp.
Document a Python Module With a README Using Atlas (2026)
Atlas writes Python docs from source, not memory: lsp documentSymbol lists the real exports, read supplies behavior, and every code sample is proven with pytest.
Migrate a Deprecated API Across Every Callsite in Python with Atlas (2026)
Move a Python codebase off a deprecated function with Atlas in 2026: enumerate callers with the lsp tool, patch each with apply_patch, and run pytest after every file.
Add a Regression Test for a Bug Fix in Python with Atlas (2026)
Red first, then green. Atlas writes a failing pytest case, proves it fails with the bash tool exit code, applies the fix with edit, and re-runs the same command.