Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/commands-update-order-explore.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"clerk": patch
---

Show the "+ Create a new application" option first in the interactive application picker used by `clerk link` and `clerk users`.
Comment on lines +1 to +5

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Include clerk init in the release note.

The shared picker change also affects clerk init, but the changeset currently mentions only clerk link and clerk users. Add clerk init so the patch note covers every affected CLI flow.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In @.changeset/commands-update-order-explore.md around lines 1 - 5, Update the
changeset description to include clerk init alongside clerk link and clerk
users, since the shared application picker change affects all three CLI flows.

23 changes: 14 additions & 9 deletions packages/cli-core/src/commands/link/index.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -434,7 +434,7 @@ describe("link", () => {
expect(mockFetchApplication).not.toHaveBeenCalled();
});

test("source returns all choices plus create option when term is empty", async () => {
test("source returns create option first, then all choices, when term is empty", async () => {
mockIsAgent.mockReturnValue(false);
mockGetToken.mockResolvedValue("token");
mockListApplications.mockResolvedValue([
Expand All @@ -454,9 +454,14 @@ describe("link", () => {
},
]);
mockSearch.mockImplementation(
async (config: { source: (term: string | undefined) => unknown[] }) => {
async (config: {
source: (term: string | undefined) => { name: string; value: string }[];
}) => {
const results = config.source(undefined);
expect(results).toHaveLength(3); // 2 apps + create option
expect(results).toHaveLength(3); // create option + 2 apps
expect(results[0]!.value).toBe("__create_new__");
expect(results[1]!.value).toBe("app_a");
expect(results[2]!.value).toBe("app_b");
return "app_a";
},
);
Expand Down Expand Up @@ -489,9 +494,9 @@ describe("link", () => {
source: (term: string | undefined) => { name: string; value: string }[];
}) => {
const results = config.source("my");
expect(results).toHaveLength(2); // 1 match + create option
expect(results[0]!.value).toBe("app_a");
expect(results[1]!.value).toBe("__create_new__");
expect(results).toHaveLength(2); // create option + 1 match
expect(results[0]!.value).toBe("__create_new__");
expect(results[1]!.value).toBe("app_a");

const noMatch = config.source("zzz");
expect(noMatch).toHaveLength(1); // only create option
Expand Down Expand Up @@ -528,9 +533,9 @@ describe("link", () => {
source: (term: string | undefined) => { name: string; value: string }[];
}) => {
const results = config.source("abc");
expect(results).toHaveLength(2); // 1 match + create option
expect(results[0]!.value).toBe("app_abc");
expect(results[1]!.value).toBe("__create_new__");
expect(results).toHaveLength(2); // create option + 1 match
expect(results[0]!.value).toBe("__create_new__");
expect(results[1]!.value).toBe("app_abc");
return "app_abc";
},
);
Expand Down
2 changes: 1 addition & 1 deletion packages/cli-core/src/lib/app-picker.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ export async function pickOrCreateApp(opts: {
const filtered = term
? appChoices.filter((c) => c.name.toLowerCase().includes(term.toLowerCase()))
: appChoices;
return [...filtered, createChoice];
return [createChoice, ...filtered];
},
});

Expand Down