Developer Automation Toolkit (DAT_CLI)
DAT_CLI is a cross-platform, IDE-independent toolkit designed to automate the tedious parts of developer documentation. It intelligently analyzes your Git repository to generate professional, formatted documentation in seconds.
🚀 Core Features
- Automatic Document Generation:
dat generate-docbuilds the document and opens the Preview Panel to review and export it (--headlesswrites a.docx/.mdstraight to disk for automation). - Smart Git Analysis: Automatically parses your current branch name (e.g.,
feature/PROJECT-123-topic) to infer Ticket IDs and professional titles. - AI-Powered Summaries: Integrates with Google Gemini to read your
git diffand write concise, professional "Changes Done" and "Test Case" summaries. - Interactive Screenshot Selection: Drag-and-drop screenshots onto the Preview Panel, or browse for them — you decide per document whether any are needed.
- Smart Image Layout:
- Mobile Screenshots: Automatically groups tall images side-by-side (2 per row).
- Web Screenshots: Places wide images at full page width for maximum clarity.
- Professional Templates: Generates documents with a clean Arial-based layout, including Metadata Tables, Task Details, and Test Case sections.
- Custom Document Templates: Build your own document structure visually in the GUI — see Custom Document Templates.
- MCP Server: Use
dat mcpto expose DAT as tools to any MCP-compatible AI client (Claude Desktop, Claude Code, Cursor, etc.) — see MCP Integration.md.
🛠 Installation & Setup
Prerequisites
- Python 3.9+
- pip — Python's package installer, used by both install paths below
- Git
Verify all three before you start:
python3 --version # 3.9 or newer
python3 -m pip --version # pip, belonging to that same Python
git --version
Use python3 -m pip, not a bare pip: on many systems only pip3 exists, and
where both exist pip can belong to a different Python than the one that will
run DAT. If all three commands print a version, skip ahead to the install paths.
If Python or pip is missing
Install both from your OS package manager (the shortest route, needs root):
| System | Command |
|---|---|
| Debian / Ubuntu | sudo apt update && sudo apt install python3 python3-pip python3-venv |
| Fedora / RHEL | sudo dnf install python3 python3-pip |
| Arch | sudo pacman -S python python-pip |
| Alpine | sudo apk add python3 py3-pip |
| macOS | brew install python — bundles pip |
| Windows | The python.org installer, with Add python.exe to PATH checked; verify with py -m pip --version |
If Python is installed but pip isn't, bootstrap it from Python's own standard library — no root and no download required:
python3 -m ensurepip --upgrade
Debian and Ubuntu strip ensurepip out of the base python3 package, so there
it fails with No module named ensurepip; use the apt command above instead.
As a last resort on any system:
curl -fsSL https://bootstrap.pypa.io/get-pip.py -o get-pip.py
python3 get-pip.py --user
Pick one of the two paths below. Install from PyPI if you just want to use DAT; install from source if you intend to change its code.
Option A — Install from PyPI (Recommended)
DAT is published on PyPI as
developer-automation-toolkit.
Three steps, no clone required:
-
Install DAT:
pip install --user --upgrade developer-automation-toolkit
If pip refuses with an externally-managed-environment error, your Python follows PEP 668; use
pipx install developer-automation-toolkitinstead. -
Put
daton your PATH.pip install --userwrites the launcher to~/.local/bin, which many distros leave off PATH:which dat || { echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.bashrc # macOS: ~/.zshrc source ~/.bashrc }
-
Check your environment:
dat doctorIf it reports
Tkinter (GUI) : MISSING, it prints the exact install command for your OS — run that and you're done. Tk is the one dependency that has to come from your OS packages rather than PyPI, which is why pip can't supply it.On Debian/Ubuntu the interactive preview needs one more OS package for the same reason — Pillow's Tk bridge, which the distro ships separately:
sudo apt install python3-tk python3-pil.imagetk
Without it the preview shows
[image unavailable]in place of every screenshot, even though the exported.docxembeds them correctly. (Fedora:python3-tkinter python3-pillow-tk; Arch:tk python-pillow. macOS and Windows need nothing extra — those Pillow wheels bundle it.)
You do not need to clone the repository or run setup.sh for this path —
pip generates a real dat executable, so there is no alias to configure.
Optional: do all three with one script
If you would rather not run the steps by hand, install.sh does all of them —
including installing Tk for you via apt/dnf/pacman/Homebrew — and is safe to
re-run:
curl -fsSL https://raw.githubusercontent.com/Priyansu-Kr/DAT_CLI/main/install.sh -o install.sh
bash install.sh
source ~/.bashrc # macOS: source ~/.zshrc
curl fetches that single file from this repository; you still don't need a
clone. Read it before running it, as with any script from the internet.
Upgrading later:
pip install --user --upgrade developer-automation-toolkit
Option B — Install from source (for contributors)
This toolkit includes a universal setup script that works on Linux (Ubuntu/Debian) and macOS.
-
Clone the repository:
git clone https://github.com/Priyansu-Kr/DAT_CLI.git cd DAT_CLI
-
Run the setup script:
chmod +x setup.sh ./setup.sh
This creates a virtualenv, installs DAT in editable mode (
pip install -e .) so your edits take effect immediately, and adds adatalias to your shell. -
Refresh your terminal:
- Linux:
source ~/.bashrc - macOS:
source ~/.zshrc
- Linux:
🔑 AI Configuration (Optional)
A Gemini API key is not required. DAT can write a document's content three ways:
| Content source | When it's used | "Changes Done" | Test cases |
|---|---|---|---|
| Gemini AI | A key is saved (or $DAT_AI_KEY is set) |
Precise summary written from the branch diff | Written for you |
| An LLM / AI agent | Your agent drives DAT through its MCP server | Authored by the agent | Authored by the agent |
| Git diff | No key — the fallback | The file names your work touched | Left empty for you to fill in |
The first time you run dat generate-doc, DAT asks once whether you have a key —
answer n and it never asks again, generating documents from your Git diff.
Answer y and it takes the key, checks its format and saves it.
To add (or remove) a key at any time:
dat save-api-key # prompts for the key, then saves it
dat save-api-key --clear # forget the key and go back to Git-diff content
Get a free key from Google AI Studio.
$DAT_AI_KEY also works if you prefer to keep the key in your shell config —
DAT uses it but never copies it into ~/.dat/config.yaml.
Run dat config to see which source your documents currently use.
📖 Usage
You can run dat from any project folder (Android, iOS, Web, etc.) once the setup is complete.
Generate Feature Documentation
# Build the document and open the Preview Panel to review it,
# attach screenshots by drag-and-drop, and export (the default)
dat generate-doc
# Pre-attach specific local images, then review in the panel
dat generate-doc -i path/to/image1.png path/to/image2.png
# Automation/CI only: write the file straight to disk with no review
dat generate-doc --headless -o docs/feature.docx
The Preview Panel is the default destination so nothing is exported before you
have seen it and decided whether screenshots are needed. --headless is the
explicit opt-out; if no graphical session is available the command says so and
points at that flag rather than quietly writing a file.
Other Commands
# Check if your environment is set up correctly
dat doctor
# View current configuration (including which content source is active)
dat config
# Set the name that appears as "Created By" on every generated document
dat config set author-name "Your Name"
dat config set author-email you@company.com
# Also settable: where documents are written, and the git binary to use
dat config set output-dir ./docs
dat config set git-path /usr/bin/git
Omit the value (dat config set author-name) to be prompted for it instead —
handy for names with spaces. The author DAT puts in a document is resolved in
this order:
--author "…"on the command line (or the Author field in the Preview Panel)dat config set author-name, or$DAT_AUTHOR- the author segment of your branch name, when it follows the
TICKET-First-Last-Topicconvention Developer, as a last resort
# Save a Gemini API key to enable AI-written summaries (or --clear to remove it)
dat save-api-key
Connecting DAT to your IDE or AI agent
dat mcp-setup # pick your client from a list
dat mcp-setup vscode # or name it: claude-code, claude-desktop, kiro,
# intellij, vscode, cursor, android-studio, antigravity
dat mcp-setup --list # just show the clients, and which are on this machine
It prints the JSON with your launcher path already filled in, points at the
config file that actually exists on this machine (including versioned ones like
~/.config/Google/AndroidStudio2026.1.1/mcp.json), uses the right shape for the
client (VS Code wants servers + "type": "stdio"; everyone else wants
mcpServers), and tells you if DAT is already configured there.
The server it configures is
dat mcp, which is deliberately not listed indat --help: your MCP client starts it for you ("args": ["mcp"]), it isn't a command to type. Run by hand it just sits there waiting for a client that never speaks. Full reference: MCP Integration.md.
Closing a stuck window
A DAT window can occasionally outlive every normal way of closing it — most
often a Preview Panel the MCP server launched detached, which no longer belongs
to any terminal. dat kill closes DAT's own windows and nothing else:
dat kill # close every DAT GUI window (Control Center + Preview Panels)
dat kill --list # show what would be closed, without closing anything
dat kill --all # also stop DAT MCP servers and other DAT CLI processes
dat kill --force # skip the polite close request and terminate immediately
It matches a process only when its command line is a real DAT entry point
(dat …, python -m dat.main …, python …/dat/main.py …), so your other
Python programs are never touched — and it never targets itself, or the
IDE/MCP server that started it. Windows that ignore the close request are
force-terminated after 5 seconds (--timeout to change that).
🧩 Custom Document Templates
Not every document fits the built-in layout. In the GUI (dat gui), the left
panel has a Custom Document section:
- + Create Your Custom Doc opens the Template Builder.
- Build the document from the Components palette — Heading, Subheading, Paragraph, Bullet List, Table, Image, Screenshots, Code Block, Two Columns, Separator.
- Group blocks into Sections. Each section can be reordered, hidden, and can optionally print its title as a document heading.
- Layers shows the document outline; Preview renders exactly what the
exported
.docxwill contain. - Save Template persists the structure and makes it the active document.
Once a template is active:
- Document Structure in the left panel lists one show/hide switch per template section — the same hide/show behaviour as the built-in layout.
- Document Content below it holds that structure's own components, ready to fill in. Edits show up in the preview as you type and are saved automatically — the preview rewrites the text of the widgets already on screen rather than redrawing the page, so it never flickers or jumps.
- Export DOCX renders through the template.
- The template (and which one was active) is remembered, so reopening DAT shows the same structure you built last time.
Templates are stored as one JSON file per template in ~/.dat/templates/.
Structure vs. content
The split is deliberate, and it decides where each control lives:
| Set in | Example | |
|---|---|---|
| Structure | Template Builder | sections, block order, a table's column count, headings and widths |
| Content | Control Center → Document Content | the text itself, list items, and a table's rows — add as many as you need with + Add Row, or remove one with ✕ |
So a table's columns are fixed when you design the document, while its rows grow as you fill it in — exactly like + Add Test Case on the standard document.
Column widths
Columns don't have to share the width evenly. Under each column heading in the builder is a − % + control that sets that column's relative width, so an Index / Case / Status table can be weighted 1 / 4 / 1:
Columns − 3 + ☑ Header row
[Index] [Case ] [Status]
− 17% + − 67% + − 17% +
Widths are relative rather than fixed measurements, so the table stays correct
in the preview, at any page size, and in the exported .docx (which is written
with a fixed layout so Word keeps them instead of re-fitting to the text).
Dynamic tokens
Any text field in a template can reference live values, resolved at render time:
| Token | Value |
|---|---|
{{title}} |
Ticket ID + topic |
{{ticket_id}} (or {{ticket}}) |
Ticket ID |
{{topic}} |
Feature topic |
{{author}} / {{approved_by}} |
Created By / Approved By |
{{branch}} |
Current git branch |
{{date}} |
Document date |
{{key_points}} |
The changes made (AI-written, or the changed file names) |
{{impact_areas}} (or {{modules}}) |
Affected modules |
{{test_cases}} |
Test cases written by Gemini or by your MCP agent |
{{test_recommendations}} |
Suggested QA steps |
{{changed_files}} |
Files your branch touched |
{{code_changes}} |
The code your branch added, per file |
{{code_diff}} |
The same excerpt in patch form (+/-/@@) |
Unknown tokens are left visible in the output so typos are easy to spot.
List tokens expand. {{key_points}}, {{test_cases}},
{{test_recommendations}}, {{changed_files}} and {{impact_areas}} join with
commas mid-sentence — but on their own in a bullet item or a table cell
they become one bullet (or row) per entry. In a table row, {{index}} numbers
them, which is all a Test Cases table needs:
| Index | Case | Status |
|---|---|---|
{{index}} |
{{test_cases}} |
Success |
An empty list contributes nothing rather than a blank bullet, and a table whose only row was an expansion is dropped entirely — so with no API key you get no half-empty Test Cases table, not a naked header row.
{{code_changes}} needs no API key. It comes from your branch diff, not
from a model, so a Code Block fills itself in every mode. It is bounded to keep
a document readable: 8 files, 30 lines per file, 120 lines total, and whatever
is cut is reported inline (... 42 more changed line(s) in this file ...)
rather than silently dropped.
The Control Center only offers the shared fields your document actually uses:
Created By and Approved By belong to the built-in metadata table, so a
custom structure hides them — unless it writes {{author}} or
{{approved_by}}, in which case the field reappears so there is somewhere to
type the value.
🔍 What the AI actually sees
When DAT writes the summary itself (the dat generate-doc / GUI path), this is
the evidence it works from:
| Source | Notes | |
|---|---|---|
| Diff | git diff HEAD + the content of new untracked files |
Falls back to <merge-base>..HEAD — every commit on the branch — when the tree is clean, and to HEAD~1..HEAD only if there's no branch point |
| File list | <merge-base>..HEAD plus git status --porcelain -uall |
The branch's committed work and what's still in the working tree. Modifications and additions only — deletions, untracked files and ignored files are left out, and renames are reported by destination |
| Commits | <merge-base>..HEAD (up to 25) |
This branch's own commits, not unrelated ones from main |
The diff is packed to a character budget that is shared across files, so a 20-file change is summarised from all 20 files rather than from whichever one git printed first. Whatever doesn't fit is named in the prompt, so the model can reference an omitted file without inventing its contents.
Raise or lower the budget with an environment variable (default 500,000
characters, roughly 125k tokens — about 12% of gemini-3.5-flash-lite's
1,048,576-token input window; ~370 files can each get a usable share):
export DAT_AI_DIFF_CHAR_BUDGET=1000000
The budget is a ceiling, not an amount: DAT sends the diff it actually has,
and this only ever trims it. A three-file bug fix sends a few thousand
characters whatever the budget says, so raising it changes nothing unless the
prompt reports Diff truncated to fit. Going much higher is not free — input
tokens cost money and time, and a single request larger than your account's
per-minute token allowance is rejected outright rather than queued. Check your
own limits at AI Studio.
Waiting, and what happens when it takes too long
The Preview Panel opens with the Git-diff content already in it — the changed file names — and shows a "Writing AI summary…" chip while the model works. When the answer arrives the content is replaced; anything you typed in the meantime wins, and the AI text stays one click away.
The answer deadline is 15 seconds, growing by 15s per extra 100k characters of prompt, capped at 180s — so a small fix still fails fast while a full-budget prompt gets the ~90s it needs:
| Prompt size | Deadline |
|---|---|
| up to 100k chars | 15s |
| 200k chars | 45s |
| 500k chars (the default budget) | 90s |
Miss it and the document keeps the Git-diff content with a "Retry AI" action — nothing is left half-written. Pin the deadline if you'd rather wait (or fail faster):
export DAT_AI_TIMEOUT_SECONDS=60
New files matter here: git diff never shows untracked content, so without
DAT reading them a brand-new screen or class would have its code unseen.
Binary and very large files are skipped, and your git index is never modified.
What is never sent
Untracked files are the one thing DAT reads by itself rather than getting from
git, so nothing in version control gatekeeps them — a .env sitting in your
project folder is a file no reviewer ever approved sharing. DAT refuses to read
them, and says so on stderr rather than dropping them silently:
| Refused | Examples |
|---|---|
| Credentials and local config | .env / .env.*, local.properties, google-services.json, GoogleService-Info.plist, serviceAccount*.json, *-adminsdk-*.json, terraform.tfstate, .npmrc, .netrc, .pgpass, and anything named *secret*, *credential* or *password* |
| Keys and certificates | *.pem, *.key, *.jks, *.keystore, *.p12, *.pfx, *.crt, id_rsa*, id_ed25519* |
| Generated / editor files | *.log, *.min.js, *.map, lock files, *.bak, .DS_Store |
Files git already ignores never reach DAT at all — git status omits them.
Add your own patterns (comma-separated globs, matched against the filename and the full path, case-insensitively):
export DAT_UNTRACKED_EXCLUDE="fixtures/*.json,*.internal"
To include a refused file deliberately, git add it. Staged content
reaches the AI through git diff HEAD like any other tracked change, which
makes sharing it a decision you made rather than a side effect of the file
being in the folder. The same follows in reverse: this filter covers untracked
files, so a tracked secret already committed to the repository is sent like
any other tracked change.
None of this applies to the MCP flow — there the calling model authors
key_points and test_cases from its own reading of the code, and DAT's AI
provider isn't called at all.
📝 Document Structure
The generated document follows a standard professional template:
- Heading: [Ticket ID] - [Topic]
- Task Detail Table: Includes Ticket No, Description, Date, and Author (Extracted from branch).
- Changes Done: High-level affected modules and brief AI-generated bullet points.
- Test Cases Table: A 3-column grid (Index, Case, Status) verifying the fix.
- Screenshots: Smartly positioned images with Test Case sub-headings.
Metadata
Release files for developer-automation-toolkit 0.2.1
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| developer_automation_toolkit-0.2.1.tar.gz | 420.3 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| developer_automation_toolkit-0.2.1-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 824.0 kB
Release files / developer_automation_toolkit-0.2.1.tar.gz
| Download URL | developer_automation_toolkit-0.2.1.tar.gz |
|---|---|
| Size | 420.3 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
cd34fa2a20a05921c68e6bd41a30d19088a5ae047ef31d1d6d57352cd5f57398
|
|
BLAKE2b-256 checksum How to use checksums |
1cd5ae568154d9b1bf60cdb5295bd0247a0b720e633aa6d52c7196c525aa1142
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 7, 2026.
Transparency logRelease files / developer_automation_toolkit-0.2.1-py3-none-any.whl
| Download URL | developer_automation_toolkit-0.2.1-py3-none-any.whl |
|---|---|
| Size | 403.7 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
f96ae501507f3e725d7d966f6609a0aaf4b02f5bcc710205174576a4dfc77154
|
|
BLAKE2b-256 checksum How to use checksums |
661520bc5bea194d059432098c8236dfc8782804e6f5a6c88766ccae447985f7
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Sep 7, 2026.
Transparency log