just-cli 0.2.1__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.
Files changed (104) hide show
  1. just_cli-0.2.1/.github/workflows/publish.yml +37 -0
  2. just_cli-0.2.1/.gitignore +22 -0
  3. just_cli-0.2.1/PKG-INFO +208 -0
  4. just_cli-0.2.1/README.md +192 -0
  5. just_cli-0.2.1/docs/extension_guide.md +301 -0
  6. just_cli-0.2.1/docs/images/editor_demo.png +0 -0
  7. just_cli-0.2.1/docs/images/viewer_demo.png +0 -0
  8. just_cli-0.2.1/pyproject.toml +29 -0
  9. just_cli-0.2.1/scripts/system/linux/proxy/proxy.sh +137 -0
  10. just_cli-0.2.1/scripts/system/windows/proxy/proxy.bat +56 -0
  11. just_cli-0.2.1/scripts/system/windows/proxy/proxy.ps1 +58 -0
  12. just_cli-0.2.1/src/just/__init__.py +40 -0
  13. just_cli-0.2.1/src/just/cli.py +106 -0
  14. just_cli-0.2.1/src/just/commands/__init__.py +0 -0
  15. just_cli-0.2.1/src/just/commands/download.py +67 -0
  16. just_cli-0.2.1/src/just/commands/edit.py +37 -0
  17. just_cli-0.2.1/src/just/commands/ext/__init__.py +24 -0
  18. just_cli-0.2.1/src/just/commands/ext/add.py +102 -0
  19. just_cli-0.2.1/src/just/commands/ext/edit.py +67 -0
  20. just_cli-0.2.1/src/just/commands/ext/list.py +155 -0
  21. just_cli-0.2.1/src/just/commands/ext/remove.py +131 -0
  22. just_cli-0.2.1/src/just/commands/extract.py +76 -0
  23. just_cli-0.2.1/src/just/commands/install.py +79 -0
  24. just_cli-0.2.1/src/just/commands/linux.py +213 -0
  25. just_cli-0.2.1/src/just/commands/tunnel.py +27 -0
  26. just_cli-0.2.1/src/just/commands/view.py +33 -0
  27. just_cli-0.2.1/src/just/core/__init__.py +0 -0
  28. just_cli-0.2.1/src/just/core/config/__init__.py +34 -0
  29. just_cli-0.2.1/src/just/core/config/config.py +7 -0
  30. just_cli-0.2.1/src/just/core/config/utils.py +94 -0
  31. just_cli-0.2.1/src/just/core/extension/__init__.py +0 -0
  32. just_cli-0.2.1/src/just/core/extension/generator.py +614 -0
  33. just_cli-0.2.1/src/just/core/extension/parser.py +420 -0
  34. just_cli-0.2.1/src/just/core/extension/utils.py +145 -0
  35. just_cli-0.2.1/src/just/core/extension/validator.py +118 -0
  36. just_cli-0.2.1/src/just/core/installer/__init__.py +10 -0
  37. just_cli-0.2.1/src/just/core/installer/binary.py +148 -0
  38. just_cli-0.2.1/src/just/core/installer/decorator.py +15 -0
  39. just_cli-0.2.1/src/just/core/installer/install_package.py +122 -0
  40. just_cli-0.2.1/src/just/core/installer/package_info.py +12 -0
  41. just_cli-0.2.1/src/just/core/installer/simple_release.py +296 -0
  42. just_cli-0.2.1/src/just/core/installer/source/__init__.py +17 -0
  43. just_cli-0.2.1/src/just/core/installer/source/base.py +22 -0
  44. just_cli-0.2.1/src/just/core/installer/source/http.py +103 -0
  45. just_cli-0.2.1/src/just/core/installer/source/local.py +54 -0
  46. just_cli-0.2.1/src/just/core/system_probe/__init__.py +15 -0
  47. just_cli-0.2.1/src/just/core/system_probe/system_info.py +101 -0
  48. just_cli-0.2.1/src/just/core/system_probe/system_probe.py +198 -0
  49. just_cli-0.2.1/src/just/installers/__init__.py +0 -0
  50. just_cli-0.2.1/src/just/installers/claude-code/__init__.py +0 -0
  51. just_cli-0.2.1/src/just/installers/claude-code/installer.py +21 -0
  52. just_cli-0.2.1/src/just/installers/cloudflare/__init__.py +1 -0
  53. just_cli-0.2.1/src/just/installers/cloudflare/installer.py +16 -0
  54. just_cli-0.2.1/src/just/installers/docker/__init__.py +0 -0
  55. just_cli-0.2.1/src/just/installers/docker/installer.py +16 -0
  56. just_cli-0.2.1/src/just/installers/edit/__init__.py +0 -0
  57. just_cli-0.2.1/src/just/installers/edit/installer.py +23 -0
  58. just_cli-0.2.1/src/just/installers/mssh/__init__.py +0 -0
  59. just_cli-0.2.1/src/just/installers/mssh/installer.py +14 -0
  60. just_cli-0.2.1/src/just/installers/nvm/__init__.py +0 -0
  61. just_cli-0.2.1/src/just/installers/nvm/installer.py +31 -0
  62. just_cli-0.2.1/src/just/installers/qodercli/__init__.py +0 -0
  63. just_cli-0.2.1/src/just/installers/qodercli/installer.py +14 -0
  64. just_cli-0.2.1/src/just/installers/tailscale/__init__.py +0 -0
  65. just_cli-0.2.1/src/just/installers/tailscale/installer.py +15 -0
  66. just_cli-0.2.1/src/just/tui/__init__.py +4 -0
  67. just_cli-0.2.1/src/just/tui/editor.py +111 -0
  68. just_cli-0.2.1/src/just/tui/extension.py +658 -0
  69. just_cli-0.2.1/src/just/tui/markdown.py +70 -0
  70. just_cli-0.2.1/src/just/utils/__init__.py +37 -0
  71. just_cli-0.2.1/src/just/utils/archive/__init__.py +22 -0
  72. just_cli-0.2.1/src/just/utils/archive/compression_handler.py +178 -0
  73. just_cli-0.2.1/src/just/utils/archive/extractor.py +87 -0
  74. just_cli-0.2.1/src/just/utils/archive/format_detect.py +199 -0
  75. just_cli-0.2.1/src/just/utils/archive/sevenzip_handler.py +44 -0
  76. just_cli-0.2.1/src/just/utils/archive/tar_handler.py +117 -0
  77. just_cli-0.2.1/src/just/utils/archive/zip_handler.py +81 -0
  78. just_cli-0.2.1/src/just/utils/download_utils.py +552 -0
  79. just_cli-0.2.1/src/just/utils/echo_utils.py +69 -0
  80. just_cli-0.2.1/src/just/utils/env_utils.py +164 -0
  81. just_cli-0.2.1/src/just/utils/file_utils.py +184 -0
  82. just_cli-0.2.1/src/just/utils/format_utils.py +9 -0
  83. just_cli-0.2.1/src/just/utils/progress.py +457 -0
  84. just_cli-0.2.1/src/just/utils/shell_utils.py +72 -0
  85. just_cli-0.2.1/src/just/utils/system_probe.py +214 -0
  86. just_cli-0.2.1/src/just/utils/typer_utils.py +62 -0
  87. just_cli-0.2.1/src/just/utils/user_interaction.py +25 -0
  88. just_cli-0.2.1/tests/Dockerfile +23 -0
  89. just_cli-0.2.1/tests/requirements.txt +12 -0
  90. just_cli-0.2.1/tests/run_tests.py +230 -0
  91. just_cli-0.2.1/tests/test_archive_extraction.py +345 -0
  92. just_cli-0.2.1/tests/test_download.py +131 -0
  93. just_cli-0.2.1/tests/test_extension/README.md +20 -0
  94. just_cli-0.2.1/tests/test_extension/test_ext.py +36 -0
  95. just_cli-0.2.1/tests/test_extension/test_extension_add.py +0 -0
  96. just_cli-0.2.1/tests/test_extension.py +162 -0
  97. just_cli-0.2.1/tests/test_file_utils.py +369 -0
  98. just_cli-0.2.1/tests/test_init.py +175 -0
  99. just_cli-0.2.1/tests/test_installer.py +166 -0
  100. just_cli-0.2.1/tests/test_linux_commands.py +296 -0
  101. just_cli-0.2.1/tests/test_progress_utils.py +134 -0
  102. just_cli-0.2.1/tests/test_system_probe.py +123 -0
  103. just_cli-0.2.1/tests/testing.py +422 -0
  104. just_cli-0.2.1/uv.lock +798 -0
