vercel-cli 50.9.5__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 (115) hide show
  1. vercel_cli-50.9.5/.gitignore +5 -0
  2. vercel_cli-50.9.5/PKG-INFO +210 -0
  3. vercel_cli-50.9.5/README.md +180 -0
  4. vercel_cli-50.9.5/pyproject.toml +117 -0
  5. vercel_cli-50.9.5/vercel_cli/vendor/LICENSE +202 -0
  6. vercel_cli-50.9.5/vercel_cli/vendor/README.md +83 -0
  7. vercel_cli-50.9.5/vercel_cli/vendor/dist/VERCEL_DIR_README.txt +11 -0
  8. vercel_cli-50.9.5/vercel_cli/vendor/dist/builder-worker.cjs +62 -0
  9. vercel_cli-50.9.5/vercel_cli/vendor/dist/get-latest-worker.cjs +272 -0
  10. vercel_cli-50.9.5/vercel_cli/vendor/dist/index.js +197962 -0
  11. vercel_cli-50.9.5/vercel_cli/vendor/dist/vc.js +12 -0
  12. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/.package-lock.json +27 -0
  13. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/CHANGELOG.md +856 -0
  14. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/LICENSE +202 -0
  15. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/build.mjs +3 -0
  16. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/clone-env.d.ts +10 -0
  17. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/clone-env.js +43 -0
  18. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/debug.d.ts +1 -0
  19. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/debug.js +31 -0
  20. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/default-cache-path-glob.d.ts +1 -0
  21. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/default-cache-path-glob.js +28 -0
  22. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/edge-function.d.ts +41 -0
  23. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/edge-function.js +40 -0
  24. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/errors.d.ts +39 -0
  25. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/errors.js +95 -0
  26. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-blob.d.ts +24 -0
  27. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-blob.js +67 -0
  28. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-fs-ref.d.ts +27 -0
  29. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-fs-ref.js +113 -0
  30. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-ref.d.ts +38 -0
  31. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/file-ref.js +147 -0
  32. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/framework-helpers.d.ts +22 -0
  33. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/framework-helpers.js +96 -0
  34. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/download.d.ts +9 -0
  35. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/download.js +136 -0
  36. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/get-writable-directory.d.ts +1 -0
  37. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/get-writable-directory.js +32 -0
  38. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/glob.d.ts +10 -0
  39. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/glob.js +111 -0
  40. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/node-version.d.ts +13 -0
  41. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/node-version.js +222 -0
  42. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/normalize-path.d.ts +4 -0
  43. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/normalize-path.js +31 -0
  44. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/read-config-file.d.ts +7 -0
  45. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/read-config-file.js +87 -0
  46. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/rename.d.ts +11 -0
  47. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/rename.js +30 -0
  48. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/run-user-scripts.d.ts +230 -0
  49. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/run-user-scripts.js +1135 -0
  50. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/stream-to-buffer.d.ts +4 -0
  51. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/fs/stream-to-buffer.js +87 -0
  52. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/generate-node-builder-functions.d.ts +17 -0
  53. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/generate-node-builder-functions.js +198 -0
  54. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-ignore-filter.d.ts +1 -0
  55. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-ignore-filter.js +90 -0
  56. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-installed-package-version.d.ts +1 -0
  57. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-installed-package-version.js +53 -0
  58. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-platform-env.d.ts +5 -0
  59. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-platform-env.js +45 -0
  60. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-prefixed-env-vars.d.ts +14 -0
  61. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/get-prefixed-env-vars.js +54 -0
  62. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/hard-link-dir.d.ts +1 -0
  63. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/hard-link-dir.js +104 -0
  64. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/index.d.ts +36 -0
  65. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/index.js +26940 -0
  66. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/lambda.d.ts +138 -0
  67. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/lambda.js +339 -0
  68. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/nodejs-lambda.d.ts +16 -0
  69. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/nodejs-lambda.js +44 -0
  70. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/os.d.ts +3 -0
  71. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/os.js +62 -0
  72. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/prerender.d.ts +48 -0
  73. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/prerender.js +170 -0
  74. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/python.d.ts +22 -0
  75. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/python.js +85 -0
  76. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/schemas.d.ts +105 -0
  77. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/schemas.js +133 -0
  78. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/should-serve.d.ts +2 -0
  79. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/should-serve.js +47 -0
  80. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/constants.d.ts +2 -0
  81. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/constants.js +31 -0
  82. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/index.d.ts +3 -0
  83. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/index.js +33 -0
  84. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/trace.d.ts +37 -0
  85. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/trace/trace.js +92 -0
  86. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/types.d.ts +611 -0
  87. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/types.js +55 -0
  88. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/validate-npmrc.d.ts +12 -0
  89. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/dist/validate-npmrc.js +41 -0
  90. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/file-blob.js +1 -0
  91. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/file-fs-ref.js +1 -0
  92. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/file-ref.js +1 -0
  93. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/download.js +1 -0
  94. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/get-writable-directory.js +1 -0
  95. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/glob.js +1 -0
  96. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/rename.js +1 -0
  97. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/run-user-scripts.js +1 -0
  98. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/fs/stream-to-buffer.js +1 -0
  99. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/lambda.js +1 -0
  100. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/lib/python/ast_parser.py +72 -0
  101. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/lib/python/tests/test_ast_parser.py +72 -0
  102. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/build-utils/package.json +61 -0
  103. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/CHANGELOG.md +25 -0
  104. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/LICENSE +202 -0
  105. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/README.md +123 -0
  106. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/dist/index.d.ts +33 -0
  107. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/dist/index.js +93 -0
  108. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/detect-agent/package.json +59 -0
  109. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/LICENSE +202 -0
  110. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/dist/index.js +4730 -0
  111. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/package.json +43 -0
  112. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/vc_init.py +916 -0
  113. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/vc_init_dev_asgi.py +100 -0
  114. vercel_cli-50.9.5/vercel_cli/vendor/node_modules/@vercel/python/vc_init_dev_wsgi.py +123 -0
  115. vercel_cli-50.9.5/vercel_cli/vendor/package.json +42 -0
