@grantjs/cli 1.11.0 → 1.13.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/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # @grantjs/cli
2
2
 
3
- Grant CLI for setup, authentication, profiles, and typings generation.
3
+ Grant CLI for profiles, REST API access, and typings generation. Agents and scripts should use `grant api` or `grant <resource> <verb>` with `--output json` (or `GRANT_*` environment variables).
4
4
 
5
5
  ## Install
6
6
 
@@ -17,13 +17,25 @@ npm install -g @grantjs/cli
17
17
  | `grant version` | Show CLI version (`-j, --json` for JSON) |
18
18
  | `grant help` / `grant --help` | Show help |
19
19
  | `grant start` | Interactive setup (API URL, auth, profile, scope); alias: `grant setup` |
20
+ | `grant whoami` | Show the authenticated caller (`GET /api/me`) |
21
+ | `grant api <method> <path>` | Call any REST path with the resolved profile |
22
+ | `grant <resource> <verb>` | Named REST commands from OpenAPI (e.g. `grant users list`) |
20
23
  | `grant generate-types` | Generate project-scoped `ResourceSlug` and `ResourceAction` TypeScript (uses selected profile) |
21
24
  | `grant config path` | Print path to the config file |
22
25
  | `grant config list` | List profiles and which is default |
23
26
  | `grant config show` | Show config summary for a profile (no secrets) |
24
27
  | `grant config set <key>` | Set a config value for a profile (see below) |
25
28
 
26
- All commands that use config accept **`-p, --profile <name>`** to target a profile (default: the configured default profile).
29
+ All commands that use config accept **`-p, --profile <name>`** (or `GRANT_PROFILE`). API commands also accept `--output json|text` (JSON when stdout is not a TTY).
30
+
31
+ Environment: `GRANT_API_URL`, `GRANT_ACCESS_TOKEN`, `GRANT_CLIENT_ID`, `GRANT_CLIENT_SECRET`, `GRANT_SCOPE_TENANT`, `GRANT_SCOPE_ID`, `GRANT_ORIGIN_VERIFY`. Flags win over env, env over the profile file.
32
+
33
+ ```bash
34
+ export GRANT_PROFILE=ci
35
+ grant whoami --output json
36
+ grant users list --output json
37
+ grant api post /api/roles --body '{"name":"Reviewer"}'
38
+ ```
27
39
 
28
40
  ---
29
41
 
