Skip to main content

Cross-platform Python utilities with CLI and AI-friendly JSON envelopes

Project description

中文 | English

Cross-platform Python utilities (2.0): same code on Windows, macOS, and Linux. The etool command exposes major features from the shell; use --json for a pretty-printed JSON envelope (2-space indent, valid JSON) suitable for AI agents and scripts (ok / err).

Requires Python 3.12+.

Install

pip install -U etool

After install, the etool entry point is on your PATH. You can also run python -m etool .... With uv from a clone: uv run etool ....


CLI: --json envelope

With --json, stdout is one JSON document per invocation (pretty-printed with 2-space indent):

  • Success: {"ok": true, "data": { ... }}
  • Failure: {"ok": false, "error": {"code", "message", "details"}}

Without --json, output is a human-readable form (often pretty-printed JSON for structured data).

Below, Input is the command; Output shows typical --json stdout (values such as paths, passwords, and timings are illustrative).


Version

Input

etool --json version

Output

{"ok": true, "data": {"version": "2.1.0"}}

Password

Random password

etool --json password random --length 16
{"ok": true, "data": {"password": "xYz9...16chars"}}

Base conversion

etool --json password convert-base --from-base 16 --to-base 2 A1F
{"ok": true, "data": {"result": "101000011111"}}

Speed (network / disk / memory)

Network (uses speedtest-cli; needs internet, can be slow)

etool --json speed network
{"ok": true, "data": {"report": "\n network test result:\ndownload speed: ... Mbps\n..."}}

Disk

etool --json speed disk --file-size-mb 10
{"ok": true, "data": {"report": "\n disk test result:\nread speed: ... MB/s\nwrite speed: ... MB/s\n"}}

Memory (stdlib buffer test)

etool --json speed memory --size-mb 32
{"ok": true, "data": {"report": "\n memory test result:\nread speed: ... MB/s\nwrite speed: ... MB/s"}}

PDF (ManagerPdf)

Merge

etool --json pdf merge --out merged.pdf part1.pdf part2.pdf
{"ok": true, "data": {"merged": "merged.pdf", "log": "merged: part1.pdf\nmerged: part2.pdf\nmerged file saved as: merged.pdf"}}

Split by page chunk size

etool --json pdf split-pages --pages 3 document.pdf
{"ok": true, "data": {"source": "document.pdf", "log": "generated: document_part_by_page1.pdf\n..."}}

Split into N parts

etool --json pdf split-num --parts 2 document.pdf
{"ok": true, "data": {"source": "document.pdf", "log": "..."}}

Encrypt / decrypt

etool --json pdf encrypt --password secret doc.pdf --out doc_encrypted.pdf
etool --json pdf decrypt --password secret doc_encrypted.pdf --out doc_clear.pdf
{"ok": true, "data": {"log": "encrypted file saved as: doc_encrypted.pdf"}}

Insert another PDF after a page index

etool --json pdf insert --pdf1 a.pdf --pdf2 b.pdf --after-page 0 --out out.pdf
{"ok": true, "data": {"output": "out.pdf", "log": "inserted file saved as: out.pdf"}}

Watermark

etool --json pdf watermark --target folder_or_file.pdf --watermark wm.pdf --out-dir watermarked
{"ok": true, "data": {"log": "..."}}

PDF → PNG images

etool --json pdf to-images --input doc.pdf --out-dir png_out --dpi 2
{"ok": true, "data": {"log": "found 1 PDF file(s)\n..."}}

Word (ManagerDocx)

Replace text

etool --json docx replace --path report.docx --old foo --new bar
{"ok": true, "data": {"path": "report.docx"}}

Swap page dimensions (landscape ↔ portrait style)

etool --json docx swap-dimensions --input in.docx --output out.docx
{"ok": true, "data": {"path": "out.docx"}}

Extract embedded images

etool --json docx extract-images --input in.docx --out-dir ./img_out
{"ok": true, "data": {"path": "./img_out"}}

Excel (ManagerExcel)

Copy formatting from a template workbook

etool --json excel copy-format --source template.xlsx --output out.xlsx
{"ok": true, "data": {"path": "out.xlsx"}}

Images (ManagerImage)

Merge left–right / top–bottom

etool --json image merge-lr left.png right.png --out lr.png
etool --json image merge-ud top.png bottom.png --out ud.png
{"ok": true, "data": {"path": "lr.png"}}

Pad to square / 3×3 grid crop / batch rename to WebP

etool --json image fill-square photo.jpg --out square.jpg
etool --json image cut-grid photo.jpg
etool --json image rename-webp ./shots --remove-original
{"ok": true, "data": {"paths": ["photo_cut00.jpg", "..."]}}