@@ -0,0 +1,5 @@
1
+ .DS_Store
2
+ *.pyc
3
+ .coverage
4
+ .venv
5
+ /dist/
@@ -0,0 +1,210 @@
1
+ Metadata-Version: 2.4
2
+ Name: vercel-cli
3
+ Version: 50.9.5
4
+ Summary: Vercel CLI packaged for Python (bundled Node.js, vendored npm)
5
+ Project-URL: Homepage, https://github.com/nuage-studio/vercel-cli-python
6
+ Project-URL: Repository, https://github.com/nuage-studio/vercel-cli-python
7
+ Project-URL: Issues, https://github.com/nuage-studio/vercel-cli-python/issues
8
+ Project-URL: Documentation, https://github.com/nuage-studio/vercel-cli-python#readme
9
+ Author: Nuage
10
+ Maintainer: Nuage
11
+ Keywords: cli,deployment,edge,functions,nodejs,npm,serverless,vercel,wrapper
12
+ Classifier: Development Status :: 5 - Production/Stable
13
+ Classifier: Environment :: Console
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: Operating System :: OS Independent
16
+ Classifier: Programming Language :: Python :: 3
17
+ Classifier: Programming Language :: Python :: 3 :: Only
18
+ Classifier: Programming Language :: Python :: 3.8
19
+ Classifier: Programming Language :: Python :: 3.9
20
+ Classifier: Programming Language :: Python :: 3.10
21
+ Classifier: Programming Language :: Python :: 3.11
22
+ Classifier: Programming Language :: Python :: 3.12
23
+ Classifier: Programming Language :: Python :: 3.13
24
+ Classifier: Topic :: Software Development :: Build Tools
25
+ Classifier: Topic :: System :: Systems Administration
26
+ Classifier: Topic :: Utilities
27
+ Requires-Python: >=3.8
28
+ Requires-Dist: nodejs-wheel-binaries==22.16.0
29
+ Description-Content-Type: text/markdown
30
+
31
+ # Python package wrapper for Vercel CLI
32
+
33
+ [![CI](https://github.com/nuage-studio/vercel-cli-python/actions/workflows/test.yml/badge.svg)](https://github.com/nuage-studio/vercel-cli-python/actions/workflows/test.yml)
34
+ [![codecov](https://codecov.io/gh/nuage-studio/vercel-cli-python/graph/badge.svg)](https://codecov.io/gh/nuage-studio/vercel-cli-python)
35
+ [![Supported Python Versions](https://img.shields.io/badge/python-3.8--3.13-blue.svg)](https://www.python.org/)
36
+
37
+ **vercel-cli** packages the npm `vercel` CLI for Python environments. It vendors the npm package under `vercel_cli/vendor/` and uses the bundled Node.js runtime provided by `nodejs-wheel-binaries`, so you can run `vercel` without installing Node.js.
38
+
39
+ It provides both a command-line interface and a Python API that other libraries can use programmatically instead of resorting to subprocess calls.
40
+
41
+ ## Quick start
42
+
43
+ - **Install**:
44
+
45
+ ```bash
46
+ pip install vercel-cli
47
+ ```
48
+
49
+ - **Use** (same arguments and behavior as the official npm CLI):
50
+
51
+ ```bash
52
+ vercel --version
53
+ vercel login
54
+ vercel deploy
55
+ ```
56
+
57
+ - **Use programmatically in Python** (for libraries that depend on this package):
58
+
59
+ ```python
60
+ from vercel_cli import run_vercel
61
+
62
+ # Deploy current directory
63
+ exit_code = run_vercel(["deploy"])
64
+
65
+ # Deploy specific directory with custom environment
66
+ exit_code = run_vercel(
67
+ ["deploy", "--prod"],
68
+ cwd="/path/to/project",
69
+ env={"VERCEL_TOKEN": "my-token"}
70
+ )
71
+
72
+ # Check version
73
+ exit_code = run_vercel(["--version"])
74
+ ```
75
+
76
+ ## What this provides
77
+
78
+ - **No system Node.js required**: The CLI runs via the Node binary from `nodejs-wheel-binaries` (currently Node 22.x).
79
+ - **Vendored npm package**: The `vercel` npm package (production deps only) is checked into `vercel_cli/vendor/`.
80
+ - **Console entrypoint**: The `vercel` command maps to `vercel_cli.run:main`, which executes `vercel_cli/vendor/dist/vc.js` with the bundled Node runtime.
81
+ - **Python API**: The `run_vercel()` function allows other Python libraries to use Vercel CLI programmatically without subprocess calls, with secure environment variable handling.
82
+
83
+ ## Requirements
84
+
85
+ - Python 3.8+
86
+ - macOS, Linux, or Windows supported by the Node wheels
87
+
88
+ ## How it works
89
+
90
+ At runtime, `vercel_cli.run` locates `vercel_cli/vendor/dist/vc.js` and launches it via the Node executable exposed by `nodejs_wheel_binaries`. CLI arguments are passed through unchanged, while environment variables are handled securely.
91
+
92
+ ## Programmatic usage
93
+
94
+ When using this package as a dependency in other Python libraries, you can call Vercel CLI commands directly without using subprocess:
95
+
96
+ ```python
97
+ from vercel_cli import run_vercel
98
+ import tempfile
99
+ import os
100
+
101
+ def deploy_my_app(source_dir: str, token: str) -> bool:
102
+ """Deploy an application to Vercel programmatically."""
103
+ with tempfile.TemporaryDirectory() as temp_dir:
104
+ # Copy your app to temp directory and modify as needed
105
+ # ...
106
+
107
+ # Deploy with custom environment
108
+ env = {
109
+ "VERCEL_TOKEN": token,
110
+ "NODE_ENV": "production"
111
+ }
112
+
113
+ exit_code = run_vercel(
114
+ ["deploy", "--prod", "--yes"],
115
+ cwd=temp_dir,
116
+ env=env
117
+ )
118
+
119
+ return exit_code == 0
120
+
121
+ # Usage
122
+ success = deploy_my_app("./my-app", "my-vercel-token")
123
+ ```
124
+
125
+ The `run_vercel()` function accepts:
126
+
127
+ - `args`: List of CLI arguments (same as command line)
128
+ - `cwd`: Working directory for the command
129
+ - `env`: Environment variables to set (passed directly to the Node.js runtime)
130
+
131
+ ## Security considerations
132
+
133
+ When using the `env` parameter, only explicitly provided environment variables are passed to the Vercel CLI. This prevents accidental leakage of sensitive environment variables from your Python process while still allowing you to set necessary variables like `VERCEL_TOKEN`.
134
+
135
+ Example with secure token handling:
136
+
137
+ ```python
138
+ from vercel_cli import run_vercel
139
+
140
+ # Secure: only VERCEL_TOKEN is passed to the CLI
141
+ exit_code = run_vercel(
142
+ ["deploy", "--prod"],
143
+ env={"VERCEL_TOKEN": "your-secure-token"}
144
+ )
145
+ ```
146
+
147
+ This approach avoids common security pitfalls of subprocess environment variable handling.
148
+
149
+ ## Updating the vendored Vercel CLI (maintainers)
150
+
151
+ There are two ways to update the vendored npm package under `vercel_cli/vendor/`:
152
+
153
+ 1) Manual update to a specific version
154
+
155
+ ```bash
156
+ # Using the console script defined in pyproject.toml
157
+ uv run update-vendor 46.0.2
158
+ # or equivalently
159
+ uv run python scripts/update_vendor.py 46.0.2
160
+ ```
161
+
162
+ This will:
163
+
164
+ - fetch `vercel@46.0.2` from npm,
165
+ - verify integrity/shasum,
166
+ - install production dependencies with `npm install --omit=dev`, and
167
+ - copy the result into `vercel_cli/vendor/`.
168
+
169
+ 1) Automatic check-and-release (GitHub Actions)
170
+
171
+ The workflow `.github/workflows/release.yml` checks npm `latest` and, if newer than the vendored version, will:
172
+
173
+ - vendor the new version using `scripts/check_and_update.py`,
174
+ - commit the changes and create a tag `v<version>`,
175
+ - build distributions, and
176
+ - publish to PyPI (requires `PYPI_API_TOKEN`).
177
+
178
+ ## Versioning
179
+
180
+ The Python package version is derived dynamically from the vendored `package.json` via Hatch’s version source:
181
+
182
+ ```toml
183
+ [tool.hatch.version]
184
+ path = "vercel_cli/vendor/package.json"
185
+ pattern = '"version"\s*:\s*"(?P<version>[^\\"]+)"'
186
+ ```
187
+
188
+ ## Development
189
+
190
+ - Build backend: `hatchling`
191
+ - Dependency management: `uv` (see `uv.lock`)
192
+ - Tests: `pytest` with coverage in `tests/`
193
+ - Lint/format: `ruff`; type-check: `basedpyright`
194
+
195
+ Common commands (using `uv`):
196
+
197
+ ```bash
198
+ # Run tests with coverage
199
+ uv run pytest --cov=vercel_cli --cov-report=term-missing
200
+
201
+ # Lint and format
202
+ uv run ruff check .
203
+ uv run ruff format .
204
+
205
+ # Type-check
206
+ uv run basedpyright
207
+
208
+ # Build wheel and sdist
209
+ uv run --with build python -m build
210
+ ```
@@ -0,0 +1,180 @@
1
+ # Python package wrapper for Vercel CLI
2
+
3
+ [![CI](https://github.com/nuage-studio/vercel-cli-python/actions/workflows/test.yml/badge.svg)](https://github.com/nuage-studio/vercel-cli-python/actions/workflows/test.yml)
4
+ [![codecov](https://codecov.io/gh/nuage-studio/vercel-cli-python/graph/badge.svg)](https://codecov.io/gh/nuage-studio/vercel-cli-python)
5
+ [![Supported Python Versions](https://img.shields.io/badge/python-3.8--3.13-blue.svg)](https://www.python.org/)
6
+
7
+ **vercel-cli** packages the npm `vercel` CLI for Python environments. It vendors the npm package under `vercel_cli/vendor/` and uses the bundled Node.js runtime provided by `nodejs-wheel-binaries`, so you can run `vercel` without installing Node.js.
8
+
9
+ It provides both a command-line interface and a Python API that other libraries can use programmatically instead of resorting to subprocess calls.
10
+
11
+ ## Quick start
12
+
13
+ - **Install**:
14
+
15
+ ```bash
16
+ pip install vercel-cli
17
+ ```
18
+
19
+ - **Use** (same arguments and behavior as the official npm CLI):
20
+
21
+ ```bash
22
+ vercel --version
23
+ vercel login
24
+ vercel deploy
25
+ ```
26
+
27
+ - **Use programmatically in Python** (for libraries that depend on this package):
28
+
29
+ ```python
30
+ from vercel_cli import run_vercel
31
+
32
+ # Deploy current directory
33
+ exit_code = run_vercel(["deploy"])
34
+
35
+ # Deploy specific directory with custom environment
36
+ exit_code = run_vercel(
37
+ ["deploy", "--prod"],
38
+ cwd="/path/to/project",
39
+ env={"VERCEL_TOKEN": "my-token"}
40
+ )
41
+
42
+ # Check version
43
+ exit_code = run_vercel(["--version"])
44
+ ```
45
+
46
+ ## What this provides
47
+
48
+ - **No system Node.js required**: The CLI runs via the Node binary from `nodejs-wheel-binaries` (currently Node 22.x).
49
+ - **Vendored npm package**: The `vercel` npm package (production deps only) is checked into `vercel_cli/vendor/`.
50
+ - **Console entrypoint**: The `vercel` command maps to `vercel_cli.run:main`, which executes `vercel_cli/vendor/dist/vc.js` with the bundled Node runtime.
51
+ - **Python API**: The `run_vercel()` function allows other Python libraries to use Vercel CLI programmatically without subprocess calls, with secure environment variable handling.
52
+
53
+ ## Requirements
54
+
55
+ - Python 3.8+
56
+ - macOS, Linux, or Windows supported by the Node wheels
57
+
58
+ ## How it works
59
+
60
+ At runtime, `vercel_cli.run` locates `vercel_cli/vendor/dist/vc.js` and launches it via the Node executable exposed by `nodejs_wheel_binaries`. CLI arguments are passed through unchanged, while environment variables are handled securely.
61
+
62
+ ## Programmatic usage
63
+
64
+ When using this package as a dependency in other Python libraries, you can call Vercel CLI commands directly without using subprocess:
65
+
66
+ ```python
67
+ from vercel_cli import run_vercel
68
+ import tempfile
69
+ import os
70
+
71
+ def deploy_my_app(source_dir: str, token: str) -> bool:
72
+ """Deploy an application to Vercel programmatically."""
73
+ with tempfile.TemporaryDirectory() as temp_dir:
74
+ # Copy your app to temp directory and modify as needed
75
+ # ...
76
+
77
+ # Deploy with custom environment
78
+ env = {
79
+ "VERCEL_TOKEN": token,
80
+ "NODE_ENV": "production"
81
+ }
82
+
83
+ exit_code = run_vercel(
84
+ ["deploy", "--prod", "--yes"],
85
+ cwd=temp_dir,
86
+ env=env
87
+ )
88
+
89
+ return exit_code == 0
90
+
91
+ # Usage
92
+ success = deploy_my_app("./my-app", "my-vercel-token")
93
+ ```
94
+
95
+ The `run_vercel()` function accepts:
96
+
97
+ - `args`: List of CLI arguments (same as command line)
98
+ - `cwd`: Working directory for the command
99
+ - `env`: Environment variables to set (passed directly to the Node.js runtime)
100
+
101
+ ## Security considerations
102
+
103
+ When using the `env` parameter, only explicitly provided environment variables are passed to the Vercel CLI. This prevents accidental leakage of sensitive environment variables from your Python process while still allowing you to set necessary variables like `VERCEL_TOKEN`.
104
+
105
+ Example with secure token handling:
106
+
107
+ ```python
108
+ from vercel_cli import run_vercel
109
+
110
+ # Secure: only VERCEL_TOKEN is passed to the CLI
111
+ exit_code = run_vercel(
112
+ ["deploy", "--prod"],
113
+ env={"VERCEL_TOKEN": "your-secure-token"}
114
+ )
115
+ ```
116
+
117
+ This approach avoids common security pitfalls of subprocess environment variable handling.
118
+
119
+ ## Updating the vendored Vercel CLI (maintainers)
120
+
121
+ There are two ways to update the vendored npm package under `vercel_cli/vendor/`:
122
+
123
+ 1) Manual update to a specific version
124
+
125
+ ```bash
126
+ # Using the console script defined in pyproject.toml
127
+ uv run update-vendor 46.0.2
128
+ # or equivalently
129
+ uv run python scripts/update_vendor.py 46.0.2
130
+ ```
131
+
132
+ This will:
133
+
134
+ - fetch `vercel@46.0.2` from npm,
135
+ - verify integrity/shasum,
136
+ - install production dependencies with `npm install --omit=dev`, and
137
+ - copy the result into `vercel_cli/vendor/`.
138
+
139
+ 1) Automatic check-and-release (GitHub Actions)
140
+
141
+ The workflow `.github/workflows/release.yml` checks npm `latest` and, if newer than the vendored version, will:
142
+
143
+ - vendor the new version using `scripts/check_and_update.py`,
144
+ - commit the changes and create a tag `v<version>`,
145
+ - build distributions, and
146
+ - publish to PyPI (requires `PYPI_API_TOKEN`).
147
+
148
+ ## Versioning
149
+
150
+ The Python package version is derived dynamically from the vendored `package.json` via Hatch’s version source:
151
+
152
+ ```toml
153
+ [tool.hatch.version]
154
+ path = "vercel_cli/vendor/package.json"
155
+ pattern = '"version"\s*:\s*"(?P<version>[^\\"]+)"'
156
+ ```
157
+
158
+ ## Development
159
+
160
+ - Build backend: `hatchling`
161
+ - Dependency management: `uv` (see `uv.lock`)
162
+ - Tests: `pytest` with coverage in `tests/`
163
+ - Lint/format: `ruff`; type-check: `basedpyright`
164
+
165
+ Common commands (using `uv`):
166
+
167
+ ```bash
168
+ # Run tests with coverage
169
+ uv run pytest --cov=vercel_cli --cov-report=term-missing
170
+
171
+ # Lint and format
172
+ uv run ruff check .
173
+ uv run ruff format .
174
+
175
+ # Type-check
176
+ uv run basedpyright
177
+
178
+ # Build wheel and sdist
179
+ uv run --with build python -m build
180
+ ```
@@ -0,0 +1,117 @@
1
+ [project]
2
+ name = "vercel-cli"
3
+ dynamic = ["version"]
4
+ description = "Vercel CLI packaged for Python (bundled Node.js, vendored npm)"
5
+ readme = "README.md"
6
+ requires-python = ">=3.8"
7
+ dependencies = [
8
+ "nodejs-wheel-binaries==22.16.0",
9
+ ]
10
+ authors = [
11
+ { name = "Nuage" }
12
+ ]
13
+ maintainers = [
14
+ { name = "Nuage" }
15
+ ]
16
+ keywords = [
17
+ "vercel",
18
+ "cli",
19
+ "deployment",
20
+ "serverless",
21
+ "nodejs",
22
+ "wrapper",
23
+ "npm",
24
+ "edge",
25
+ "functions",
26
+ ]
27
+ classifiers = [
28
+ "Development Status :: 5 - Production/Stable",
29
+ "Intended Audience :: Developers",
30
+ "Environment :: Console",
31
+ "Operating System :: OS Independent",
32
+ "Programming Language :: Python :: 3",
33
+ "Programming Language :: Python :: 3 :: Only",
34
+ "Programming Language :: Python :: 3.8",
35
+ "Programming Language :: Python :: 3.9",
36
+ "Programming Language :: Python :: 3.10",
37
+ "Programming Language :: Python :: 3.11",
38
+ "Programming Language :: Python :: 3.12",
39
+ "Programming Language :: Python :: 3.13",
40
+ "Topic :: Software Development :: Build Tools",
41
+ "Topic :: Utilities",
42
+ "Topic :: System :: Systems Administration",
43
+ ]
44
+ [project.urls]
45
+ Homepage = "https://github.com/nuage-studio/vercel-cli-python"
46
+ Repository = "https://github.com/nuage-studio/vercel-cli-python"
47
+ Issues = "https://github.com/nuage-studio/vercel-cli-python/issues"
48
+ Documentation = "https://github.com/nuage-studio/vercel-cli-python#readme"
49
+
50
+ [dependency-groups]
51
+ dev = [
52
+ "basedpyright>=1.31.3",
53
+ "pytest-cov>=5.0.0",
54
+ "ruff>=0.12.10",
55
+ ]
56
+
57
+ [project.scripts]
58
+ vercel = "vercel_cli.run:main"
59
+ vendor = "vercel_cli.vendor_cli:main"
60
+
61
+ [build-system]
62
+ requires = ["hatchling"]
63
+ build-backend = "hatchling.build"
64
+
65
+ [tool.hatch.build]
66
+ include = ["vercel_cli/vendor/**"]
67
+
68
+ [tool.hatch.build.targets.wheel]
69
+ packages = ["vercel_cli"]
70
+
71
+ [tool.hatch.version]
72
+ # Extract the version from the vendored package.json
73
+ path = "vercel_cli/vendor/package.json"
74
+ pattern = '"version"\s*:\s*"(?P<version>[^\"]+)"'
75
+
76
+
77
+ [tool.pytest.ini_options]
78
+ addopts = "--cov --cov-branch --cov-report=term-missing"
79
+ testpaths = ["tests"]
80
+
81
+ [tool.ruff]
82
+ # https://docs.astral.sh/ruff/settings/
83
+ preview = true
84
+ line-length = 88
85
+ target-version = "py38"
86
+
87
+ [tool.ruff.lint]
88
+ select = ["ALL"]
89
+ ignore = [
90
+ "CPY001", # We don't want warnings about missing Copyrights because it's private code
91
+ "TID252", # Nuage team disagrees about relative imports: we find them more readable
92
+ # Opinionated choices for conflicting rules
93
+ "D203", # 1 blank line required before class docstring (we prefer D211: no blank line)
94
+ "D213", # Multi-line docstring summary should start at the second line (we prefer D212: first line)
95
+ "COM812", # Trailing comma missing (conflicts with formatter, let formatter handle it)
96
+ ]
97
+ exclude = [".venv"]
98
+
99
+ [tool.ruff.format]
100
+ preview = true
101
+ skip-magic-trailing-comma = true
102
+
103
+ [tool.ruff.lint.per-file-ignores]
104
+ "tests/*.py" = [
105
+ "S", # none of these security focused rules are relevant for tests/build scripts
106
+ "D100", # Allow missing module docstrings in tests
107
+ "D103", # Allow missing function docstrings in tests
108
+ "S101", # Allow assert in tests
109
+ "PLR2004", # Allow magic numbers in tests
110
+ ]
111
+
112
+ [tool.ruff.lint.isort]
113
+ split-on-trailing-comma = false # Align with formatter's skip-magic-trailing-comma = true
114
+
115
+ [tool.pyright]
116
+ pythonVersion = "3.8"
117
+ typeCheckingMode = "strict"