You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: .claude/skills/api-client-development/SKILL.md
+11-1Lines changed: 11 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
---
2
2
name: api-client-development
3
-
description: Creating API clients with OpenAPI specs, authentication, and OAuth scopes for SCAPI and similar APIs
3
+
description: Creating typed API clients with OpenAPI specs, authentication, and OAuth scopes for SCAPI and similar APIs. Use when adding a new SCAPI client, generating types from an OpenAPI spec, setting up OAuth middleware, or integrating a new Commerce API endpoint.
**OAuth scope errors (401/403 from SCAPI)**: Ensure the client factory calls `auth.withAdditionalScopes()` with both the domain scope (e.g., `sfcc.custom-apis`) and the tenant-specific scope (`SALESFORCE_COMMERCE_API:<tenantId>`). Use `buildTenantScope()` to strip the `f_ecom_` prefix from tenant IDs before building scopes.
444
+
445
+
**Type generation failures**: Check that the OpenAPI spec in `specs/` is valid YAML/JSON. Run `pnpm --filter @salesforce/b2c-tooling-sdk run generate:types` and inspect the output. Common issues: spec references external files that aren't present, or uses OpenAPI features not supported by openapi-typescript.
446
+
447
+
**Middleware ordering issues**: Auth middleware should be added first (`client.use(createAuthMiddleware(...))`), then logging. In openapi-fetch, middleware runs in reverse registration order for requests, so auth registered first means it runs last — ensuring the logging middleware sees the final request with auth headers.
448
+
449
+
**`organizationId` mismatch**: SCAPI path parameters need the `f_ecom_` prefix (use `toOrganizationId()`), while OAuth scopes need the raw tenant ID (use `toTenantId()`). Mixing these up causes 404s or scope errors.
Copy file name to clipboardExpand all lines: .claude/skills/cli-command-development/SKILL.md
+11-1Lines changed: 11 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
---
2
2
name: cli-command-development
3
-
description: Creating new CLI commands and topics for the B2C CLI using oclif
3
+
description: Creating new CLI commands and topics for the B2C CLI using oclif. Use when adding a new command, creating a topic, adding flags or arguments, implementing table output, or extending BaseCommand/OAuthCommand/InstanceCommand.
4
4
metadata:
5
5
internal: true
6
6
---
@@ -323,6 +323,16 @@ if (error) {
323
323
324
324
See [API Client Development](../api-client-development/SKILL.md#error-handling) for supported error patterns.
325
325
326
+
## Troubleshooting
327
+
328
+
**Command not found after creating file**: Ensure the file is in the correct `packages/b2c-cli/src/commands/` subdirectory matching the intended command path. Run `pnpm --filter @salesforce/b2c-cli run build` to regenerate the oclif manifest. For new topics, add the topic to `package.json` under `oclif.topics`.
329
+
330
+
**Flag parsing errors**: Check that flag names use kebab-case in the `static flags` definition. The `char` shorthand must be a single character. If using `dependsOn`, the referenced flag must exist in the same command's flags.
331
+
332
+
**Missing i18n keys**: The `t()` function falls back to the default string (second argument), so missing keys won't crash at runtime. However, keep key paths consistent with the `commands.<topic>.<command>.<key>` pattern for future localization.
333
+
334
+
**"requireX" methods not available**: Verify the command extends the correct base class. `requireServer()` is on `InstanceCommand`, `requireOAuthCredentials()` is on `OAuthCommand`, `requireMrtCredentials()` is on `MrtCommand`. Check the class hierarchy if a method is missing.
335
+
326
336
## Creating a Command Checklist
327
337
328
338
1. Create file at `packages/b2c-cli/src/commands/<topic>/<command>.ts`
Copy file name to clipboardExpand all lines: .claude/skills/documentation/SKILL.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
---
2
2
name: documentation
3
-
description: Updating user guides, CLI reference, and API documentation for the B2C CLI project
3
+
description: Updating user guides, CLI reference, and API documentation for the B2C CLI project. Use when adding or changing CLI command docs, writing JSDoc for TypeDoc generation, updating Vitepress sidebar config, or creating new guide pages.
Copy file name to clipboardExpand all lines: .claude/skills/sdk-module-development/SKILL.md
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
---
2
2
name: sdk-module-development
3
-
description: Adding new modules and exports to the @salesforce/b2c-tooling-sdk package
3
+
description: Adding new modules and exports to the @salesforce/b2c-tooling-sdk package. Use when creating a new SDK module, adding barrel file exports, configuring package.json exports, or building client factory functions.
Copy file name to clipboardExpand all lines: .claude/skills/testing/SKILL.md
+10-85Lines changed: 10 additions & 85 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
---
2
2
name: testing
3
-
description: Writing tests for the B2C CLI project using Mocha, Chai, and MSW
3
+
description: Writing tests for the B2C CLI project using Mocha, Chai, and MSW. Use when writing unit or integration tests, mocking HTTP requests with MSW, testing CLI commands with oclif, isolating config in tests, or setting up test coverage.
Use `@oclif/test`'s `runCommand()` for integration-style tests:
444
-
445
-
```typescript
446
-
import { runCommand } from'@oclif/test';
447
-
import { expect } from'chai';
448
-
449
-
describe('ods list', () => {
450
-
it('runs without errors', async () => {
451
-
const { error } =awaitrunCommand('ods list --help');
452
-
expect(error).to.be.undefined;
453
-
});
454
-
});
455
-
```
456
-
457
-
### SDK Base Command Integration Tests
458
-
459
-
The SDK includes a test fixture at `test/fixtures/test-cli/` for integration testing base command behavior. See `test/cli/base-command.integration.test.ts` for examples.
460
-
461
-
### When to Use Each Approach
462
-
463
-
| Approach | Use For |
464
-
|----------|---------|
465
-
| Unit tests with `stubParse`| Testing protected method logic in isolation |
466
-
| Integration tests with fixture | Testing full command lifecycle, flag parsing |
467
-
|`runCommand()` in b2c-cli | Testing actual CLI commands |
468
-
469
-
## E2E Tests
470
-
471
-
E2E tests run against real infrastructure and are skipped without credentials:
See [CLI Command Testing Patterns](./references/CLI-COMMAND-TESTING.md) for integration tests with `runCommand`, SDK base command fixture tests, E2E test patterns, and when to use each approach.
**MSW handler not matching requests**: Verify the URL pattern in `http.get()`/`http.post()` matches the full URL including base path. Use `onUnhandledRequest: 'error'` in `server.listen()` to surface unmatched requests. Check that the HTTP method matches (e.g., `http.all()` for WebDAV methods like MKCOL/PROPFIND).
529
459
530
-
| Helper | Purpose |
531
-
|--------|---------|
532
-
|`MockAuthStrategy`| Mock authentication for API clients |
|`createNullStream()`| Create a writable stream that discards output |
535
-
|`CapturingStream`| Writable stream that captures output for assertions |
460
+
**Config or env vars leaking between tests**: Always pair `isolateConfig()` with `restoreConfig()` in `beforeEach`/`afterEach`. Missing `restoreConfig()` causes subsequent tests to run with cleared env vars. Use `sinon.restore()` in `afterEach` to clean up all stubs.
536
461
537
-
### SDK Test Utils (exported from package)
462
+
**Import path errors ("module not found")**: Use package exports (`@salesforce/b2c-tooling-sdk/clients`) not relative paths. If a new export was added, ensure it's in `package.json``exports` with the `development` condition pointing to the `.ts` source file.
**Fake timers break MSW**: MSW v2 uses microtasks internally. Never use `@sinonjs/fake-timers` or `sinon.useFakeTimers()` in tests that use MSW. Use `pollInterval: 10` for fast polling tests instead.
465
+
466
+
**Test output is noisy**: Use `runSilent()` to suppress stdout/stderr from commands. The `stubParse` helper automatically sets `'log-level': 'silent'` to quiet pino logger output.
Use `@oclif/test`'s `runCommand()` for integration-style tests:
8
+
9
+
```typescript
10
+
import { runCommand } from'@oclif/test';
11
+
import { expect } from'chai';
12
+
13
+
describe('ods list', () => {
14
+
it('runs without errors', async () => {
15
+
const { error } =awaitrunCommand('ods list --help');
16
+
expect(error).to.be.undefined;
17
+
});
18
+
});
19
+
```
20
+
21
+
### SDK Base Command Integration Tests
22
+
23
+
The SDK includes a test fixture at `test/fixtures/test-cli/` for integration testing base command behavior. See `test/cli/base-command.integration.test.ts` for examples.
24
+
25
+
### When to Use Each Approach
26
+
27
+
| Approach | Use For |
28
+
|----------|---------|
29
+
| Unit tests with `stubParse`| Testing protected method logic in isolation |
30
+
| Integration tests with fixture | Testing full command lifecycle, flag parsing |
31
+
|`runCommand()` in b2c-cli | Testing actual CLI commands |
32
+
33
+
## E2E Tests
34
+
35
+
E2E tests run against real infrastructure and are skipped without credentials:
0 commit comments