@axtrabase/cli 0.1.0 → 0.1.1
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/README.md +28 -0
- package/dist/commands/logout.d.ts +12 -1
- package/dist/commands/logout.d.ts.map +1 -1
- package/dist/commands/logout.js +86 -9
- package/dist/commands/logout.js.map +1 -1
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -13,6 +13,18 @@ npm install -g @axtrabase/cli
|
|
|
13
13
|
npx @axtrabase/cli whoami
|
|
14
14
|
```
|
|
15
15
|
|
|
16
|
+
If `axtrabase --version` says `command not found` right after install, npm's
|
|
17
|
+
default global prefix likely isn't on your `PATH` (or isn't writable at all,
|
|
18
|
+
in which case the install itself silently fails). Fix:
|
|
19
|
+
|
|
20
|
+
```bash
|
|
21
|
+
mkdir -p ~/.npm-global
|
|
22
|
+
npm config set prefix ~/.npm-global
|
|
23
|
+
echo 'export PATH="$HOME/.npm-global/bin:$PATH"' >> ~/.zshrc # or ~/.bashrc
|
|
24
|
+
source ~/.zshrc
|
|
25
|
+
npm install -g @axtrabase/cli
|
|
26
|
+
```
|
|
27
|
+
|
|
16
28
|
## Authenticate
|
|
17
29
|
|
|
18
30
|
```bash
|
|
@@ -41,6 +53,22 @@ Useful for CI and for handing a coding agent a scoped, disposable token.
|
|
|
41
53
|
AXTRABASE_CLI_TOKEN=axcli_... axtrabase context --agent
|
|
42
54
|
```
|
|
43
55
|
|
|
56
|
+
`AXTRABASE_CLI_TOKEN` takes precedence over a stored `login` credential.
|
|
57
|
+
`logout` can't unset an environment variable in the shell that invoked it,
|
|
58
|
+
so instead of falsely claiming "not logged in" it says so explicitly:
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
$ AXTRABASE_CLI_TOKEN=axcli_... axtrabase logout
|
|
62
|
+
Authentication is coming from AXTRABASE_CLI_TOKEN.
|
|
63
|
+
Nothing was removed.
|
|
64
|
+
Unset the variable in your shell to log out locally:
|
|
65
|
+
bash/zsh: unset AXTRABASE_CLI_TOKEN
|
|
66
|
+
PowerShell: Remove-Item Env:AXTRABASE_CLI_TOKEN
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
`--revoke` still revokes the active env token server-side (useful for
|
|
70
|
+
CI/agent cleanup) — it just still can't remove the variable itself.
|
|
71
|
+
|
|
44
72
|
## Select an organisation and project
|
|
45
73
|
|
|
46
74
|
```bash
|
|
@@ -6,7 +6,18 @@ interface LogoutOptions {
|
|
|
6
6
|
revoke?: boolean;
|
|
7
7
|
}
|
|
8
8
|
export declare function registerLogoutCommand(program: Command): void;
|
|
9
|
-
/**
|
|
9
|
+
/**
|
|
10
|
+
* Exported for testing — registerLogoutCommand wires the real commander
|
|
11
|
+
* action to this.
|
|
12
|
+
*
|
|
13
|
+
* Uses the same resolveToken() every other command uses (env >
|
|
14
|
+
* stored — see config/resolve.ts) so `logout` can never disagree with what
|
|
15
|
+
* the CLI is actually authenticating with. That resolver is also why the
|
|
16
|
+
* three-way split below exists: a stored credential can be present but
|
|
17
|
+
* inactive (AXTRABASE_CLI_TOKEN currently overrides it), and `logout` must
|
|
18
|
+
* only ever act on the credential that's actually in effect — never revoke
|
|
19
|
+
* or clear an unrelated, inactive one.
|
|
20
|
+
*/
|
|
10
21
|
export declare function runLogout(options: LogoutOptions): Promise<void>;
|
|
11
22
|
export {};
|
|
12
23
|
//# sourceMappingURL=logout.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"logout.d.ts","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAOzC,UAAU,aAAa;IACrB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAY5D;AAED
|
|
1
|
+
{"version":3,"file":"logout.d.ts","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAOzC,UAAU,aAAa;IACrB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI,CAY5D;AAED;;;;;;;;;;;GAWG;AACH,wBAAsB,SAAS,CAAC,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAwBrE"}
|
package/dist/commands/logout.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { CredentialStore } from "../config/credentials.js";
|
|
2
|
-
import { resolveApiUrl } from "../config/resolve.js";
|
|
2
|
+
import { resolveApiUrl, resolveToken } from "../config/resolve.js";
|
|
3
3
|
import { ControlPlaneClient } from "../http/client.js";
|
|
4
4
|
import { printJson, printLine, printProgress } from "../output/print.js";
|
|
5
5
|
import { runWithErrorHandling } from "../report-error.js";
|
|
@@ -13,24 +13,97 @@ export function registerLogoutCommand(program) {
|
|
|
13
13
|
await runWithErrorHandling(() => runLogout(options), options);
|
|
14
14
|
});
|
|
15
15
|
}
|
|
16
|
-
/**
|
|
16
|
+
/**
|
|
17
|
+
* Exported for testing — registerLogoutCommand wires the real commander
|
|
18
|
+
* action to this.
|
|
19
|
+
*
|
|
20
|
+
* Uses the same resolveToken() every other command uses (env >
|
|
21
|
+
* stored — see config/resolve.ts) so `logout` can never disagree with what
|
|
22
|
+
* the CLI is actually authenticating with. That resolver is also why the
|
|
23
|
+
* three-way split below exists: a stored credential can be present but
|
|
24
|
+
* inactive (AXTRABASE_CLI_TOKEN currently overrides it), and `logout` must
|
|
25
|
+
* only ever act on the credential that's actually in effect — never revoke
|
|
26
|
+
* or clear an unrelated, inactive one.
|
|
27
|
+
*/
|
|
17
28
|
export async function runLogout(options) {
|
|
18
|
-
const
|
|
19
|
-
|
|
20
|
-
if (!stored) {
|
|
29
|
+
const resolved = resolveToken();
|
|
30
|
+
if (!resolved) {
|
|
21
31
|
if (options.json) {
|
|
22
|
-
printJson({
|
|
32
|
+
printJson({
|
|
33
|
+
loggedOut: false,
|
|
34
|
+
revoked: false,
|
|
35
|
+
credentialSource: null,
|
|
36
|
+
environmentVariableStillSet: false,
|
|
37
|
+
reason: "not-logged-in"
|
|
38
|
+
});
|
|
23
39
|
}
|
|
24
40
|
else {
|
|
25
41
|
printLine("Not logged in — nothing to do.");
|
|
26
42
|
}
|
|
27
43
|
return;
|
|
28
44
|
}
|
|
45
|
+
if (resolved.source === "env") {
|
|
46
|
+
await runEnvTokenLogout(resolved.token, options);
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
await runStoredTokenLogout(resolved.token, options);
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* The CLI never has authority over the caller's shell — it can read
|
|
53
|
+
* AXTRABASE_CLI_TOKEN, but it cannot unset an environment variable in the
|
|
54
|
+
* parent process that invoked it. `logout` must never claim otherwise, and
|
|
55
|
+
* must never quietly clear an unrelated stored credential just because one
|
|
56
|
+
* happens to exist on disk while the env token is what's actually active.
|
|
57
|
+
*/
|
|
58
|
+
async function runEnvTokenLogout(token, options) {
|
|
59
|
+
const hasStoredCredential = new CredentialStore().read() !== undefined;
|
|
60
|
+
let revoked = false;
|
|
61
|
+
let revokeError;
|
|
62
|
+
if (options.revoke) {
|
|
63
|
+
try {
|
|
64
|
+
revoked = await revokeActiveToken(token, resolveApiUrl(options.apiUrl));
|
|
65
|
+
}
|
|
66
|
+
catch (error) {
|
|
67
|
+
revokeError = error instanceof Error ? error.message : "Unknown error.";
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
if (options.json) {
|
|
71
|
+
printJson({
|
|
72
|
+
loggedOut: false,
|
|
73
|
+
revoked,
|
|
74
|
+
credentialSource: "environment",
|
|
75
|
+
environmentVariableStillSet: true,
|
|
76
|
+
...(hasStoredCredential ? { storedCredentialUntouched: true } : {}),
|
|
77
|
+
...(revokeError ? { revokeError } : {})
|
|
78
|
+
});
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
if (revoked) {
|
|
82
|
+
printLine("Revoked the active CLI token on AxtraBase.");
|
|
83
|
+
printLine("AXTRABASE_CLI_TOKEN is still set in your shell; unset it before continuing.");
|
|
84
|
+
}
|
|
85
|
+
else if (options.revoke) {
|
|
86
|
+
printLine(`Could not revoke the token on AxtraBase: ${revokeError}`);
|
|
87
|
+
printLine("AXTRABASE_CLI_TOKEN is still set in your shell.");
|
|
88
|
+
}
|
|
89
|
+
else {
|
|
90
|
+
printLine("Authentication is coming from AXTRABASE_CLI_TOKEN.");
|
|
91
|
+
printLine("Nothing was removed.");
|
|
92
|
+
printLine("Unset the variable in your shell to log out locally:");
|
|
93
|
+
printLine(" bash/zsh: unset AXTRABASE_CLI_TOKEN");
|
|
94
|
+
printLine(" PowerShell: Remove-Item Env:AXTRABASE_CLI_TOKEN");
|
|
95
|
+
}
|
|
96
|
+
if (hasStoredCredential) {
|
|
97
|
+
printProgress("Note: a stored credential from `axtrabase login` also exists and was not touched.");
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
async function runStoredTokenLogout(token, options) {
|
|
101
|
+
const credentials = new CredentialStore();
|
|
29
102
|
let revoked = false;
|
|
30
103
|
let revokeError;
|
|
31
104
|
if (options.revoke) {
|
|
32
105
|
try {
|
|
33
|
-
revoked = await
|
|
106
|
+
revoked = await revokeActiveToken(token, resolveApiUrl(options.apiUrl));
|
|
34
107
|
}
|
|
35
108
|
catch (error) {
|
|
36
109
|
revokeError = error instanceof Error ? error.message : "Unknown error.";
|
|
@@ -46,6 +119,8 @@ export async function runLogout(options) {
|
|
|
46
119
|
printJson({
|
|
47
120
|
loggedOut: true,
|
|
48
121
|
revoked,
|
|
122
|
+
credentialSource: "stored",
|
|
123
|
+
environmentVariableStillSet: false,
|
|
49
124
|
...(revokeError ? { revokeError } : {})
|
|
50
125
|
});
|
|
51
126
|
}
|
|
@@ -67,9 +142,11 @@ export async function runLogout(options) {
|
|
|
67
142
|
* uses — that route is session-only, and a CLI running non-interactively
|
|
68
143
|
* (CI, an agent) has no browser session to authenticate it with. The token
|
|
69
144
|
* being revoked *is* the authentication here, so there is no id to look up
|
|
70
|
-
* client-side first.
|
|
145
|
+
* client-side first. Works identically whether the active token came from
|
|
146
|
+
* AXTRABASE_CLI_TOKEN or the stored credential file — the endpoint only
|
|
147
|
+
* ever knows "the token that authenticated this request."
|
|
71
148
|
*/
|
|
72
|
-
async function
|
|
149
|
+
async function revokeActiveToken(rawToken, apiUrl) {
|
|
73
150
|
const client = new ControlPlaneClient({ baseUrl: apiUrl, token: rawToken });
|
|
74
151
|
await client.delete("/api/v1/cli-tokens/self");
|
|
75
152
|
return true;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"logout.js","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AAC3D,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;
|
|
1
|
+
{"version":3,"file":"logout.js","sourceRoot":"","sources":["../../src/commands/logout.ts"],"names":[],"mappings":"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"}
|
package/dist/version.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
/** Bump alongside package.json's version — read at runtime for --version and the X-AxtraBase-Client User-Agent, same convention as @axtrabase/sdk's SDK_VERSION. */
|
|
2
|
-
export declare const CLI_VERSION = "0.1.
|
|
2
|
+
export declare const CLI_VERSION = "0.1.1";
|
|
3
3
|
export declare const CLI_CLIENT_NAME = "axtrabase-cli";
|
|
4
4
|
//# sourceMappingURL=version.d.ts.map
|
package/dist/version.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
/** Bump alongside package.json's version — read at runtime for --version and the X-AxtraBase-Client User-Agent, same convention as @axtrabase/sdk's SDK_VERSION. */
|
|
2
|
-
export const CLI_VERSION = "0.1.
|
|
2
|
+
export const CLI_VERSION = "0.1.1";
|
|
3
3
|
export const CLI_CLIENT_NAME = "axtrabase-cli";
|
|
4
4
|
//# sourceMappingURL=version.js.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@axtrabase/cli",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.1",
|
|
4
4
|
"description": "The AxtraBase CLI — inspect an AxtraBase project's schema, permissions, and environment, and build against it without touching Dataverse directly.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "UNLICENSED",
|