evolver-tools 1.5.0__tar.gz → 2.5.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- evolver_tools-2.5.0/PKG-INFO +112 -0
- evolver_tools-2.5.0/README.md +90 -0
- evolver_tools-2.5.0/pyproject.toml +134 -0
- evolver_tools-2.5.0/src/evolver_tools/autoreg.py +150 -0
- evolver_tools-2.5.0/src/evolver_tools/cli.py +156 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/__init__.py +3 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/agent_b_tool.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/api_tester.py +229 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/ascii_gen.py +142 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/audit_log.py +261 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/backup.py +79 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/banner/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/banner/banner.py +484 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/banner.py +75 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/bookmark.py +276 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/cal_tool/__init__.py +1 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/cert_check.py +257 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/changelog_gen/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/changelog_gen/changelog_gen.py +199 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/changelog_gen.py +77 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/checksum_dir.py +301 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/clipboard/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/clipboard/clipboard.py +146 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/colorize.py +192 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/config_validator.py +312 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/crontab_helper.py +425 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/db_schema.py +209 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/dep_graph.py +250 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/diff_csv.py +195 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/disk_usage/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/disk_usage/disk_usage.py +176 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/env_manager.py +242 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/excel2csv.py +232 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/figlet_cli.py +142 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/figlet_tool.py +268 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/file_encrypt.py +176 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/firewall_rule.py +272 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/fmt/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/fmt/fmt.py +143 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/git_branch_cleaner.py +234 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/html2markdown.py +150 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/html2md.py +375 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/image_meta.py +318 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/ini_parser/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/ini_parser/ini_parser.py +167 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/join.py +24 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/joke.py +91 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/json_pretty/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/json_pretty/json_pretty.py +121 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/log_analyzer.py +276 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/log_tail.py +117 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/morse.py +122 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/net_speed.py +81 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/note_taker.py +116 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/otp_gen.py +229 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/password_strength.py +169 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/pr_tool/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/pr_tool/pr_tool.py +118 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/process_kill.py +252 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/progress_bar.py +46 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/qrcode.py +121 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/quote_tool/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/quote_tool/quote.py +211 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/rainbow.py +72 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/reminder.py +94 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/restore.py +111 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/scan_ports.py +101 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/service_check.py +210 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/shuffle.py +29 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/sort/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/sort/sort.py +180 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/spinner.py +81 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/split.py +39 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/split_tool/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/split_tool/split.py +190 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/sql2csv.py +603 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/ssh_key_gen.py +122 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/ssl_check.py +119 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/stopwatch.py +94 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/timer_pro/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/timer_pro/timer_pro.py +233 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/timer_pro.py +81 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/todo_cli.py +170 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/uniq_tool/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/uniq_tool/uniq.py +134 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/weather_cli.py +45 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/xml2json.py +83 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/yaml2json/__init__.py +2 -0
- evolver_tools-2.5.0/src/evolver_tools/vendor/yaml2json/yaml2json.py +311 -0
- evolver_tools-2.5.0/src/evolver_tools.egg-info/PKG-INFO +112 -0
- evolver_tools-2.5.0/src/evolver_tools.egg-info/SOURCES.txt +164 -0
- evolver_tools-2.5.0/src/evolver_tools.egg-info/entry_points.txt +100 -0
- evolver_tools-1.5.0/PKG-INFO +0 -107
- evolver_tools-1.5.0/README.md +0 -85
- evolver_tools-1.5.0/pyproject.toml +0 -72
- evolver_tools-1.5.0/src/evolver_tools/cli.py +0 -93
- evolver_tools-1.5.0/src/evolver_tools/vendor/cal_tool/__init__.py +0 -1
- evolver_tools-1.5.0/src/evolver_tools.egg-info/PKG-INFO +0 -107
- evolver_tools-1.5.0/src/evolver_tools.egg-info/SOURCES.txt +0 -80
- evolver_tools-1.5.0/src/evolver_tools.egg-info/entry_points.txt +0 -38
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/LICENSE +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/setup.cfg +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/b64/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/b64/b64.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/cal_tool/cli.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/chart_cli/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/chart_cli/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/colors/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/colors/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/cron/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/cron/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/csv_stats/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/csv_stats/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/csv_stats/analyzer.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/csv_stats/cli.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/diff_tool/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/diff_tool/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/dirsize/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/dt_convert.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/envcheck/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ff/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ff/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/find_dups/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/find_dups/cli.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/hashsum/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/hashsum/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/http_live/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/http_live/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ipcalc/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ipcalc/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ipinfo/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ipinfo/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/jq_lite/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/jq_lite/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/json2csv/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/json2csv/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/jsonql/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/jsonql/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/license_cli/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/license_cli/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/license_cli/cli.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/markdown_check/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/nb/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/nb/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/passgen/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/portcheck/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/portcheck/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/project_doctor/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/project_doctor/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ren/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/ren/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/siege_lite/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/siege_lite/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/smellfinder/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/smellfinder/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/sqlite_cli/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/sqlite_cli/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/sysmon/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/sysmon/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/timer/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/treedir/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/treedir/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/urlparse_tool/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/urlparse_tool/cli.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/uuid_tool/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/uuid_tool/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/web_summary/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/web_summary/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/wordcount/__init__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools/vendor/wordcount/__main__.py +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools.egg-info/dependency_links.txt +0 -0
- {evolver_tools-1.5.0 → evolver_tools-2.5.0}/src/evolver_tools.egg-info/top_level.txt +0 -0
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: evolver-tools
|
|
3
|
+
Version: 2.5.0
|
|
4
|
+
Summary: 99 essential CLI tools - one pip install
|
|
5
|
+
Author: EVOLVER
|
|
6
|
+
License-Expression: MIT
|
|
7
|
+
Project-URL: Homepage, https://evolver-dev.github.io/evolver-tools
|
|
8
|
+
Project-URL: Repository, https://github.com/evolver-dev/evolver-tools
|
|
9
|
+
Keywords: cli,devops,productivity,developer-tools,terminal
|
|
10
|
+
Classifier: Development Status :: 5 - Production/Stable
|
|
11
|
+
Classifier: Environment :: Console
|
|
12
|
+
Classifier: Intended Audience :: Developers
|
|
13
|
+
Classifier: Intended Audience :: System Administrators
|
|
14
|
+
Classifier: Operating System :: OS Independent
|
|
15
|
+
Classifier: Programming Language :: Python :: 3
|
|
16
|
+
Classifier: Programming Language :: Python :: 3 :: Only
|
|
17
|
+
Classifier: Topic :: Utilities
|
|
18
|
+
Requires-Python: >=3.8
|
|
19
|
+
Description-Content-Type: text/markdown
|
|
20
|
+
License-File: LICENSE
|
|
21
|
+
Dynamic: license-file
|
|
22
|
+
|
|
23
|
+
# EVOLVER Tools
|
|
24
|
+
|
|
25
|
+
**50 essential CLI tools — one `pip install`.**
|
|
26
|
+
|
|
27
|
+
Zero-dependency (49/50), cross-platform, production-ready.
|
|
28
|
+
Systems ops, data processing, dev tools, security, and creativity.
|
|
29
|
+
~170KB total — one install, not 50.
|
|
30
|
+
|
|
31
|
+
## Quick Start
|
|
32
|
+
|
|
33
|
+
```bash
|
|
34
|
+
pip install evolver-tools
|
|
35
|
+
evtool list # Show all 50 tools
|
|
36
|
+
evtool ff < data.txt # Fuzzy search through data
|
|
37
|
+
evtool sysmon # Launch system monitor
|
|
38
|
+
evtool sort -n data.txt # Numeric sort
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
## Tools
|
|
42
|
+
|
|
43
|
+
### Ops
|
|
44
|
+
|
|
45
|
+
| Tool | Description | Selling point |
|
|
46
|
+
|------|-------------|---------------|
|
|
47
|
+
| **sysmon** | Real-time system monitor (curses TUI — CPU/mem/disk/net/processes) | See your server breathe |
|
|
48
|
+
| **dirsize** | Recursive directory space analyzer | Find what's eating your disk |
|
|
49
|
+
| **envcheck** | Environment variable validator (missing keys, formats) | Stop .env typos from breaking prod |
|
|
50
|
+
| **portcheck** | TCP port scanner & service detection | Port open? Service running? |
|
|
51
|
+
| **siege-lite** | HTTP load tester (concurrency, latency percentile) | How many req/s can your app handle? |
|
|
52
|
+
| **http-live** | SSE hot-reload HTTP server for development | Edit code, see changes. No refresh. |
|
|
53
|
+
| **ipinfo** | Public IP & geolocation lookup | Where's this server? |
|
|
54
|
+
| **hashsum** | File hash verification (MD5/SHA-1/256/512/BLAKE2, auto-detect) | Verify downloads in one command |
|
|
55
|
+
| **find-dups** | Find duplicate files by SHA256 hash, size, or name | Reclaim gigabytes |
|
|
56
|
+
|
|
57
|
+
### Developer
|
|
58
|
+
|
|
59
|
+
| Tool | Description | Selling point |
|
|
60
|
+
|------|-------------|---------------|
|
|
61
|
+
| **smellfinder** | Python code smell detector (AST-based, 10+ patterns) | Lint without pip install pylint |
|
|
62
|
+
| **project-doctor** | Project health checker (meta, structure, quality) | Project checkup in one command |
|
|
63
|
+
| **license-cli** | Open-source license generator/validator | License your repo instantly |
|
|
64
|
+
| **markdown-check** | Markdown format validator & style checker | Docs that don't embarrass you |
|
|
65
|
+
| **sqlite-cli** | SQLite query tool — CSV/JSON/table output | Query .db files without a GUI |
|
|
66
|
+
| **b64** | Base64 encode/decode with auto-detection | Paste, pipe, done |
|
|
67
|
+
| **jsonql** | Zero-dep JSON query tool (SQL-like syntax) | `jsonql "SELECT name FROM data WHERE age > 18"` |
|
|
68
|
+
| **jq-lite** | jq-style JSON query — filter, extract, transform | jq without installing jq |
|
|
69
|
+
| **urlparse** | URL parser & debugger | What's in that URL? |
|
|
70
|
+
| **colors** | 256-color table & HEX↔RGB conversion | Design that terminal theme |
|
|
71
|
+
| **fmt** | Code/text formatter — trailing whitespace, EOF newline, indent | Clean files, one command |
|
|
72
|
+
|
|
73
|
+
### Data & Analysis
|
|
74
|
+
|
|
75
|
+
| Tool | Description | Selling point |
|
|
76
|
+
|------|-------------|---------------|
|
|
77
|
+
| **csv-stats** | CSV column analysis — histograms, frequencies, correlations | Understand your CSV in seconds |
|
|
78
|
+
| **json2csv** | JSON to CSV converter with nested key flattening | API response → spreadsheet |
|
|
79
|
+
| **chart-cli** | Terminal chart generator — bar, line, pie, histogram | Charts without leaving the terminal |
|
|
80
|
+
| **cal** | Calendar & date calculator | What day is 45 days from now? |
|
|
81
|
+
| **web-summary** | Web page content extractor (title, body, links) | Read the web from your terminal |
|
|
82
|
+
| **yaml2json** | Convert YAML to JSON (zero dependencies, basic YAML subset) | Config files \u2192 pipeable JSON |
|
|
83
|
+
| **sort** | Line sorting — alpha, numeric, reverse, unique, by column | Sort data without `sort(1)` |
|
|
84
|
+
|
|
85
|
+
### Productivity
|
|
86
|
+
|
|
87
|
+
| Tool | Description | Selling point |
|
|
88
|
+
|------|-------------|---------------|
|
|
89
|
+
| **ff** | Interactive fuzzy finder (fzf, pure Python curses TUI) | Search files, history, anything |
|
|
90
|
+
| **nb** | Command-line notebook (JSON storage, full-text search) | Notes in your terminal |
|
|
91
|
+
| **ren** | Batch file renamer (prefix/suffix/regex/numbering) | Rename 100 files in one command |
|
|
92
|
+
| **timer** | Countdown timer & stopwatch with desktop notifications | Pomodoro in your terminal |
|
|
93
|
+
| **treedir** | Directory tree visualizer with depth control | `tree` on every OS |
|
|
94
|
+
| **wordcount** | Enhanced word/char/line counter with language detection | wc on steroids |
|
|
95
|
+
| **dt** | Date/time format converter (timestamps, timezones) | `dt 1735689600` → human date |
|
|
96
|
+
|
|
97
|
+
### Security
|
|
98
|
+
|
|
99
|
+
| Tool | Description | Selling point |
|
|
100
|
+
|------|-------------|---------------|
|
|
101
|
+
| **passgen** | Password generator with entropy display & charset rules | Generate passwords that don't suck |
|
|
102
|
+
| **uuid** | UUID generator (v1/v3/v4/v5/v7) | v4, v7, any UUID in one command |
|
|
103
|
+
| **cron** | Cron expression parser & next-run calculator | "What does 0 2 * * 1 actually run?" |
|
|
104
|
+
|
|
105
|
+
## Requirements
|
|
106
|
+
|
|
107
|
+
- Python 3.8+
|
|
108
|
+
- No external dependencies (38 of 39 tools use stdlib only; ipinfo hits ip-api.com)
|
|
109
|
+
|
|
110
|
+
## License
|
|
111
|
+
|
|
112
|
+
MIT
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
# EVOLVER Tools
|
|
2
|
+
|
|
3
|
+
**50 essential CLI tools — one `pip install`.**
|
|
4
|
+
|
|
5
|
+
Zero-dependency (49/50), cross-platform, production-ready.
|
|
6
|
+
Systems ops, data processing, dev tools, security, and creativity.
|
|
7
|
+
~170KB total — one install, not 50.
|
|
8
|
+
|
|
9
|
+
## Quick Start
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
pip install evolver-tools
|
|
13
|
+
evtool list # Show all 50 tools
|
|
14
|
+
evtool ff < data.txt # Fuzzy search through data
|
|
15
|
+
evtool sysmon # Launch system monitor
|
|
16
|
+
evtool sort -n data.txt # Numeric sort
|
|
17
|
+
```
|
|
18
|
+
|
|
19
|
+
## Tools
|
|
20
|
+
|
|
21
|
+
### Ops
|
|
22
|
+
|
|
23
|
+
| Tool | Description | Selling point |
|
|
24
|
+
|------|-------------|---------------|
|
|
25
|
+
| **sysmon** | Real-time system monitor (curses TUI — CPU/mem/disk/net/processes) | See your server breathe |
|
|
26
|
+
| **dirsize** | Recursive directory space analyzer | Find what's eating your disk |
|
|
27
|
+
| **envcheck** | Environment variable validator (missing keys, formats) | Stop .env typos from breaking prod |
|
|
28
|
+
| **portcheck** | TCP port scanner & service detection | Port open? Service running? |
|
|
29
|
+
| **siege-lite** | HTTP load tester (concurrency, latency percentile) | How many req/s can your app handle? |
|
|
30
|
+
| **http-live** | SSE hot-reload HTTP server for development | Edit code, see changes. No refresh. |
|
|
31
|
+
| **ipinfo** | Public IP & geolocation lookup | Where's this server? |
|
|
32
|
+
| **hashsum** | File hash verification (MD5/SHA-1/256/512/BLAKE2, auto-detect) | Verify downloads in one command |
|
|
33
|
+
| **find-dups** | Find duplicate files by SHA256 hash, size, or name | Reclaim gigabytes |
|
|
34
|
+
|
|
35
|
+
### Developer
|
|
36
|
+
|
|
37
|
+
| Tool | Description | Selling point |
|
|
38
|
+
|------|-------------|---------------|
|
|
39
|
+
| **smellfinder** | Python code smell detector (AST-based, 10+ patterns) | Lint without pip install pylint |
|
|
40
|
+
| **project-doctor** | Project health checker (meta, structure, quality) | Project checkup in one command |
|
|
41
|
+
| **license-cli** | Open-source license generator/validator | License your repo instantly |
|
|
42
|
+
| **markdown-check** | Markdown format validator & style checker | Docs that don't embarrass you |
|
|
43
|
+
| **sqlite-cli** | SQLite query tool — CSV/JSON/table output | Query .db files without a GUI |
|
|
44
|
+
| **b64** | Base64 encode/decode with auto-detection | Paste, pipe, done |
|
|
45
|
+
| **jsonql** | Zero-dep JSON query tool (SQL-like syntax) | `jsonql "SELECT name FROM data WHERE age > 18"` |
|
|
46
|
+
| **jq-lite** | jq-style JSON query — filter, extract, transform | jq without installing jq |
|
|
47
|
+
| **urlparse** | URL parser & debugger | What's in that URL? |
|
|
48
|
+
| **colors** | 256-color table & HEX↔RGB conversion | Design that terminal theme |
|
|
49
|
+
| **fmt** | Code/text formatter — trailing whitespace, EOF newline, indent | Clean files, one command |
|
|
50
|
+
|
|
51
|
+
### Data & Analysis
|
|
52
|
+
|
|
53
|
+
| Tool | Description | Selling point |
|
|
54
|
+
|------|-------------|---------------|
|
|
55
|
+
| **csv-stats** | CSV column analysis — histograms, frequencies, correlations | Understand your CSV in seconds |
|
|
56
|
+
| **json2csv** | JSON to CSV converter with nested key flattening | API response → spreadsheet |
|
|
57
|
+
| **chart-cli** | Terminal chart generator — bar, line, pie, histogram | Charts without leaving the terminal |
|
|
58
|
+
| **cal** | Calendar & date calculator | What day is 45 days from now? |
|
|
59
|
+
| **web-summary** | Web page content extractor (title, body, links) | Read the web from your terminal |
|
|
60
|
+
| **yaml2json** | Convert YAML to JSON (zero dependencies, basic YAML subset) | Config files \u2192 pipeable JSON |
|
|
61
|
+
| **sort** | Line sorting — alpha, numeric, reverse, unique, by column | Sort data without `sort(1)` |
|
|
62
|
+
|
|
63
|
+
### Productivity
|
|
64
|
+
|
|
65
|
+
| Tool | Description | Selling point |
|
|
66
|
+
|------|-------------|---------------|
|
|
67
|
+
| **ff** | Interactive fuzzy finder (fzf, pure Python curses TUI) | Search files, history, anything |
|
|
68
|
+
| **nb** | Command-line notebook (JSON storage, full-text search) | Notes in your terminal |
|
|
69
|
+
| **ren** | Batch file renamer (prefix/suffix/regex/numbering) | Rename 100 files in one command |
|
|
70
|
+
| **timer** | Countdown timer & stopwatch with desktop notifications | Pomodoro in your terminal |
|
|
71
|
+
| **treedir** | Directory tree visualizer with depth control | `tree` on every OS |
|
|
72
|
+
| **wordcount** | Enhanced word/char/line counter with language detection | wc on steroids |
|
|
73
|
+
| **dt** | Date/time format converter (timestamps, timezones) | `dt 1735689600` → human date |
|
|
74
|
+
|
|
75
|
+
### Security
|
|
76
|
+
|
|
77
|
+
| Tool | Description | Selling point |
|
|
78
|
+
|------|-------------|---------------|
|
|
79
|
+
| **passgen** | Password generator with entropy display & charset rules | Generate passwords that don't suck |
|
|
80
|
+
| **uuid** | UUID generator (v1/v3/v4/v5/v7) | v4, v7, any UUID in one command |
|
|
81
|
+
| **cron** | Cron expression parser & next-run calculator | "What does 0 2 * * 1 actually run?" |
|
|
82
|
+
|
|
83
|
+
## Requirements
|
|
84
|
+
|
|
85
|
+
- Python 3.8+
|
|
86
|
+
- No external dependencies (38 of 39 tools use stdlib only; ipinfo hits ip-api.com)
|
|
87
|
+
|
|
88
|
+
## License
|
|
89
|
+
|
|
90
|
+
MIT
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools>=64.0", "wheel"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "evolver-tools"
|
|
7
|
+
version = "2.5.0"
|
|
8
|
+
description = "99 essential CLI tools - one pip install"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
license = "MIT"
|
|
11
|
+
requires-python = ">=3.8"
|
|
12
|
+
keywords = ["cli", "devops", "productivity", "developer-tools", "terminal"]
|
|
13
|
+
authors = [
|
|
14
|
+
{name = "EVOLVER"},
|
|
15
|
+
]
|
|
16
|
+
classifiers = [
|
|
17
|
+
"Development Status :: 5 - Production/Stable",
|
|
18
|
+
"Environment :: Console",
|
|
19
|
+
"Intended Audience :: Developers",
|
|
20
|
+
"Intended Audience :: System Administrators",
|
|
21
|
+
"Operating System :: OS Independent",
|
|
22
|
+
"Programming Language :: Python :: 3",
|
|
23
|
+
"Programming Language :: Python :: 3 :: Only",
|
|
24
|
+
"Topic :: Utilities",
|
|
25
|
+
]
|
|
26
|
+
|
|
27
|
+
[project.urls]
|
|
28
|
+
Homepage = "https://evolver-dev.github.io/evolver-tools"
|
|
29
|
+
Repository = "https://github.com/evolver-dev/evolver-tools"
|
|
30
|
+
|
|
31
|
+
[project.scripts]
|
|
32
|
+
evtool = "evolver_tools.cli:main"
|
|
33
|
+
colorize = "evolver_tools.vendor.colorize:main"
|
|
34
|
+
env-manager = "evolver_tools.vendor.env_manager:main"
|
|
35
|
+
git-branch-cleaner = "evolver_tools.vendor.git_branch_cleaner:main"
|
|
36
|
+
diff-csv = "evolver_tools.vendor.diff_csv:main"
|
|
37
|
+
excel2csv = "evolver_tools.vendor.excel2csv:main"
|
|
38
|
+
sql2csv = "evolver_tools.vendor.sql2csv:main"
|
|
39
|
+
html2md = "evolver_tools.vendor.html2md:main"
|
|
40
|
+
process-kill = "evolver_tools.vendor.process_kill:main"
|
|
41
|
+
service-check = "evolver_tools.vendor.service_check:main"
|
|
42
|
+
crontab-helper = "evolver_tools.vendor.crontab_helper:main"
|
|
43
|
+
cert-check = "evolver_tools.vendor.cert_check:main"
|
|
44
|
+
checksum-dir = "evolver_tools.vendor.checksum_dir:main"
|
|
45
|
+
b64 = "evolver_tools.vendor.b64:main"
|
|
46
|
+
ff = "evolver_tools.vendor.ff:main"
|
|
47
|
+
cal = "evolver_tools.vendor.cal_tool.cli:main"
|
|
48
|
+
chart-cli = "evolver_tools.vendor.chart_cli:main"
|
|
49
|
+
colors = "evolver_tools.vendor.colors:main"
|
|
50
|
+
cron = "evolver_tools.vendor.cron:main"
|
|
51
|
+
csv-stats = "evolver_tools.vendor.csv_stats.cli:main"
|
|
52
|
+
diff = "evolver_tools.vendor.diff_tool:main"
|
|
53
|
+
dirsize = "evolver_tools.vendor.dirsize:entry"
|
|
54
|
+
dt = "evolver_tools.vendor.dt_convert:main"
|
|
55
|
+
envcheck = "evolver_tools.vendor.envcheck:main"
|
|
56
|
+
find-dups = "evolver_tools.vendor.find_dups.cli:main"
|
|
57
|
+
hashsum = "evolver_tools.vendor.hashsum:main"
|
|
58
|
+
http-live = "evolver_tools.vendor.http_live:main"
|
|
59
|
+
ipcalc = "evolver_tools.vendor.ipcalc:main"
|
|
60
|
+
ipinfo = "evolver_tools.vendor.ipinfo:main"
|
|
61
|
+
jq-lite = "evolver_tools.vendor.jq_lite:main"
|
|
62
|
+
json2csv = "evolver_tools.vendor.json2csv:main"
|
|
63
|
+
jsonql = "evolver_tools.vendor.jsonql:main"
|
|
64
|
+
license-cli = "evolver_tools.vendor.license_cli.cli:main"
|
|
65
|
+
markdown-check = "evolver_tools.vendor.markdown_check:main"
|
|
66
|
+
nb = "evolver_tools.vendor.nb:main"
|
|
67
|
+
passgen = "evolver_tools.vendor.passgen:entry"
|
|
68
|
+
portcheck = "evolver_tools.vendor.portcheck.__main__:main"
|
|
69
|
+
project-doctor = "evolver_tools.vendor.project_doctor:main"
|
|
70
|
+
ren = "evolver_tools.vendor.ren:main"
|
|
71
|
+
siege-lite = "evolver_tools.vendor.siege_lite:main"
|
|
72
|
+
smellfinder = "evolver_tools.vendor.smellfinder:main"
|
|
73
|
+
sqlite-cli = "evolver_tools.vendor.sqlite_cli:main"
|
|
74
|
+
sysmon = "evolver_tools.vendor.sysmon:entry"
|
|
75
|
+
timer = "evolver_tools.vendor.timer:entry"
|
|
76
|
+
treedir = "evolver_tools.vendor.treedir.__main__:main"
|
|
77
|
+
urlparse = "evolver_tools.vendor.urlparse_tool.cli:main"
|
|
78
|
+
uuid = "evolver_tools.vendor.uuid_tool:main"
|
|
79
|
+
web-summary = "evolver_tools.vendor.web_summary:main"
|
|
80
|
+
wordcount = "evolver_tools.vendor.wordcount.__main__:main"
|
|
81
|
+
fmt = "evolver_tools.vendor.fmt:main"
|
|
82
|
+
yaml2json = "evolver_tools.vendor.yaml2json:main"
|
|
83
|
+
sort = "evolver_tools.vendor.sort:main"
|
|
84
|
+
pr-tool = "evolver_tools.vendor.pr_tool:main"
|
|
85
|
+
clipboard = "evolver_tools.vendor.clipboard:main"
|
|
86
|
+
uniq = "evolver_tools.vendor.uniq_tool:main"
|
|
87
|
+
changelog-gen = "evolver_tools.vendor.changelog_gen:main"
|
|
88
|
+
timer-pro = "evolver_tools.vendor.timer_pro:main"
|
|
89
|
+
banner-gen = "evolver_tools.vendor.banner:main"
|
|
90
|
+
json-pretty = "evolver_tools.vendor.json_pretty:main"
|
|
91
|
+
ini-parser = "evolver_tools.vendor.ini_parser:main"
|
|
92
|
+
split = "evolver_tools.vendor.split_tool:main"
|
|
93
|
+
disk-usage = "evolver_tools.vendor.disk_usage:main"
|
|
94
|
+
quote = "evolver_tools.vendor.quote_tool:main"
|
|
95
|
+
shuffle = "evolver_tools.vendor.shuffle:main"
|
|
96
|
+
join = "evolver_tools.vendor.join:main"
|
|
97
|
+
weather-cli = "evolver_tools.vendor.weather_cli:main"
|
|
98
|
+
progress-bar = "evolver_tools.vendor.progress_bar:main"
|
|
99
|
+
xml2json = "evolver_tools.vendor.xml2json:main"
|
|
100
|
+
backup = "evolver_tools.vendor.backup:main"
|
|
101
|
+
net-speed = "evolver_tools.vendor.net_speed:main"
|
|
102
|
+
ascii-gen = "evolver_tools.vendor.ascii_gen:main"
|
|
103
|
+
stopwatch = "evolver_tools.vendor.stopwatch:main"
|
|
104
|
+
qrcode = "evolver_tools.vendor.qrcode:main"
|
|
105
|
+
restore = "evolver_tools.vendor.restore:main"
|
|
106
|
+
reminder = "evolver_tools.vendor.reminder:main"
|
|
107
|
+
todo-cli = "evolver_tools.vendor.todo_cli:main"
|
|
108
|
+
log-tail = "evolver_tools.vendor.log_tail:main"
|
|
109
|
+
spinner = "evolver_tools.vendor.spinner:main"
|
|
110
|
+
joke = "evolver_tools.vendor.joke:main"
|
|
111
|
+
morse = "evolver_tools.vendor.morse:main"
|
|
112
|
+
password-strength = "evolver_tools.vendor.password_strength:main"
|
|
113
|
+
html2markdown = "evolver_tools.vendor.html2markdown:main"
|
|
114
|
+
rainbow = "evolver_tools.vendor.rainbow:main"
|
|
115
|
+
figlet-cli = "evolver_tools.vendor.figlet_cli:main"
|
|
116
|
+
file-encrypt = "evolver_tools.vendor.file_encrypt:main"
|
|
117
|
+
otp-gen = "evolver_tools.vendor.otp_gen:main"
|
|
118
|
+
ssl-check = "evolver_tools.vendor.ssl_check:main"
|
|
119
|
+
scan-ports = "evolver_tools.vendor.scan_ports:main"
|
|
120
|
+
note-taker = "evolver_tools.vendor.note_taker:main"
|
|
121
|
+
bookmark = "evolver_tools.vendor.bookmark:main"
|
|
122
|
+
dep-graph = "evolver_tools.vendor.dep_graph:main"
|
|
123
|
+
image-meta = "evolver_tools.vendor.image_meta:main"
|
|
124
|
+
api-tester = "evolver_tools.vendor.api_tester:main"
|
|
125
|
+
audit-log = "evolver_tools.vendor.audit_log:main"
|
|
126
|
+
config-validator = "evolver_tools.vendor.config_validator:main"
|
|
127
|
+
db-schema = "evolver_tools.vendor.db_schema:main"
|
|
128
|
+
firewall-rule = "evolver_tools.vendor.firewall_rule:main"
|
|
129
|
+
log-analyzer = "evolver_tools.vendor.log_analyzer:main"
|
|
130
|
+
ssh-key-gen = "evolver_tools.vendor.ssh_key_gen:main"
|
|
131
|
+
|
|
132
|
+
[tool.setuptools.packages.find]
|
|
133
|
+
where = ["src"]
|
|
134
|
+
include = ["evolver_tools*"]
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""
|
|
3
|
+
EVOLVER Auto-Registration — eliminates the TOOLS dict bottleneck.
|
|
4
|
+
|
|
5
|
+
Instead of manually editing cli.py's TOOLS dict, any module in the vendor/
|
|
6
|
+
directory that exports TOOL_META is automatically discovered and registered.
|
|
7
|
+
|
|
8
|
+
Tool authors just need to add to their Python file:
|
|
9
|
+
TOOL_META = {"name": "my-tool", "desc": "What it does"}
|
|
10
|
+
|
|
11
|
+
The auto-register scans vendor/ at import time and builds the full registry.
|
|
12
|
+
"""
|
|
13
|
+
|
|
14
|
+
import importlib
|
|
15
|
+
import importlib.util
|
|
16
|
+
import inspect
|
|
17
|
+
import os
|
|
18
|
+
import pkgutil
|
|
19
|
+
import sys
|
|
20
|
+
|
|
21
|
+
VENDOR_DIR = os.path.join(os.path.dirname(__file__), "vendor")
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
def auto_discover():
|
|
25
|
+
"""
|
|
26
|
+
Scan the vendor/ directory and discover all tools with TOOL_META.
|
|
27
|
+
|
|
28
|
+
Returns:
|
|
29
|
+
dict: {tool_name: {"module": "module.path", "func": "main", "desc": "..."}}
|
|
30
|
+
"""
|
|
31
|
+
tools = {}
|
|
32
|
+
vendor_path = VENDOR_DIR
|
|
33
|
+
|
|
34
|
+
if not os.path.isdir(vendor_path):
|
|
35
|
+
return tools
|
|
36
|
+
|
|
37
|
+
# Scan all items in vendor directory
|
|
38
|
+
for entry in sorted(os.listdir(vendor_path)):
|
|
39
|
+
entry_path = os.path.join(vendor_path, entry)
|
|
40
|
+
mod_name = None
|
|
41
|
+
|
|
42
|
+
# Case 1: Single .py file (e.g., colorize.py)
|
|
43
|
+
if entry.endswith(".py") and entry != "__init__.py":
|
|
44
|
+
mod_name = f"evolver_tools.vendor.{entry[:-3]}"
|
|
45
|
+
|
|
46
|
+
# Case 2: Package directory (e.g., b64/)
|
|
47
|
+
elif os.path.isdir(entry_path) and not entry.startswith("_"):
|
|
48
|
+
init_path = os.path.join(entry_path, "__init__.py")
|
|
49
|
+
cli_path = os.path.join(entry_path, "cli.py")
|
|
50
|
+
main_path = os.path.join(entry_path, "__main__.py")
|
|
51
|
+
if os.path.isfile(init_path) or os.path.isfile(cli_path) or os.path.isfile(main_path):
|
|
52
|
+
mod_name = f"evolver_tools.vendor.{entry}"
|
|
53
|
+
|
|
54
|
+
if mod_name is None:
|
|
55
|
+
continue
|
|
56
|
+
|
|
57
|
+
# Try to import and read TOOL_META
|
|
58
|
+
try:
|
|
59
|
+
mod = importlib.import_module(mod_name)
|
|
60
|
+
except Exception as e:
|
|
61
|
+
# Silently skip modules that can't be imported
|
|
62
|
+
continue
|
|
63
|
+
|
|
64
|
+
# Check for TOOL_META
|
|
65
|
+
meta = getattr(mod, "TOOL_META", None)
|
|
66
|
+
if meta is None:
|
|
67
|
+
# No TOOL_META defined — skip this module
|
|
68
|
+
continue
|
|
69
|
+
|
|
70
|
+
tool_name = meta.get("name", entry.replace("_", "-").replace(".py", ""))
|
|
71
|
+
tool_desc = meta.get("desc", getattr(mod, "__doc__", "") or f"Tool: {entry}")
|
|
72
|
+
func_name = meta.get("func", "main")
|
|
73
|
+
|
|
74
|
+
# Determine the correct function reference
|
|
75
|
+
if func_name and "." in func_name:
|
|
76
|
+
# e.g., "cli:main" — handled differently
|
|
77
|
+
pass
|
|
78
|
+
|
|
79
|
+
# Prefer `main` function, fallback to entry, then any callable
|
|
80
|
+
actual_func = func_name
|
|
81
|
+
if not hasattr(mod, actual_func):
|
|
82
|
+
candidates = ["main", "entry", "run"]
|
|
83
|
+
for c in candidates:
|
|
84
|
+
if hasattr(mod, c):
|
|
85
|
+
actual_func = c
|
|
86
|
+
break
|
|
87
|
+
|
|
88
|
+
tools[tool_name] = {
|
|
89
|
+
"module": mod_name,
|
|
90
|
+
"func": actual_func,
|
|
91
|
+
"desc": tool_desc,
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
return tools
|
|
95
|
+
|
|
96
|
+
|
|
97
|
+
def auto_generate_pyproject(vendor_dir=None):
|
|
98
|
+
"""
|
|
99
|
+
Generate the [project.scripts] section for pyproject.toml.
|
|
100
|
+
Useful for batch-updating the console_scripts entries.
|
|
101
|
+
|
|
102
|
+
Returns:
|
|
103
|
+
str: The scripts section as TOML text (no leading indent)
|
|
104
|
+
"""
|
|
105
|
+
if vendor_dir is None:
|
|
106
|
+
vendor_dir = VENDOR_DIR
|
|
107
|
+
|
|
108
|
+
lines = ["[project.scripts]"]
|
|
109
|
+
lines.append('evtool = "evolver_tools.cli:main"')
|
|
110
|
+
|
|
111
|
+
for entry in sorted(os.listdir(vendor_dir)):
|
|
112
|
+
# Same logic as above
|
|
113
|
+
entry_path = os.path.join(vendor_dir, entry)
|
|
114
|
+
if entry.endswith(".py") and entry != "__init__.py":
|
|
115
|
+
mod_path = f"evolver_tools.vendor.{entry[:-3]}"
|
|
116
|
+
tool_name = entry[:-3].replace("_", "-")
|
|
117
|
+
lines.append(f'{tool_name} = "{mod_path}:main"')
|
|
118
|
+
elif os.path.isdir(entry_path) and not entry.startswith("_"):
|
|
119
|
+
init_path = os.path.join(entry_path, "__init__.py")
|
|
120
|
+
cli_path = os.path.join(entry_path, "cli.py")
|
|
121
|
+
main_path = os.path.join(entry_path, "__main__.py")
|
|
122
|
+
if os.path.isfile(init_path) or os.path.isfile(cli_path) or os.path.isfile(main_path):
|
|
123
|
+
mod_path = f"evolver_tools.vendor.{entry}"
|
|
124
|
+
# Try to determine the entry function
|
|
125
|
+
func = "main"
|
|
126
|
+
try:
|
|
127
|
+
spec = importlib.util.find_spec(mod_path)
|
|
128
|
+
if spec and spec.loader:
|
|
129
|
+
mod = importlib.import_module(mod_path)
|
|
130
|
+
if hasattr(mod, "entry"):
|
|
131
|
+
func = "entry"
|
|
132
|
+
elif hasattr(mod, "run"):
|
|
133
|
+
func = "run"
|
|
134
|
+
except Exception:
|
|
135
|
+
pass
|
|
136
|
+
tool_name = entry.replace("_", "-")
|
|
137
|
+
lines.append(f'{tool_name} = "{mod_path}:{func}"')
|
|
138
|
+
|
|
139
|
+
return "\n".join(lines)
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
if __name__ == "__main__":
|
|
143
|
+
tools = auto_discover()
|
|
144
|
+
print(f"Auto-discovered {len(tools)} tools:")
|
|
145
|
+
for name, info in sorted(tools.items()):
|
|
146
|
+
print(f" {name:<20} → {info['module']}.{info['func']} ({info['desc']})")
|
|
147
|
+
print()
|
|
148
|
+
print("=" * 60)
|
|
149
|
+
print("Generated pyproject.toml scripts section:")
|
|
150
|
+
print(auto_generate_pyproject())
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""evolver CLI - Unified interface for all EVOLVER tools."""
|
|
3
|
+
|
|
4
|
+
import sys, importlib, os
|
|
5
|
+
|
|
6
|
+
# Tool registry
|
|
7
|
+
TOOLS = {
|
|
8
|
+
"colorize": {"module": "evolver_tools.vendor.colorize", "func": "main", "desc": "Terminal text colorizer"},
|
|
9
|
+
"env-manager": {"module": "evolver_tools.vendor.env_manager", "func": "main", "desc": ".env file manager"},
|
|
10
|
+
"git-branch-cleaner": {"module": "evolver_tools.vendor.git_branch_cleaner", "func": "main", "desc": "Clean stale git branches"},
|
|
11
|
+
"diff-csv": {"module": "evolver_tools.vendor.diff_csv", "func": "main", "desc": "Diff two CSV files"},
|
|
12
|
+
"excel2csv": {"module": "evolver_tools.vendor.excel2csv", "func": "main", "desc": "Convert Excel to CSV"},
|
|
13
|
+
"sql2csv": {"module": "evolver_tools.vendor.sql2csv", "func": "main", "desc": "Run SQL on CSV files"},
|
|
14
|
+
"html2md": {"module": "evolver_tools.vendor.html2md", "func": "main", "desc": "Convert HTML to Markdown"},
|
|
15
|
+
"process-kill": {"module": "evolver_tools.vendor.process_kill", "func": "main", "desc": "Kill processes by name/port/user"},
|
|
16
|
+
"service-check": {"module": "evolver_tools.vendor.service_check", "func": "main", "desc": "Check systemd service status"},
|
|
17
|
+
"crontab-helper": {"module": "evolver_tools.vendor.crontab_helper", "func": "main", "desc": "Simplify crontab management"},
|
|
18
|
+
"cert-check": {"module": "evolver_tools.vendor.cert_check", "func": "main", "desc": "Check SSL certificate expiry"},
|
|
19
|
+
"checksum-dir": {"module": "evolver_tools.vendor.checksum_dir", "func": "main", "desc": "Generate/verify directory checksums"},
|
|
20
|
+
"b64": {"module": "evolver_tools.vendor.b64", "func": "main", "desc": "b64"},
|
|
21
|
+
"cal": {"module": "evolver_tools.vendor.cal_tool.cli", "func": "main", "desc": "Cal"},
|
|
22
|
+
"chart-cli": {"module": "evolver_tools.vendor.chart_cli", "func": "main", "desc": "Chart CLI"},
|
|
23
|
+
"colors": {"module": "evolver_tools.vendor.colors", "func": "main", "desc": "Colors"},
|
|
24
|
+
"cron": {"module": "evolver_tools.vendor.cron", "func": "main", "desc": "Cron expression parser"},
|
|
25
|
+
"csv-stats": {"module": "evolver_tools.vendor.csv_stats.cli", "func": "main", "desc": "csv-stats"},
|
|
26
|
+
"diff": {"module": "evolver_tools.vendor.diff_tool", "func": "main", "desc": "File comparator"},
|
|
27
|
+
"dirsize": {"module": "evolver_tools.vendor.dirsize", "func": "entry", "desc": "Dirsize"},
|
|
28
|
+
"dt": {"module": "evolver_tools.vendor.dt_convert", "func": "main", "desc": "Dt"},
|
|
29
|
+
"ff": {"module": "evolver_tools.vendor.ff", "func": "main", "desc": "Fuzzy Finder"},
|
|
30
|
+
"envcheck": {"module": "evolver_tools.vendor.envcheck", "func": "main", "desc": "Envcheck"},
|
|
31
|
+
"find-dups": {"module": "evolver_tools.vendor.find_dups.cli", "func": "main", "desc": "Find Dups"},
|
|
32
|
+
"hashsum": {"module": "evolver_tools.vendor.hashsum", "func": "main", "desc": "Hashsum"},
|
|
33
|
+
"http-live": {"module": "evolver_tools.vendor.http_live", "func": "main", "desc": "HTTP Live Server"},
|
|
34
|
+
"ipcalc": {"module": "evolver_tools.vendor.ipcalc", "func": "main", "desc": "IP/CIDR calculator"},
|
|
35
|
+
"ipinfo": {"module": "evolver_tools.vendor.ipinfo", "func": "main", "desc": "Ipinfo"},
|
|
36
|
+
"jq-lite": {"module": "evolver_tools.vendor.jq_lite", "func": "main", "desc": "Jq Lite"},
|
|
37
|
+
"json2csv": {"module": "evolver_tools.vendor.json2csv", "func": "main", "desc": "Json2Csv"},
|
|
38
|
+
"jsonql": {"module": "evolver_tools.vendor.jsonql", "func": "main", "desc": "JSONQL"},
|
|
39
|
+
"license-cli": {"module": "evolver_tools.vendor.license_cli.cli", "func": "main", "desc": "License CLI"},
|
|
40
|
+
"markdown-check": {"module": "evolver_tools.vendor.markdown_check", "func": "main", "desc": "Markdown Check"},
|
|
41
|
+
"nb": {"module": "evolver_tools.vendor.nb", "func": "main", "desc": "nb"},
|
|
42
|
+
"passgen": {"module": "evolver_tools.vendor.passgen", "func": "entry", "desc": "Passgen"},
|
|
43
|
+
"portcheck": {"module": "evolver_tools.vendor.portcheck.__main__", "func": "main", "desc": "Portcheck"},
|
|
44
|
+
"project-doctor": {"module": "evolver_tools.vendor.project_doctor", "func": "main", "desc": "Project Doctor"},
|
|
45
|
+
"ren": {"module": "evolver_tools.vendor.ren", "func": "main", "desc": "Ren"},
|
|
46
|
+
"siege-lite": {"module": "evolver_tools.vendor.siege_lite", "func": "main", "desc": "Siege Lite"},
|
|
47
|
+
"smellfinder": {"module": "evolver_tools.vendor.smellfinder", "func": "main", "desc": "Smellfinder"},
|
|
48
|
+
"sqlite-cli": {"module": "evolver_tools.vendor.sqlite_cli", "func": "main", "desc": "Sqlite CLI"},
|
|
49
|
+
"sysmon": {"module": "evolver_tools.vendor.sysmon", "func": "entry", "desc": "Sysmon"},
|
|
50
|
+
"timer": {"module": "evolver_tools.vendor.timer", "func": "entry", "desc": "Timer"},
|
|
51
|
+
"treedir": {"module": "evolver_tools.vendor.treedir.__main__", "func": "main", "desc": "Treedir"},
|
|
52
|
+
"urlparse": {"module": "evolver_tools.vendor.urlparse_tool.cli", "func": "main", "desc": "URL Parse"},
|
|
53
|
+
"uuid": {"module": "evolver_tools.vendor.uuid_tool", "func": "main", "desc": "UUID generator"},
|
|
54
|
+
"web-summary": {"module": "evolver_tools.vendor.web_summary", "func": "main", "desc": "Web Summary"},
|
|
55
|
+
"wordcount": {"module": "evolver_tools.vendor.wordcount.__main__", "func": "main", "desc": "Wordcount"},
|
|
56
|
+
"fmt": {"module": "evolver_tools.vendor.fmt", "func": "main", "desc": "Code/text formatter"},
|
|
57
|
+
"yaml2json": {"module": "evolver_tools.vendor.yaml2json", "func": "main", "desc": "YAML → JSON converter"},
|
|
58
|
+
"sort": {"module": "evolver_tools.vendor.sort", "func": "main", "desc": "Line sorting (alpha, numeric, unique, by column)"},
|
|
59
|
+
"pr-tool": {"module": "evolver_tools.vendor.pr_tool", "func": "main", "desc": "GitHub PR helper (create, list, review, checkout)"},
|
|
60
|
+
"clipboard": {"module": "evolver_tools.vendor.clipboard", "func": "main", "desc": "Terminal clipboard copy/paste/clear"},
|
|
61
|
+
"uniq": {"module": "evolver_tools.vendor.uniq_tool", "func": "main", "desc": "Unique line filter with count & case-insensitive"},
|
|
62
|
+
"changelog-gen": {"module": "evolver_tools.vendor.changelog_gen", "func": "main", "desc": "Generate changelog from git log"},
|
|
63
|
+
"timer-pro": {"module": "evolver_tools.vendor.timer_pro", "func": "main", "desc": "Countdown, stopwatch, alarms, lap timer"},
|
|
64
|
+
"banner-gen": {"module": "evolver_tools.vendor.banner", "func": "main", "desc": "ASCII banner generator (4 styles, colors)"},
|
|
65
|
+
"shuffle": {"module": "evolver_tools.vendor.shuffle", "func": "main", "desc": "Randomize lines from stdin"},
|
|
66
|
+
"split": {"module": "evolver_tools.vendor.split_tool", "func": "main", "desc": "File splitter and joiner (by lines or size)"},
|
|
67
|
+
"join": {"module": "evolver_tools.vendor.join", "func": "main", "desc": "Join lines with delimiter"},
|
|
68
|
+
"weather-cli": {"module": "evolver_tools.vendor.weather_cli", "func": "main", "desc": "Weather forecast from wttr.in"},
|
|
69
|
+
"progress-bar": {"module": "evolver_tools.vendor.progress_bar", "func": "main", "desc": "Animated terminal progress bar"},
|
|
70
|
+
"json-pretty": {"module": "evolver_tools.vendor.json_pretty", "func": "main", "desc": "JSON pretty-printer, validator, minifier"},
|
|
71
|
+
"ini-parser": {"module": "evolver_tools.vendor.ini_parser", "func": "main", "desc": "INI file parser, query, and JSON converter"},
|
|
72
|
+
"disk-usage": {"module": "evolver_tools.vendor.disk_usage", "func": "main", "desc": "Disk usage analyzer (largest dirs/files)"},
|
|
73
|
+
"quote": {"module": "evolver_tools.vendor.quote_tool", "func": "main", "desc": "Random quote generator (100+ in 5 categories)"},
|
|
74
|
+
"xml2json": {"module": "evolver_tools.vendor.xml2json", "func": "main", "desc": "Convert XML to JSON"},
|
|
75
|
+
"backup": {"module": "evolver_tools.vendor.backup", "func": "main", "desc": "File/dir backup with rotation"},
|
|
76
|
+
"net-speed": {"module": "evolver_tools.vendor.net_speed", "func": "main", "desc": "Internet download speed test"},
|
|
77
|
+
"ascii-gen": {"module": "evolver_tools.vendor.ascii_gen", "func": "main", "desc": "ASCII art generator (8 styles)"},
|
|
78
|
+
"stopwatch": {"module": "evolver_tools.vendor.stopwatch", "func": "main", "desc": "Terminal stopwatch with lap support"},
|
|
79
|
+
"qrcode": {"module": "evolver_tools.vendor.qrcode", "func": "main", "desc": "QR code generator (ASCII art)"},
|
|
80
|
+
"restore": {"module": "evolver_tools.vendor.restore", "func": "main", "desc": "Restore files from .bak backups"},
|
|
81
|
+
"reminder": {"module": "evolver_tools.vendor.reminder", "func": "main", "desc": "Timer-based reminder with countdown"},
|
|
82
|
+
"todo-cli": {"module": "evolver_tools.vendor.todo_cli", "func": "main", "desc": "Simple prioritized TODO list manager"},
|
|
83
|
+
"log-tail": {"module": "evolver_tools.vendor.log_tail", "func": "main", "desc": "Tail logs with follow, filter, colorize"},
|
|
84
|
+
"spinner": {"module": "evolver_tools.vendor.spinner", "func": "main", "desc": "Animated terminal spinner (6 styles)"},
|
|
85
|
+
"joke": {"module": "evolver_tools.vendor.joke", "func": "main", "desc": "Random programming/tech/dad jokes"},
|
|
86
|
+
"morse": {"module": "evolver_tools.vendor.morse", "func": "main", "desc": "Text-Morse code converter with audio"},
|
|
87
|
+
"password-strength": {"module": "evolver_tools.vendor.password_strength", "func": "main", "desc": "Password strength checker (0-100)"},
|
|
88
|
+
"html2markdown": {"module": "evolver_tools.vendor.html2markdown", "func": "main", "desc": "Convert HTML to Markdown"},
|
|
89
|
+
"rainbow": {"module": "evolver_tools.vendor.rainbow", "func": "main", "desc": "Rainbow-colored text output"},
|
|
90
|
+
"figlet-cli": {"module": "evolver_tools.vendor.figlet_cli", "func": "main", "desc": "ASCII art font display (5 fonts)"},
|
|
91
|
+
"file-encrypt": {"module": "evolver_tools.vendor.file_encrypt", "func": "main", "desc": "Simple file encrypt/decrypt"},
|
|
92
|
+
"otp-gen": {"module": "evolver_tools.vendor.otp_gen", "func": "main", "desc": "TOTP/HOTP one-time password generator"},
|
|
93
|
+
"ssl-check": {"module": "evolver_tools.vendor.ssl_check", "func": "main", "desc": "SSL/TLS certificate checker"},
|
|
94
|
+
"scan-ports": {"module": "evolver_tools.vendor.scan_ports", "func": "main", "desc": "TCP port scanner (range, common ports)"},
|
|
95
|
+
"note-taker": {"module": "evolver_tools.vendor.note_taker", "func": "main", "desc": "CLI note-taking (add, list, search)"},
|
|
96
|
+
"bookmark": {"module": "evolver_tools.vendor.bookmark", "func": "main", "desc": "CLI bookmark manager"},
|
|
97
|
+
"dep-graph": {"module": "evolver_tools.vendor.dep_graph", "func": "main", "desc": "Dependency graph from Python files"},
|
|
98
|
+
"image-meta": {"module": "evolver_tools.vendor.image_meta", "func": "main", "desc": "Image metadata (EXIF) viewer"},
|
|
99
|
+
"agent-b": {"module": "evolver_tools.vendor.agent_b_tool", "func": "main", "desc": "Agent B tool"},
|
|
100
|
+
"api-tester": {"module": "evolver_tools.vendor.api_tester", "func": "main", "desc": "HTTP API testing tool"},
|
|
101
|
+
"audit-log": {"module": "evolver_tools.vendor.audit_log", "func": "main", "desc": "Parse and filter system audit logs"},
|
|
102
|
+
"config-validator": {"module": "evolver_tools.vendor.config_validator", "func": "main", "desc": "Validate JSON/YAML/TOML config files"},
|
|
103
|
+
"db-schema": {"module": "evolver_tools.vendor.db_schema", "func": "main", "desc": "Display database schema as ASCII"},
|
|
104
|
+
"firewall-rule": {"module": "evolver_tools.vendor.firewall_rule", "func": "main", "desc": "iptables/nftables helper tool"},
|
|
105
|
+
"log-analyzer": {"module": "evolver_tools.vendor.log_analyzer", "func": "main", "desc": "Log file analyzer with stats"},
|
|
106
|
+
"ssh-key-gen": {"module": "evolver_tools.vendor.ssh_key_gen", "func": "main", "desc": "Generate SSH key pairs"},
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
def list_tools():
|
|
110
|
+
"""Display all available tools."""
|
|
111
|
+
print('\x1b[1;36m===== EVOLVER Tools v2.5.0 =====\x1b[0m')
|
|
112
|
+
print()
|
|
113
|
+
for name, info in sorted(TOOLS.items()):
|
|
114
|
+
print(f' \033[1;33m{name:<18}\033[0m {info["desc"]}')
|
|
115
|
+
print()
|
|
116
|
+
print(f' Total: {len(TOOLS)} tools')
|
|
117
|
+
print()
|
|
118
|
+
print('Usage: evolver <toolname> [args...]')
|
|
119
|
+
print(' evolver list')
|
|
120
|
+
|
|
121
|
+
def run_tool(tool_name, args):
|
|
122
|
+
if tool_name not in TOOLS:
|
|
123
|
+
print(f'Unknown tool: {tool_name}')
|
|
124
|
+
sys.exit(1)
|
|
125
|
+
info = TOOLS[tool_name]
|
|
126
|
+
mod_path = info["module"]
|
|
127
|
+
func_name = info["func"]
|
|
128
|
+
old_argv = sys.argv
|
|
129
|
+
sys.argv = [tool_name] + args
|
|
130
|
+
try:
|
|
131
|
+
mod = importlib.import_module(mod_path)
|
|
132
|
+
func = getattr(mod, func_name)
|
|
133
|
+
result = func()
|
|
134
|
+
if result is not None:
|
|
135
|
+
print(result)
|
|
136
|
+
except KeyboardInterrupt:
|
|
137
|
+
pass
|
|
138
|
+
except Exception as e:
|
|
139
|
+
print(f'Error running {tool_name}: {e}', file=sys.stderr)
|
|
140
|
+
sys.exit(1)
|
|
141
|
+
finally:
|
|
142
|
+
sys.argv = old_argv
|
|
143
|
+
|
|
144
|
+
def main():
|
|
145
|
+
if len(sys.argv) < 2 or sys.argv[1] in ("-h", "--help"):
|
|
146
|
+
list_tools()
|
|
147
|
+
return
|
|
148
|
+
tool_name = sys.argv[1]
|
|
149
|
+
args = sys.argv[2:]
|
|
150
|
+
if tool_name == "list":
|
|
151
|
+
list_tools()
|
|
152
|
+
return
|
|
153
|
+
run_tool(tool_name, args)
|
|
154
|
+
|
|
155
|
+
if __name__ == "__main__":
|
|
156
|
+
main()
|