QR code (ManagerQrcode)

Generate

etool --json qrcode generate --text "https://example.com" --out qr.png
{"ok": true, "data": {"path": "qr.png"}}

Decode (local OpenCV)

etool --json qrcode decode qr.png
{"ok": true, "data": {"text": "https://example.com"}}

Jupyter (ManagerIpynb)

Merge all .ipynb in a directory

etool --json ipynb merge-dir ./notebooks/
{"ok": true, "data": {"path": "./notebooks.ipynb"}}

Notebook → Markdown file

etool --json ipynb to-markdown analysis.ipynb --out-dir ./md_out
{"ok": true, "data": {"path": "analysis.md"}}

Markdown (ManagerMd)

etool --json md to-docx notes.md --out notes.docx
etool --json md to-html notes.md --out notes.html
etool --json md tables-to-xlsx tables.md --out tables.xlsx
{"ok": true, "data": {"message": "已将Markdown文件转换为Word文档并保存至: notes.docx"}}

Standard-library usage analysis

One subcommand: stdlib analyze DIR. By default the envelope puts the nested counts under data.result (JSON object). With --json-string, the same analysis is returned as a single formatted JSON text under data.json (useful when you want one string field instead of nested JSON).

etool --json stdlib analyze ./src
etool --json stdlib analyze ./src --json-string
{"ok": true, "data": {"result": {"os": {"path.join": 12, "listdir": 3}}}}
{"ok": true, "data": {"json": "{\n  \"os\": {\n    \"path.join\": 12\n  }\n}"}}

Install requirements (ManagerInstall)

Uses python -m pip install internally.

etool --json install-reqs --file requirements.txt --failed-file failed.txt --retry 2
{"ok": true, "data": {"success": true}}

On failure:

{"ok": false, "error": {"code": "RUNTIME_ERROR", "message": "some packages failed to install", "details": {}}}

Scheduler (ManagerScheduler.parse_schedule_time — debug printout)

etool --json scheduler parse 120
etool --json scheduler parse '"08:00"'
{"ok": true, "data": {"log": "Execute every 120 seconds"}}

Email (ManagerEmail.send_email)

Do not paste real passwords into shell history; prefer environment-specific secrets in automation.

etool --json email send \
  --sender you@example.com \
  --password "$SMTP_PASSWORD" \
  --recipient other@example.com \
  --message "Hello" \
  --subject "Test"
{"ok": true, "data": {"result": "send success"}}

Python API and AI envelopes

Library usage matches the managers above. For structured envelopes in code:

from etool import ok, err, EtoolError, ErrorCode

payload = ok({"path": "/tmp/out.pdf"})
failure = err(EtoolError(ErrorCode.VALIDATION_ERROR, "bad input", {"field": "x"}))

Removed in 2.0

  • Windows COM / registry / context menu (ManagerMenu)
  • Screen sharing and Flask file share (ManagerShare)
  • GPU memory / CUDA speed test
  • ManagerPdf.pdfconverter (Office → PDF via local Microsoft Office)

Development

With uv: uv sync installs runtime deps plus the dev group (pytest). Commit uv.lock with the repo.

uv sync
uv run pytest tests/test_etool.py -v

With pip:

pip install -e ".[dev]"
pytest tests/test_etool.py -v

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

etool-2.1.0.tar.gz (40.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

etool-2.1.0-py3-none-any.whl (39.9 kB view details)

Uploaded Python 3

File details

Details for the file etool-2.1.0.tar.gz.

File metadata

  • Download URL: etool-2.1.0.tar.gz
  • Upload date:
  • Size: 40.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.9.25

File hashes

Hashes for etool-2.1.0.tar.gz
Algorithm Hash digest
SHA256 f50d34c393a0653bc160549ddc89bb9958703440c674973256d50ead3ebe3f85
MD5 ea43ae59a45537d13abca7c4ba5cbd2f
BLAKE2b-256 743b0fbd6be26c7605e25d2e970fec2a9f912420f2f8d7d9076f5ab247412b0d

See more details on using hashes here.

File details

Details for the file etool-2.1.0-py3-none-any.whl.

File metadata

  • Download URL: etool-2.1.0-py3-none-any.whl
  • Upload date:
  • Size: 39.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.9.25

File hashes

Hashes for etool-2.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 1dd8b4e529b915e1d1b39bec7435d28da791eaaf5dcd5e19374bd9d9ee701af7
MD5 3a12f39a03c2ee2c6164b57649322621
BLAKE2b-256 f82494a30c54a2c4c2c78ad91c347ea4e302094c0c42d0af2ead1abe9472596b

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page