@@ -0,0 +1,37 @@
1
+ name: Publish to PyPI
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - "v*"
7
+
8
+ permissions:
9
+ contents: read
10
+
11
+ jobs:
12
+ build-and-publish:
13
+ name: Build and publish
14
+ runs-on: ubuntu-latest
15
+ permissions:
16
+ id-token: write
17
+ contents: read
18
+
19
+ steps:
20
+ - name: Checkout code
21
+ uses: actions/checkout@v4
22
+
23
+ - name: Set up Python
24
+ uses: actions/setup-python@v5
25
+ with:
26
+ python-version: "3.10"
27
+
28
+ - name: Install build tools
29
+ run: |
30
+ python -m pip install --upgrade pip
31
+ pip install build
32
+
33
+ - name: Build package
34
+ run: python -m build
35
+
36
+ - name: Publish to PyPI
37
+ uses: pypa/gh-action-pypi-publish@release/v1
@@ -0,0 +1,22 @@
1
+ # Python-generated files
2
+ __pycache__/
3
+ *.py[oc]
4
+ build/
5
+ dist/
6
+ wheels/
7
+ *.egg-info
8
+
9
+ # Virtual environments
10
+ .venv
11
+
12
+ # IDE-specific files
13
+ .vscode
14
+ .idea
15
+ .claude
16
+ .qoder
17
+
18
+ # Environment configuration
19
+ .env
20
+ workspace/
21
+ extensions/
22
+ CLAUDE.md
@@ -0,0 +1,208 @@
1
+ Metadata-Version: 2.4
2
+ Name: just-cli
3
+ Version: 0.2.1
4
+ Summary: Your all-in-one CLI Toolkit
5
+ Author-email: zzzcb <zjxs.zzzcb@gmail.com>
6
+ Requires-Python: >=3.10
7
+ Requires-Dist: httpx
8
+ Requires-Dist: prompt-toolkit>=3.0.0
9
+ Requires-Dist: py7zr
10
+ Requires-Dist: python-dotenv
11
+ Requires-Dist: rich>=14.2.0
12
+ Requires-Dist: textual>=6.4.0
13
+ Requires-Dist: typer>=0.20.0
14
+ Requires-Dist: zstandard
15
+ Description-Content-Type: text/markdown
16
+
17
+ # ๐Ÿ› ๏ธ JUST CLI
18
+
19
+ ## The simple stuff should be simple.
20
+
21
+ Sick of Googling *"how to install X on XXX"* for the 47th time, only to end up copying and pasting similar commands from various official docs?
22
+
23
+ Tired of copy-pasting giant commands and tapping arrow keys forever just to change one little thing?
24
+
25
+ Just want an all-in-one toolkit for everyday simple tasks, instead of endlessly searching and testing Deep Research results one by one?
26
+
27
+ **Just** is built to end the hassle. It focuses purely on making the simple, everyday developer tasks *actually simple*.
28
+
29
+
30
+ ## Installation
31
+
32
+ ```shell
33
+ pip install just-cli
34
+ ```
35
+
36
+ ## ๐Ÿ˜‹ The Good Stuff
37
+
38
+ ### The Toolkit ๐Ÿงฐ
39
+
40
+ A collection of essential tools that work exactly how you expect them to.
41
+
42
+ #### ๐Ÿ“ฅ Easy Download
43
+ Just download files like `wget` or `curl`, but with smart naming, auto-resume, and a beautiful progress bar by default.
44
+
45
+ ```bash
46
+ # Auto-resume is on by default. The filename is automatically extracted from the URL.
47
+ just download https://example.com/big-file.zip
48
+
49
+ # Use -H for custom headers and -o to specify a custom output filename.
50
+ just download https://api.example.com/data -H "Authorization: Bearer token" -o data.json
51
+ ```
52
+
53
+ #### ๐Ÿ“ฆ Universal Extract
54
+ Just extract the archive. It intelligently detects the compression format (via magic bytes) and handles everything.
55
+ * **Supported**: ZIP, TAR, GZ, BZ2, XZ, ZSTD, 7Z.
56
+ * **Note**: RAR is **not** supported.
57
+
58
+ ```bash
59
+ # Extracts to a folder named after the archive by default
60
+ just extract archive.tar.gz
61
+
62
+ # Specify a custom output directory
63
+ just extract data.7z -o ./output_dir
64
+ ```
65
+
66
+ #### ๐Ÿ“ Text Editor
67
+ Just edit files with a simple TUI editor.
68
+
69
+ ```bash
70
+ just edit README.md
71
+ ```
72
+
73
+ ![Editor Screenshot](docs/images/editor_demo.png)
74
+
75
+ #### ๐Ÿ“– Smart Viewer
76
+ Just view files with intelligent rendering. Currently supports Markdown with syntax highlighting and TOC.
77
+ *Based on the excellent [Textual Markdown example](https://github.com/Textualize/textual).*
78
+
79
+ ```bash
80
+ just view README.md
81
+ ```
82
+
83
+ ![Viewer Screenshot](docs/images/viewer_demo.png)
84
+
85
+ #### ๐ŸŒ Cloudflare Tunnel
86
+ Just expose your local server to the internet.
87
+
88
+ ```bash
89
+ # Powered by Cloudflare Tunnel (cloudflared)
90
+ just tunnel http://localhost:8000
91
+ ```
92
+
93
+ #### ๐Ÿง Common Linux File Operations
94
+ Just some common file operations implemented in Python, for those tired of remembering command differences between Linux and Windows.
95
+
96
+ ```bash
97
+ just cat
98
+ just ls
99
+ just cp
100
+ just mv
101
+ just rm
102
+ just mkdir
103
+ ```
104
+
105
+ ### The Extension System ๐Ÿงฉ
106
+
107
+ #### Create a CLI tool with Just Extension in just 2 steps
108
+
109
+ The core idea is simple: **String Replacement**. You take a long, complex command, mark the parts you want to change, and `just` generates a CLI for it.
110
+
111
+ Here is an example:
112
+
113
+ 1. **Register the complex command**:
114
+ Tell `just` what command you want to alias.
115
+ ```bash
116
+ just ext add docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' f523e75ca4ef
117
+ ```
118
+
119
+ 2. **Design your command**:
120
+ Design a command structure that is easy for you to remember by marking dynamic parts using the syntax `[<name>:<type>=<default>#<help>]`.
121
+ ```text
122
+ # Replace the static container ID with a dynamic argument
123
+ Enter extension commands: just docker ip f523e75ca4ef[container_id:str#The Container ID]
124
+ ```
125
+
126
+ **That's it!** Now you can use your new command:
127
+ ```bash
128
+ just docker ip <container_id>
129
+ ```
130
+
131
+ #### โœจ How it works
132
+
133
+ When you run the command above, `just` compiles a native Python script using **typer**.
134
+
135
+ 1. **Parsing**: The syntax `f523e75ca4ef[container_id:str#The Container ID]` tells `just` to:
136
+ * Identify `f523e75ca4ef` as the **target string** to replace.
137
+ * Create a variable `container_id` of type `str`.
138
+ * Use "The Container ID" as the help message.
139
+
140
+ 2. **Code Generation**: It generates a Python function with a type-safe signature:
141
+ ```python
142
+ def main(container_id: Annotated[str, typer.Argument(help="The Container ID")]):
143
+ # The original command template
144
+ command = "docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' f523e75ca4ef"
145
+
146
+ # String Replacement Logic
147
+ command = command.replace('f523e75ca4ef', str(container_id))
148
+
149
+ # Execution
150
+ subprocess.run(shlex.split(command))
151
+ ```
152
+
153
+ 3. **Result**: You get a fully functional CLI with auto-completion, type validation, and help messagesโ€”all powered by the simple act of string replacement.
154
+
155
+
156
+ ### The Installer ๐Ÿ’ฟ
157
+
158
+ #### Automate the "Official Docs" with minimal code.
159
+
160
+ `just` allows you to run any command from the official docs using `just.execute_commands`. It simply automates your manual steps.
161
+
162
+ To help you make decisions, `just` provides system probing tools:
163
+ * `just.system.platform`: `linux`, `windows`, `darwin`
164
+ * `just.system.arch`: `x86_64`, `aarch64`
165
+ * `just.system.pms`: Detects `winget`, `brew`, `apt`, etc.
166
+
167
+ We also provide two specialized helpers for common scenarios:
168
+ * **`just.BinaryInstaller`**: Best for single-file binaries (handles download, chmod, path).
169
+ * **`just.SimpleReleaseInstaller`**: Best for archives (handles download, extraction, linking).
170
+
171
+ #### Example: Installing Cloudflared
172
+
173
+ Here is a complete example that mimics the official installation logic:
174
+
175
+ ```python
176
+ @just.installer(check="cloudflared --version")
177
+ def install_cloudflare():
178
+ """Install Cloudflare Tunnel client."""
179
+
180
+ # Use standard package managers if available
181
+ if just.system.pms.winget.is_available():
182
+ just.execute_commands("winget install --id Cloudflare.cloudflared")
183
+
184
+ elif just.system.pms.brew.is_available():
185
+ just.execute_commands("brew install cloudflared")
186
+
187
+ # Use BinaryInstaller
188
+ elif just.system.platform == 'linux':
189
+ # This helper automates: curl -> chmod +x -> symlink to bin
190
+ just.BinaryInstaller(
191
+ url='https://github.com/cloudflare/cloudflared/releases/.../cloudflared-linux-amd64',
192
+ alias='cloudflared'
193
+ ).run()
194
+
195
+ else:
196
+ raise NotImplementedError
197
+ ```
198
+
199
+
200
+ ## ๐Ÿค Contributing
201
+
202
+ Found a bug? Want to add a new installer?
203
+ Fork it, fix it, ship it. We love PRs.
204
+ Just keep it cool, keep it simple, and don't break the "just works" vibe.
205
+
206
+ ## ๐Ÿ“„ License
207
+
208
+ MIT. Go wild.
@@ -0,0 +1,192 @@
1
+ # ๐Ÿ› ๏ธ JUST CLI
2
+
3
+ ## The simple stuff should be simple.
4
+
5
+ Sick of Googling *"how to install X on XXX"* for the 47th time, only to end up copying and pasting similar commands from various official docs?
6
+
7
+ Tired of copy-pasting giant commands and tapping arrow keys forever just to change one little thing?
8
+
9
+ Just want an all-in-one toolkit for everyday simple tasks, instead of endlessly searching and testing Deep Research results one by one?
10
+
11
+ **Just** is built to end the hassle. It focuses purely on making the simple, everyday developer tasks *actually simple*.
12
+
13
+
14
+ ## Installation
15
+
16
+ ```shell
17
+ pip install just-cli
18
+ ```
19
+
20
+ ## ๐Ÿ˜‹ The Good Stuff
21
+
22
+ ### The Toolkit ๐Ÿงฐ
23
+
24
+ A collection of essential tools that work exactly how you expect them to.
25
+
26
+ #### ๐Ÿ“ฅ Easy Download
27
+ Just download files like `wget` or `curl`, but with smart naming, auto-resume, and a beautiful progress bar by default.
28
+
29
+ ```bash
30
+ # Auto-resume is on by default. The filename is automatically extracted from the URL.
31
+ just download https://example.com/big-file.zip
32
+
33
+ # Use -H for custom headers and -o to specify a custom output filename.
34
+ just download https://api.example.com/data -H "Authorization: Bearer token" -o data.json
35
+ ```
36
+
37
+ #### ๐Ÿ“ฆ Universal Extract
38
+ Just extract the archive. It intelligently detects the compression format (via magic bytes) and handles everything.
39
+ * **Supported**: ZIP, TAR, GZ, BZ2, XZ, ZSTD, 7Z.
40
+ * **Note**: RAR is **not** supported.
41
+
42
+ ```bash
43
+ # Extracts to a folder named after the archive by default
44
+ just extract archive.tar.gz
45
+
46
+ # Specify a custom output directory
47
+ just extract data.7z -o ./output_dir
48
+ ```
49
+
50
+ #### ๐Ÿ“ Text Editor
51
+ Just edit files with a simple TUI editor.
52
+
53
+ ```bash
54
+ just edit README.md
55
+ ```
56
+
57
+ ![Editor Screenshot](docs/images/editor_demo.png)
58
+
59
+ #### ๐Ÿ“– Smart Viewer
60
+ Just view files with intelligent rendering. Currently supports Markdown with syntax highlighting and TOC.
61
+ *Based on the excellent [Textual Markdown example](https://github.com/Textualize/textual).*
62
+
63
+ ```bash
64
+ just view README.md
65
+ ```
66
+
67
+ ![Viewer Screenshot](docs/images/viewer_demo.png)
68
+
69
+ #### ๐ŸŒ Cloudflare Tunnel
70
+ Just expose your local server to the internet.
71
+
72
+ ```bash
73
+ # Powered by Cloudflare Tunnel (cloudflared)
74
+ just tunnel http://localhost:8000
75
+ ```
76
+
77
+ #### ๐Ÿง Common Linux File Operations
78
+ Just some common file operations implemented in Python, for those tired of remembering command differences between Linux and Windows.
79
+
80
+ ```bash
81
+ just cat
82
+ just ls
83
+ just cp
84
+ just mv
85
+ just rm
86
+ just mkdir
87
+ ```
88
+
89
+ ### The Extension System ๐Ÿงฉ
90
+
91
+ #### Create a CLI tool with Just Extension in just 2 steps
92
+
93
+ The core idea is simple: **String Replacement**. You take a long, complex command, mark the parts you want to change, and `just` generates a CLI for it.
94
+
95
+ Here is an example:
96
+
97
+ 1. **Register the complex command**:
98
+ Tell `just` what command you want to alias.
99
+ ```bash
100
+ just ext add docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' f523e75ca4ef
101
+ ```
102
+
103
+ 2. **Design your command**:
104
+ Design a command structure that is easy for you to remember by marking dynamic parts using the syntax `[<name>:<type>=<default>#<help>]`.
105
+ ```text
106
+ # Replace the static container ID with a dynamic argument
107
+ Enter extension commands: just docker ip f523e75ca4ef[container_id:str#The Container ID]
108
+ ```
109
+
110
+ **That's it!** Now you can use your new command:
111
+ ```bash
112
+ just docker ip <container_id>
113
+ ```
114
+
115
+ #### โœจ How it works
116
+
117
+ When you run the command above, `just` compiles a native Python script using **typer**.
118
+
119
+ 1. **Parsing**: The syntax `f523e75ca4ef[container_id:str#The Container ID]` tells `just` to:
120
+ * Identify `f523e75ca4ef` as the **target string** to replace.
121
+ * Create a variable `container_id` of type `str`.
122
+ * Use "The Container ID" as the help message.
123
+
124
+ 2. **Code Generation**: It generates a Python function with a type-safe signature:
125
+ ```python
126
+ def main(container_id: Annotated[str, typer.Argument(help="The Container ID")]):
127
+ # The original command template
128
+ command = "docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' f523e75ca4ef"
129
+
130
+ # String Replacement Logic
131
+ command = command.replace('f523e75ca4ef', str(container_id))
132
+
133
+ # Execution
134
+ subprocess.run(shlex.split(command))
135
+ ```
136
+
137
+ 3. **Result**: You get a fully functional CLI with auto-completion, type validation, and help messagesโ€”all powered by the simple act of string replacement.
138
+
139
+
140
+ ### The Installer ๐Ÿ’ฟ
141
+
142
+ #### Automate the "Official Docs" with minimal code.
143
+
144
+ `just` allows you to run any command from the official docs using `just.execute_commands`. It simply automates your manual steps.
145
+
146
+ To help you make decisions, `just` provides system probing tools:
147
+ * `just.system.platform`: `linux`, `windows`, `darwin`
148
+ * `just.system.arch`: `x86_64`, `aarch64`
149
+ * `just.system.pms`: Detects `winget`, `brew`, `apt`, etc.
150
+
151
+ We also provide two specialized helpers for common scenarios:
152
+ * **`just.BinaryInstaller`**: Best for single-file binaries (handles download, chmod, path).
153
+ * **`just.SimpleReleaseInstaller`**: Best for archives (handles download, extraction, linking).
154
+
155
+ #### Example: Installing Cloudflared
156
+
157
+ Here is a complete example that mimics the official installation logic:
158
+
159
+ ```python
160
+ @just.installer(check="cloudflared --version")
161
+ def install_cloudflare():
162
+ """Install Cloudflare Tunnel client."""
163
+
164
+ # Use standard package managers if available
165
+ if just.system.pms.winget.is_available():
166
+ just.execute_commands("winget install --id Cloudflare.cloudflared")
167
+
168
+ elif just.system.pms.brew.is_available():
169
+ just.execute_commands("brew install cloudflared")
170
+
171
+ # Use BinaryInstaller
172
+ elif just.system.platform == 'linux':
173
+ # This helper automates: curl -> chmod +x -> symlink to bin
174
+ just.BinaryInstaller(
175
+ url='https://github.com/cloudflare/cloudflared/releases/.../cloudflared-linux-amd64',
176
+ alias='cloudflared'
177
+ ).run()
178
+
179
+ else:
180
+ raise NotImplementedError
181
+ ```
182
+
183
+
184
+ ## ๐Ÿค Contributing
185
+
186
+ Found a bug? Want to add a new installer?
187
+ Fork it, fix it, ship it. We love PRs.
188
+ Just keep it cool, keep it simple, and don't break the "just works" vibe.
189
+
190
+ ## ๐Ÿ“„ License
191
+
192
+ MIT. Go wild.