feat: initial @launchdarkly/setup quickstart wizard#1
Conversation
Co-authored-by: Lindsey Bieda <lbieda@gmail.com>
ari-launchdarkly
left a comment
There was a problem hiding this comment.
Kids are awake, I'll keep reviewing when I'm back online
| | ------------------------------------- | --------- | ----------------------------------------------- | | ||
| | `package.json` + `next` dep | Next.js | `@launchdarkly/node-server-sdk` | | ||
| | `package.json` + `react` dep | React | `@launchdarkly/react-client-sdk` | | ||
| | `package.json` (other) | Node.js | `@launchdarkly/node-server-sdk` | |
There was a problem hiding this comment.
This is pretty brittle. We have a js client that would fit for package.json client apps, whereas the node-server-sdk would fit for server ones. (We also have a node-client-sdk but i've yet to see a use case for that one)
|
|
||
| ## Supported stacks | ||
|
|
||
| | Detected by | Framework | SDK installed | |
|
|
||
| ### Blocking for a production release | ||
|
|
||
| - [ ] **Verify `/internal/usage/sdk-active` endpoint** — the SDK connection polling step uses this internal LD endpoint. Confirm the exact path, query parameters, and auth requirements with the LD API team before release. It may need to be replaced with a public endpoint or a different detection strategy. |
There was a problem hiding this comment.
We can use the /api/v2/projects/{projectKey}/environments/{environmentKey}/sdk-active since that's a public-facing endpoint we should be able to hit. It should handle auth correctly and isn't internal. It was ported over so that the CLI and MCP could make direct requests. The sdk_name cna help us scope it down to the specific SDK
Added `GET /api/v2/projects/{projectKey}/environments/{environmentKey}/sdk-active` (Account usage beta) endpoint. It returns whether LaunchDarkly has recorded an SDK diagnostic initialization event for the environment. Optional query parameters `sdk_name` and `sdk_wrapper_name` apply when time-bounded diagnostic queries are enabled for the account.
| - [ ] **Verify `/internal/usage/sdk-active` endpoint** — the SDK connection polling step uses this internal LD endpoint. Confirm the exact path, query parameters, and auth requirements with the LD API team before release. It may need to be replaced with a public endpoint or a different detection strategy. | |
| - [ ] **Verify `/api/v2/projects/{projectKey}/environments/{environmentKey}/sdk-active`** — the SDK connection polling step uses this internal LD endpoint. Confirm the exact path, query parameters, and auth requirements with the LD API team before release. It may need to be replaced with a public endpoint or a different detection strategy. |
| ### Blocking for a production release | ||
|
|
||
| - [ ] **Verify `/internal/usage/sdk-active` endpoint** — the SDK connection polling step uses this internal LD endpoint. Confirm the exact path, query parameters, and auth requirements with the LD API team before release. It may need to be replaced with a public endpoint or a different detection strategy. | ||
| - [ ] **`@launchdarkly` npm org access** — coordinate with DevRel or the platform team to get publishing rights to the `@launchdarkly` npm org. Alternatively, publish under `@launchdarkly-labs/setup` for an initial release and rename later. |
There was a problem hiding this comment.
Didn't we get the terraform PR to create the repo?
|
|
||
| - [ ] **Verify `/internal/usage/sdk-active` endpoint** — the SDK connection polling step uses this internal LD endpoint. Confirm the exact path, query parameters, and auth requirements with the LD API team before release. It may need to be replaced with a public endpoint or a different detection strategy. | ||
| - [ ] **`@launchdarkly` npm org access** — coordinate with DevRel or the platform team to get publishing rights to the `@launchdarkly` npm org. Alternatively, publish under `@launchdarkly-labs/setup` for an initial release and rename later. | ||
| - [ ] **Discoverability** — the command needs to be surfaced somewhere users will actually see it (LD SDK setup page, docs quickstart pages, welcome email). The tool has no value if nobody knows to run it. Coordinate with DevRel/Docs before launch. |
There was a problem hiding this comment.
The marketing site might be a good place to set it too
| export LD_API_TOKEN=api-... | ||
| npx @launchdarkly/setup |
There was a problem hiding this comment.
Slight difference, but would we want to have the user append the LD_API_TOKEN to the command as an environment variable? So something like:
```npx @launchdarkly/setup LD_API_TOKEN=api-....`
| `You need a LaunchDarkly API token with ${chalk.bold('Admin')} or ${chalk.bold('Writer')} permissions.`, | ||
| ); | ||
| p.log.info( | ||
| `Create one at: ${chalk.cyan('https://app.launchdarkly.com/settings/authorization')}`, |
There was a problem hiding this comment.
We might want to point them directly to the creation flow:
| `Create one at: ${chalk.cyan('https://app.launchdarkly.com/settings/authorization')}`, | |
| `Create one at: ${chalk.cyan('https://app.launchdarkly.com/settings/authorization/tokens/new')}`, |
But just thinking out loud, I'm not sure if our federal or EU instance is the same URL?
| // Offer to save token for future runs | ||
| if (!stored) { | ||
| const save = await p.confirm({ | ||
| message: 'Save token to ~/.config/launchdarkly/credentials for future runs?', |
There was a problem hiding this comment.
I'm curious what the advantage of this is from a user perspective? Given that these access tokens can be used for many things, I'd be concerned that this could create a security vulnerability (or provide agents with an avenue to perform actions without proper guardrails)
| @@ -0,0 +1,154 @@ | |||
| const LD_API_BASE = 'https://app.launchdarkly.com'; | |||
There was a problem hiding this comment.
This is for most cases, but not for EU or federal
| environments: Record<string, { on: boolean }>; | ||
| } | ||
|
|
||
| export class LDApiClient { |
There was a problem hiding this comment.
Random question - it seems like we're recreating a trimmed down version of the LDCLI, i wonder if we can just utilize that under the hood and use the api-token as the basis for authenticating the LDCLI?

Summary
Implements
npx @launchdarkly/setup— a terminal-native wizard that connects any project to LaunchDarkly in a single command, without leaving the terminal.LD_API_TOKENenv var, saved credentials, or interactive promptclaudeCLI (if available) to suggest how to run the app during connection verificationWhat's included
Core
src/index.ts— wizard orchestrator (7-step flow)src/api.ts—LDApiClientwrapping native fetch (projects, environments, flags, SDK-active polling)src/detect.ts— filesystem-based framework detectionsrc/sdks.ts— SDK definitions with install commands and init/eval code snippets for 6 frameworkssrc/credentials.ts— token persistence at~/.config/launchdarkly/credentials.jsonSteps
src/steps/authenticate.ts— API token auth with retry on failuresrc/steps/select-project.ts— project + environment selection/creationsrc/steps/install-sdk.ts— package install via execasrc/steps/inject-sdk.ts— code injection into entry point with colored diff previewsrc/steps/create-flag.ts— boolean flag creationsrc/steps/detect-run-cmd.ts— LLM-assisted run command detectionsrc/steps/verify-connection.ts— polls/internal/usage/sdk-activeevery 3s (2 min timeout)Tooling
Test plan
npm run typecheck— zero type errorsnpm run lint— zero errors/warningsnpm run format:check— all files formattednpm test— 75/75 tests passnpm run dev— wizard launches and walks through interactive flow