@@ -99,6 +111,7 @@ Set a value for a profile. Use **`-p, --profile <name>`** to target a profile (d
99
111
  | `grant config set credentials` | Set API key and scope (see options below) |
100
112
  | `grant config set scope` | Set selected project scope only |
101
113
  | `grant config set generate-types-output <path>` | Set default output path for `grant generate-types` (empty to clear) |
114
+ | `grant config set origin-verify [secret]` | Set `x-origin-verify` when `apiUrl` is the raw API origin |
102
115
  | `grant config set default-profile <name>` | Set which profile is used when `--profile` is omitted |
103
116
 
104
117
  **Credentials options** (all required for `credentials`):
@@ -0,0 +1,11 @@
1
+ import { RuntimeFlags } from '../config/credentials.js';
2
+ import { TransportResponse } from './transport.js';
3
+ export interface AuthenticatedRequest {
4
+ flags?: RuntimeFlags;
5
+ method: string;
6
+ path: string;
7
+ query?: Record<string, string | number | boolean | undefined>;
8
+ body?: unknown;
9
+ injectScope?: boolean;
10
+ }
11
+ export declare function authenticatedRequest<T = unknown>(req: AuthenticatedRequest): Promise<TransportResponse<T>>;
@@ -45,6 +45,13 @@ export interface ProjectItem {
45
45
  * POST {baseUrl}/api/auth/token
46
46
  */
47
47
  export declare function exchangeApiKey(baseUrl: string, body: TokenExchangeRequest): Promise<TokenExchangeResponse>;
48
+ /**
49
+ * Refresh a session. Cookie is preferred by browsers; CLI sends the stored refresh token in the body.
50
+ */
51
+ export declare function refreshSession(baseUrl: string, refreshToken: string, originVerifySecret?: string): Promise<{
52
+ accessToken: string;
53
+ refreshToken?: string;
54
+ }>;
48
55
  /**
49
56
  * Login with email and password. POST {baseUrl}/api/auth/login
50
57
  * Returns access token, refresh token, and primary account (personal).
@@ -59,12 +66,12 @@ export declare function exchangeCliCallback(baseUrl: string, code: string): Prom
59
66
  * Fetch organizations (paginated). Requires Bearer token. GET /api/organizations?scopeId=&tenant=
60
67
  * Scope is the account context (user's personal account id, tenant 'account').
61
68
  */
62
- export declare function fetchOrganizations(baseUrl: string, accessToken: string, scope: ApiScope): Promise<OrganizationItem[]>;
69
+ export declare function fetchOrganizations(baseUrl: string, accessToken: string, scope: ApiScope, originVerifySecret?: string): Promise<OrganizationItem[]>;
63
70
  /**
64
71
  * Fetch projects for a scope (account or organization). Paginated. Requires Bearer token.
65
72
  * GET /api/projects?scopeId=&tenant=
66
73
  */
67
- export declare function fetchProjects(baseUrl: string, accessToken: string, scope: ApiScope): Promise<ProjectItem[]>;
74
+ export declare function fetchProjects(baseUrl: string, accessToken: string, scope: ApiScope, originVerifySecret?: string): Promise<ProjectItem[]>;
68
75
  export interface ApiScope {
69
76
  id: string;
70
77
  tenant: string;
@@ -85,9 +92,9 @@ export interface PermissionItem {
85
92
  /**
86
93
  * Fetch all resources for a scope (paginated). Requires Bearer token.
87
94
  */
88
- export declare function fetchResources(baseUrl: string, accessToken: string, scope: ApiScope): Promise<ResourceItem[]>;
95
+ export declare function fetchResources(baseUrl: string, accessToken: string, scope: ApiScope, originVerifySecret?: string): Promise<ResourceItem[]>;
89
96
  /**
90
97
  * Fetch all permissions for a scope (paginated). Requires Bearer token.
91
98
  */
92
- export declare function fetchPermissions(baseUrl: string, accessToken: string, scope: ApiScope): Promise<PermissionItem[]>;
99
+ export declare function fetchPermissions(baseUrl: string, accessToken: string, scope: ApiScope, originVerifySecret?: string): Promise<PermissionItem[]>;
93
100
  export {};
@@ -0,0 +1,9 @@
1
+ /** Process exit codes. 0 is success (Commander default). */
2
+ export declare const EXIT_ERROR = 1;
3
+ export declare const EXIT_AUTH = 2;
4
+ export declare class CliError extends Error {
5
+ readonly exitCode: number;
6
+ constructor(message: string, exitCode?: number);
7
+ }
8
+ export declare function isAuthFailure(status: number, message: string): boolean;
9
+ export declare function handleCliError(err: unknown): never;
@@ -0,0 +1,15 @@
1
+ export interface TransportRequest {
2
+ apiUrl: string;
3
+ method: string;
4
+ path: string;
5
+ token?: string;
6
+ originVerifySecret?: string;
7
+ query?: Record<string, string | number | boolean | undefined>;
8
+ body?: unknown;
9
+ extraHeaders?: Record<string, string>;
10
+ }
11
+ export interface TransportResponse<T = unknown> {
12
+ status: number;
13
+ data: T;
14
+ }
15
+ export declare function apiRequest<T = unknown>(req: TransportRequest): Promise<TransportResponse<T>>;
@@ -0,0 +1,2 @@
1
+ import { Command } from 'commander';
2
+ export declare function createApiCommand(program: Command): void;
@@ -0,0 +1,2 @@
1
+ import { Command } from 'commander';
2
+ export declare function createSpecCommands(program: Command): void;
@@ -0,0 +1,2 @@
1
+ import { Command } from 'commander';
2
+ export declare function createWhoamiCommand(program: Command): void;
@@ -0,0 +1,29 @@
1
+ import { GrantConfig, GrantScope } from '../types/config.js';
2
+ export declare const ENV: {
3
+ readonly profile: "GRANT_PROFILE";
4
+ readonly apiUrl: "GRANT_API_URL";
5
+ readonly clientId: "GRANT_CLIENT_ID";
6
+ readonly clientSecret: "GRANT_CLIENT_SECRET";
7
+ readonly scopeTenant: "GRANT_SCOPE_TENANT";
8
+ readonly scopeId: "GRANT_SCOPE_ID";
9
+ readonly originVerify: "GRANT_ORIGIN_VERIFY";
10
+ readonly accessToken: "GRANT_ACCESS_TOKEN";
11
+ };
12
+ export interface RuntimeFlags {
13
+ profile?: string;
14
+ scopeId?: string;
15
+ tenant?: string;
16
+ }
17
+ export interface RuntimeContext {
18
+ apiUrl: string;
19
+ authMethod: GrantConfig['authMethod'] | 'token';
20
+ config: GrantConfig;
21
+ profileName: string | null;
22
+ scope?: GrantScope;
23
+ originVerifySecret?: string;
24
+ }
25
+ /**
26
+ * Resolve API URL, credentials, and scope.
27
+ * Order: flags → GRANT_* env → named profile file.
28
+ */
29
+ export declare function resolveRuntimeContext(flags?: RuntimeFlags): Promise<RuntimeContext>;
@@ -1,2 +1 @@
1
- export { resolveAccessToken } from './resolve-token.js';
2
1
  export { DEFAULT_PROFILE_NAME, getConfigPath, listProfileNames, loadConfigFile, loadProfile, saveConfigFile, } from './storage.js';
@@ -0,0 +1,3 @@
1
+ export type OutputFormat = 'json' | 'text';
2
+ export declare function parseOutputFormat(value: string | undefined): OutputFormat;
3
+ export declare function printOutput(data: unknown, format: OutputFormat): void;
@@ -1,9 +1,8 @@
1
1
  import { GrantConfig } from '../types/config.js';
2
2
  /**
3
- * Resolve a valid access token from stored config.
4
- * Only tokens are stored (no credentials). Session auth does not auto-refresh; user must re-auth when the access token expires.
5
- *
6
- * - API key: exchanges clientId + clientSecret for a fresh token (no credentials stored after exchange).
7
- * - Session: returns the stored access token. When it expires, the user must run "grant start" again to re-authenticate.
3
+ * Resolve a valid access token from env or stored config.
4
+ * API key: exchanges clientId + clientSecret for a fresh token.
5
+ * Session: returns the stored access token. GRANT_ACCESS_TOKEN wins when set.
8
6
  */
9
7
  export declare function resolveAccessToken(config: GrantConfig): Promise<string>;
8
+ export declare function refreshAndPersistSession(config: GrantConfig, profileName?: string | null): Promise<string>;