@rafay99/cvx 0.12.0 → 0.14.0
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.
- package/LICENSE +21 -0
- package/README.md +186 -0
- package/launcher.js +3 -2
- package/package.json +19 -10
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Abdul Rafay
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
# Convex Switch (`cvx`)
|
|
2
|
+
|
|
3
|
+
Run multiple Convex accounts across multiple projects at once — without
|
|
4
|
+
logging in and out, without deploy keys, and without putting any secrets in
|
|
5
|
+
your project files.
|
|
6
|
+
|
|
7
|
+
You link a project folder to an account **once**. After that, the moment you
|
|
8
|
+
`cd` into that folder the right account becomes active, and plain
|
|
9
|
+
`bun run dev` (i.e. `convex dev`) just works. Start 5–6 projects in 5–6
|
|
10
|
+
terminals — each grabs its own account as it launches and they all run at the
|
|
11
|
+
same time.
|
|
12
|
+
|
|
13
|
+
## Purpose
|
|
14
|
+
|
|
15
|
+
The Convex CLI only remembers **one** logged-in account at a time — it lives in
|
|
16
|
+
a single global file, `~/.convex/config.json`. If you juggle several Convex
|
|
17
|
+
accounts (personal, work, clients) across many projects, that means constantly
|
|
18
|
+
`convex logout` / `convex login` churn every time you switch projects, and you
|
|
19
|
+
can never run two accounts' projects side by side.
|
|
20
|
+
|
|
21
|
+
`convex-switch` removes that friction entirely. Log into each account once, tag
|
|
22
|
+
it, and bind your projects to accounts. From then on the correct account is
|
|
23
|
+
selected automatically per project — no manual switching, no deploy keys, and
|
|
24
|
+
no tokens sitting inside your repositories. It turns "which account am I on
|
|
25
|
+
right now?" into a non-question.
|
|
26
|
+
|
|
27
|
+
## How it works (the one trick)
|
|
28
|
+
|
|
29
|
+
The Convex CLI decides *which account you are* by reading a single global file:
|
|
30
|
+
|
|
31
|
+
```
|
|
32
|
+
~/.convex/config.json → { "accessToken": "..." }
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
`cvx` keeps a private vault of your account tokens and a map of
|
|
36
|
+
project → account. A `chpwd` shell hook calls `cvx activate` on every `cd`;
|
|
37
|
+
when you enter a linked folder it rewrites that one global file to the linked
|
|
38
|
+
account. Nothing is injected at runtime, nothing lives in your repos.
|
|
39
|
+
|
|
40
|
+
```
|
|
41
|
+
~/.convex-switch/
|
|
42
|
+
accounts.json # name -> { token, teams } (chmod 600)
|
|
43
|
+
links.json # /abs/project/path -> account (chmod 600)
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
Because a running `convex dev` caches its deployment credentials at startup,
|
|
47
|
+
swapping the global file afterwards doesn't disturb sessions already
|
|
48
|
+
running — that's what makes true simultaneous multi-account work.
|
|
49
|
+
|
|
50
|
+
## Install
|
|
51
|
+
|
|
52
|
+
**Homebrew** (macOS + Linux):
|
|
53
|
+
|
|
54
|
+
```bash
|
|
55
|
+
brew install rafay99-epic/apps/cvx
|
|
56
|
+
cvx hook --install # adds the cd-hook to ~/.zshrc (once)
|
|
57
|
+
exec zsh # reload your shell
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
**npm / bun / pnpm** — installs the same prebuilt binary:
|
|
61
|
+
|
|
62
|
+
```bash
|
|
63
|
+
npm install -g @rafay99/cvx # or: bun add -g @rafay99/cvx
|
|
64
|
+
pnpm add -g @rafay99/cvx
|
|
65
|
+
cvx hook --install
|
|
66
|
+
exec zsh
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
> Distributed the esbuild way: per-platform packages
|
|
70
|
+
> (`@rafay99/cvx-<os>-<arch>`) carry the binary, gated by `os`/`cpu`, and a
|
|
71
|
+
> tiny launcher in the main package (`@rafay99/cvx`) execs it. No postinstall —
|
|
72
|
+
> so it works under `bun add -g` and `--ignore-scripts` too. The command you
|
|
73
|
+
> type is still `cvx`.
|
|
74
|
+
|
|
75
|
+
Prebuilt binaries: **macOS** (arm64/x64), **Linux** (arm64/x64), **Windows**
|
|
76
|
+
(x64). On Windows the commands all work, but automatic switching relies on a
|
|
77
|
+
zsh `chpwd` hook — so for now run `cvx activate` when you switch projects (or
|
|
78
|
+
use WSL/zsh for the auto-switch experience).
|
|
79
|
+
|
|
80
|
+
**From source** (Bun):
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
bun link # from this repo — exposes `cvx` globally
|
|
84
|
+
cvx hook --install
|
|
85
|
+
exec zsh
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
## Set up your accounts (once each)
|
|
89
|
+
|
|
90
|
+
The easy way — `cvx login <name>` opens a fresh browser sign-in and stores it:
|
|
91
|
+
|
|
92
|
+
```bash
|
|
93
|
+
cvx login personal # browser sign-in, stored as "personal"
|
|
94
|
+
cvx login work # browser sign-in (different account), stored as "work"
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
> **Gotcha:** plain `npx convex login` **no-ops if the device is already
|
|
98
|
+
> authorized** ("This device has previously been authorized…") — so it won't
|
|
99
|
+
> switch you to a second account. You must force a fresh sign-in with
|
|
100
|
+
> `npx convex login --force`. `cvx login` passes `--force` for you.
|
|
101
|
+
|
|
102
|
+
Manual equivalent (e.g. to also capture the account you're *already* signed
|
|
103
|
+
into):
|
|
104
|
+
|
|
105
|
+
```bash
|
|
106
|
+
cvx add personal # snapshot the login currently in ~/.convex/config.json
|
|
107
|
+
npx convex login --force # force browser sign-in as the next account
|
|
108
|
+
cvx add work
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
## Wire projects to accounts
|
|
112
|
+
|
|
113
|
+
```bash
|
|
114
|
+
cd ~/Code/project-a && cvx link personal
|
|
115
|
+
cd ~/Code/project-b && cvx link work
|
|
116
|
+
cd ~/Code/project-c && cvx link personal # one account → many projects
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
## Daily use
|
|
120
|
+
|
|
121
|
+
```bash
|
|
122
|
+
cd ~/Code/project-a # ⇄ convex account → personal
|
|
123
|
+
bun run dev # runs as personal
|
|
124
|
+
|
|
125
|
+
# new terminal, at the same time:
|
|
126
|
+
cd ~/Code/project-b # ⇄ convex account → work
|
|
127
|
+
bun run dev # runs as work — both live simultaneously
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
## Commands
|
|
131
|
+
|
|
132
|
+
| Command | What it does |
|
|
133
|
+
| --- | --- |
|
|
134
|
+
| `cvx add [name]` | Store the current `~/.convex` login as an account |
|
|
135
|
+
| `cvx login <name>` | `npx convex login`, then store it as `<name>` |
|
|
136
|
+
| `cvx link <account> [path]` | Link a project dir (default cwd) to an account |
|
|
137
|
+
| `cvx unlink [path]` | Remove a link |
|
|
138
|
+
| `cvx activate [-q]` | Activate this dir's account (the hook calls this) |
|
|
139
|
+
| `cvx status` | Show the active account and this dir's link |
|
|
140
|
+
| `cvx accounts` | List stored accounts |
|
|
141
|
+
| `cvx ls` | List linked projects |
|
|
142
|
+
| `cvx which [path]` | Print the account name for a dir (scripting) |
|
|
143
|
+
| `cvx rm <account>` | Forget an account and its links |
|
|
144
|
+
| `cvx hook [--install]` | Print (or install) the zsh cd-hook |
|
|
145
|
+
|
|
146
|
+
## Project layout
|
|
147
|
+
|
|
148
|
+
The CLI is split into small modules; `bun build --compile` bundles them all into
|
|
149
|
+
a single binary, so the split costs nothing at build time.
|
|
150
|
+
|
|
151
|
+
```
|
|
152
|
+
bin/cvx.ts entry point + command dispatch
|
|
153
|
+
src/store.ts data layer: vault I/O, the config swap, token verify, paths
|
|
154
|
+
src/ui.ts colors, the logo banner, first-run welcome, help
|
|
155
|
+
src/commands.ts one function per subcommand
|
|
156
|
+
src/args.ts flag parsing
|
|
157
|
+
man/cvx.1 man page (installed by Homebrew → `man cvx`)
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
First run of a bare `cvx` shows a welcome screen; `cvx welcome` shows it again,
|
|
161
|
+
and `man cvx` opens the manual.
|
|
162
|
+
|
|
163
|
+
## Releasing
|
|
164
|
+
|
|
165
|
+
Pushing to `main` (touching `bin/**` or `package.json`) triggers
|
|
166
|
+
`.github/workflows/release.yml`, which:
|
|
167
|
+
|
|
168
|
+
1. cross-compiles standalone `cvx` binaries for macOS (arm64/x64) and Linux
|
|
169
|
+
(arm64/x64) with `bun build --compile` on a single runner,
|
|
170
|
+
2. publishes a GitHub release `v0.<commit-count>` with the tarballs +
|
|
171
|
+
`checksums.txt`, and
|
|
172
|
+
3. regenerates the Homebrew formula (all four sha256s) and pushes it to the
|
|
173
|
+
`rafay99-epic/homebrew-apps` tap — no checksum is ever hand-edited.
|
|
174
|
+
|
|
175
|
+
Step 3 needs a `TAP_TOKEN` repo secret (a fine-grained PAT with
|
|
176
|
+
**Contents: Read & Write** on `rafay99-epic/homebrew-apps`); without it the
|
|
177
|
+
release still builds and publishes, only the formula bump is skipped.
|
|
178
|
+
|
|
179
|
+
## Notes
|
|
180
|
+
|
|
181
|
+
- Tokens live only in `~/.convex-switch/` (chmod 600) — never in a repo,
|
|
182
|
+
never in `.env.local`, no deploy keys.
|
|
183
|
+
- To rotate/refresh an account, `npx convex login` into it again then
|
|
184
|
+
`cvx add <name> --force`.
|
|
185
|
+
- Non-zsh shells: run `cvx hook` and adapt the snippet to your shell's
|
|
186
|
+
directory-change hook.
|
package/launcher.js
CHANGED
|
@@ -9,14 +9,15 @@
|
|
|
9
9
|
const { spawnSync } = require("child_process");
|
|
10
10
|
|
|
11
11
|
const target = `@rafay99/cvx-${process.platform}-${process.arch}`;
|
|
12
|
+
const binName = process.platform === "win32" ? "cvx.exe" : "cvx";
|
|
12
13
|
|
|
13
14
|
let binary;
|
|
14
15
|
try {
|
|
15
|
-
binary = require.resolve(`${target}/bin
|
|
16
|
+
binary = require.resolve(`${target}/bin/${binName}`);
|
|
16
17
|
} catch {
|
|
17
18
|
console.error(
|
|
18
19
|
`cvx: no prebuilt binary for ${process.platform}-${process.arch}.\n` +
|
|
19
|
-
`Supported: darwin-arm64, darwin-x64, linux-x64, linux-arm64.\n` +
|
|
20
|
+
`Supported: darwin-arm64, darwin-x64, linux-x64, linux-arm64, win32-x64.\n` +
|
|
20
21
|
`If your platform is supported, reinstall without --no-optional.`,
|
|
21
22
|
);
|
|
22
23
|
process.exit(1);
|
package/package.json
CHANGED
|
@@ -1,19 +1,28 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@rafay99/cvx",
|
|
3
|
-
"version": "0.
|
|
4
|
-
"description": "Switch Convex accounts per project automatically — no deploy keys, no tokens in repos",
|
|
5
|
-
"keywords": [
|
|
3
|
+
"version": "0.14.0",
|
|
4
|
+
"description": "Switch Convex accounts per project automatically — run many Convex accounts across projects at once, no login/logout churn, no deploy keys, no tokens in your repos",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"convex", "convex-dev", "convex-cli", "cli", "command-line",
|
|
7
|
+
"accounts", "account-switcher", "multi-account", "multi-tenant",
|
|
8
|
+
"auth", "login", "credentials", "workspace", "monorepo",
|
|
9
|
+
"developer-tools", "devtools", "terminal", "dotfiles", "bun",
|
|
10
|
+
"context-switch", "deploy"
|
|
11
|
+
],
|
|
6
12
|
"license": "MIT",
|
|
7
|
-
"homepage": "https://github.com/rafay99-epic/convex-switch",
|
|
8
|
-
"
|
|
13
|
+
"homepage": "https://github.com/rafay99-epic/convex-switch#readme",
|
|
14
|
+
"bugs": "https://github.com/rafay99-epic/convex-switch/issues",
|
|
15
|
+
"repository": { "type": "git", "url": "git+https://github.com/rafay99-epic/convex-switch.git" },
|
|
16
|
+
"author": "Abdul Rafay",
|
|
9
17
|
"bin": { "cvx": "launcher.js" },
|
|
10
18
|
"man": ["cvx.1"],
|
|
11
|
-
"files": ["launcher.js", "cvx.1"],
|
|
19
|
+
"files": ["launcher.js", "cvx.1", "README.md", "LICENSE"],
|
|
12
20
|
"engines": { "node": ">=16" },
|
|
13
21
|
"optionalDependencies": {
|
|
14
|
-
"@rafay99/cvx-darwin-arm64": "0.
|
|
15
|
-
"@rafay99/cvx-darwin-x64": "0.
|
|
16
|
-
"@rafay99/cvx-linux-x64": "0.
|
|
17
|
-
"@rafay99/cvx-linux-arm64": "0.
|
|
22
|
+
"@rafay99/cvx-darwin-arm64": "0.14.0",
|
|
23
|
+
"@rafay99/cvx-darwin-x64": "0.14.0",
|
|
24
|
+
"@rafay99/cvx-linux-x64": "0.14.0",
|
|
25
|
+
"@rafay99/cvx-linux-arm64": "0.14.0",
|
|
26
|
+
"@rafay99/cvx-win32-x64": "0.14.0"
|
|
18
27
|
}
|
|
19
28
|
}
|