Skip to content

Commit caa568e

Browse files
@W-20893800: Adding support for stateful auth [sfcc-ci compatibility] (#167)
1 parent c2df074 commit caa568e

24 files changed

Lines changed: 2222 additions & 19 deletions

File tree

.changeset/stateful-auth.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
---
2+
'@salesforce/b2c-cli': minor
3+
'@salesforce/b2c-tooling-sdk': minor
4+
---
5+
6+
Introduces stateful authentication: `auth login` (browser/implicit), `auth logout`, `auth client` (client_credentials/password), `auth client renew`, and `auth client token`. Sessions are stored as a JSON file in the CLI data directory; when a valid session exists, all OAuth commands use it automatically without requiring credentials on every invocation.
7+
8+
**Note:** Sessions are not shared with `sfcc-ci`. Re-authenticate with `b2c auth login` or `b2c auth client` after upgrading. Existing stateless auth (env vars, `dw.json`) is unaffected.

docs/cli/auth.md

Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,163 @@ description: Authentication commands for obtaining OAuth tokens and configuring
66

77
Commands for authentication and token management.
88

9+
## Stateful vs stateless auth
10+
11+
The CLI supports **stateful auth** (session stored on disk) in addition to **stateless auth** (client credentials or one-off implicit flow):
12+
13+
- **Stateful (browser)**: After you run `b2c auth login`, your token is stored on disk in the CLI data directory. Subsequent commands (e.g. `b2c auth token`, `b2c am orgs list`) use this token when it is present and valid. If the token is missing or expired, the CLI falls back to stateless auth.
14+
- **Stateful (client credentials)**: Use `b2c auth client` to authenticate with client ID and secret (or user/password) for non-interactive/automation use. Supports auto-renewal with `--renew`.
15+
- **Stateless**: You provide `--client-id` (and optionally `--client-secret`) per run or via environment/config; no session is persisted.
16+
17+
The stored session is used only when the token is valid and no explicit stateless auth flags are provided. The CLI falls back to stateless auth when the stored token is expired/invalid, or when `--client-secret`, `--user-auth`, or `--auth-methods` are passed on the command line. In both cases a warning is shown explaining why stateful auth was skipped. Note that `--client-id` alone does not force stateless; the stored session is used if the client ID matches. To opt out of stateful auth entirely, run `b2c auth logout` to clear the stored session.
18+
19+
Use **auth:logout** to clear the stored session and return to stateless-only behavior.
20+
21+
## b2c auth login
22+
23+
Log in via browser (implicit OAuth) and save the session for stateful auth.
24+
25+
### Usage
26+
27+
```bash
28+
b2c auth login [CLIENTID]
29+
```
30+
31+
`CLIENTID` is an optional positional argument. When omitted, the `SFCC_CLIENT_ID` environment variable is used as a fallback.
32+
33+
```bash
34+
# Using a positional argument
35+
b2c auth login your-client-id
36+
37+
# Using environment variable
38+
export SFCC_CLIENT_ID=your-client-id
39+
b2c auth login
40+
```
41+
42+
After a successful login, subsequent commands use the stored token until it expires or you run `b2c auth logout`.
43+
44+
## b2c auth logout
45+
46+
Clear the stored OAuth session (stateful auth). After logout, commands use stateless auth when configured.
47+
48+
```bash
49+
b2c auth logout
50+
```
51+
52+
## b2c auth client
53+
54+
Authenticate an API client using client credentials or resource owner password credentials and save the session for stateful auth. Compatible with the [sfcc-ci `client:auth`](https://github.com/SalesforceCommerceCloud/sfcc-ci) workflow.
55+
56+
This is the non-interactive alternative to `auth login` — ideal for CI/CD pipelines and automation.
57+
58+
### Usage
59+
60+
```bash
61+
# Client credentials grant (client ID + secret)
62+
b2c auth client --client-id <id> --client-secret <secret>
63+
64+
# With auto-renewal enabled
65+
b2c auth client --client-id <id> --client-secret <secret> --renew
66+
67+
# Resource owner password credentials grant (+ user credentials)
68+
b2c auth client --client-id <id> --client-secret <secret> --user <email> --user-password <pwd>
69+
70+
# Force a specific grant type
71+
b2c auth client --client-id <id> --client-secret <secret> --grant-type client_credentials
72+
```
73+
74+
### Flags
75+
76+
| Flag | Environment Variable | Description |
77+
|------|---------------------|-------------|
78+
| `--client-id` | `SFCC_CLIENT_ID` | Client ID (required) |
79+
| `--client-secret` | `SFCC_CLIENT_SECRET` | Client secret (required) |
80+
| `--renew` / `-r` | | Enable auto-renewal (stores credentials for `auth client renew`) |
81+
| `--grant-type` / `-t` | | Force grant type: `client_credentials` or `password` |
82+
| `--user` | `SFCC_OAUTH_USER_NAME` | Username for password grant |
83+
| `--user-password` | `SFCC_OAUTH_USER_PASSWORD` | Password for password grant |
84+
| `--auth-scope` | `SFCC_OAUTH_SCOPES` | OAuth scopes to request |
85+
| `--account-manager-host` | `SFCC_ACCOUNT_MANAGER_HOST` | Account Manager hostname |
86+
87+
### Grant type auto-detection
88+
89+
If `--grant-type` is not specified:
90+
- **client_credentials** is used when only `--client-id` and `--client-secret` are provided
91+
- **password** is used when `--user` and `--user-password` are also provided
92+
93+
### Examples
94+
95+
```bash
96+
# Authenticate for automation (CI/CD)
97+
export SFCC_CLIENT_ID=my-client
98+
export SFCC_CLIENT_SECRET=my-secret
99+
b2c auth client
100+
101+
# Authenticate with auto-renewal for long-running scripts
102+
b2c auth client --client-id <id> --client-secret <secret> --renew
103+
104+
# Authenticate with user credentials
105+
b2c auth client --client-id <id> --client-secret <secret> \
106+
--user admin@example.com --user-password secret123
107+
```
108+
109+
## b2c auth client renew
110+
111+
Renew the authentication token using stored credentials. Requires initial authentication with `--renew` flag.
112+
113+
Uses `refresh_token` grant when a refresh token is stored, otherwise falls back to `client_credentials` grant.
114+
115+
### Usage
116+
117+
```bash
118+
b2c auth client renew
119+
```
120+
121+
### Example
122+
123+
```bash
124+
# Initial auth with --renew
125+
b2c auth client --client-id <id> --client-secret <secret> --renew
126+
127+
# Later, renew the token without re-entering credentials
128+
b2c auth client renew
129+
```
130+
131+
## b2c auth client token
132+
133+
Return the current stored authentication token. Compatible with the [sfcc-ci `client:auth:token`](https://github.com/SalesforceCommerceCloud/sfcc-ci) workflow.
134+
135+
### Usage
136+
137+
```bash
138+
# Raw token to stdout (pipe-friendly)
139+
b2c auth client token
140+
141+
# Full metadata as JSON
142+
b2c auth client token --json
143+
```
144+
145+
### Output
146+
147+
Raw token output (default):
148+
149+
```
150+
eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...
151+
```
152+
153+
JSON output (`--json`):
154+
155+
```json
156+
{
157+
"accessToken": "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9...",
158+
"clientId": "my-client-id",
159+
"expires": "2025-01-27T12:00:00.000Z",
160+
"scopes": ["mail", "roles"],
161+
"user": "admin@example.com",
162+
"renewable": true
163+
}
164+
```
165+
9166
## b2c auth token
10167

11168
Get an OAuth access token for use in scripts or other tools.

docs/guide/authentication.md

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,17 +36,31 @@ Most CLI operations require an Account Manager API Client. This is configured in
3636

3737
### Authentication Methods
3838

39-
The CLI supports two authentication methods:
39+
The CLI supports four authentication methods:
4040

41-
| Method | When Used | Role Configuration |
42-
| ----------------------- | -------------------------------------------------------------------------------- | ----------------------------------------- |
43-
| **User Authentication** | When `--user-auth` is passed, or when only `--client-id` is provided (no secret) | Roles configured on your **user account** |
44-
| **Client Credentials** | When both `--client-id` and `--client-secret` are provided | Roles configured on the **API client** |
41+
| Method | When Used | Role Configuration |
42+
| ---------------------------------- | ---------------------------------------------------------------------------------------------- | ----------------------------------------- |
43+
| **User Authentication** | When `--user-auth` is passed, or when only a client ID is provided (no secret) | Roles configured on your **user account** |
44+
| **Client Credentials** | When both `--client-id` and `--client-secret` are provided | Roles configured on the **API client** |
45+
| **Stateful User Authentication** | After running `b2c auth login` — browser-based login, token stored and reused | Roles configured on your **user account** |
46+
| **Stateful Client Authentication** | After running `b2c auth client` — client credentials login, token stored and reused | Roles configured on the **API client** |
4547

4648
**User Authentication** opens a browser for interactive login and uses roles assigned to your user account. This is ideal for development and manual operations. Use `--user-auth` as a shorthand for `--auth-methods implicit` on any OAuth command.
4749

4850
**Client Credentials** uses the API client's secret for non-interactive authentication. This is ideal for CI/CD pipelines and automation.
4951

52+
**Stateful User Auth** uses `b2c auth login` to open a browser for interactive login once, then stores the session on disk. Subsequent commands automatically use the stored token when it is present and valid, without re-opening the browser. Clear the session with `b2c auth logout`. See [Auth Commands](/cli/auth#b2c-auth-login) for details.
53+
54+
**Stateful Client Auth** uses `b2c auth client` to authenticate once with client credentials (or user/password), store the session, and reuse it across subsequent commands without passing credentials each time. Mirrors the [sfcc-ci](https://github.com/SalesforceCommerceCloud/sfcc-ci) `client:auth` workflow. Use `--renew` to enable automatic token renewal via `b2c auth client renew`. See [Auth Commands](/cli/auth#b2c-auth-client) for details.
55+
56+
::: warning Stateful vs Stateless Precedence
57+
The stored session is used only when the token is valid **and** no explicit auth flags are provided. The CLI falls back to stateless auth when:
58+
- The stored token is **expired or invalid** — a warning suggests `b2c auth client renew` (if renewable) or `b2c auth client` / `b2c auth login` to re-authenticate.
59+
- **Explicit stateless auth flags** are passed (`--client-secret`, `--user-auth`, or `--auth-methods`) — a warning lists the flags that triggered the override. Remove them to use the stored session. Note that `--client-id` alone does not force stateless; the stored session is used if the client ID matches.
60+
61+
To opt out of stateful auth entirely, run `b2c auth logout` to clear the stored session. The CLI will then use stateless auth exclusively.
62+
:::
63+
5064
::: tip
5165
For Account Manager operations that require user-level roles (organization and API client management), use `--user-auth` to authenticate with your user account. See [Account Manager Authentication](/cli/account-manager#authentication) for per-subtopic role requirements.
5266
:::

0 commit comments

Comments
 (0)