From 80a688cba23de86c8f471272fb7967c57dea745d Mon Sep 17 00:00:00 2001 From: Peter Schilling Date: Tue, 17 Mar 2026 16:57:50 -0700 Subject: [PATCH 1/2] feat: add --label filter to issue list --- src/commands/issue/issue-list.ts | 11 +++ src/utils/linear.ts | 13 ++++ .../__snapshots__/issue-list.test.ts.snap | 10 +++ test/commands/issue/issue-list.test.ts | 67 ++++++++++++++++++- 4 files changed, 100 insertions(+), 1 deletion(-) diff --git a/src/commands/issue/issue-list.ts b/src/commands/issue/issue-list.ts index 841bfcc5..aa71e289 100644 --- a/src/commands/issue/issue-list.ts +++ b/src/commands/issue/issue-list.ts @@ -90,6 +90,11 @@ export const listCommand = new Command() "--milestone ", "Filter by project milestone name (requires --project)", ) + .option( + "-l, --label ", + "Filter by label name (can be repeated for multiple labels)", + { collect: true }, + ) .option( "--limit ", "Maximum number of issues to fetch (default: 50, use 0 for unlimited)", @@ -115,6 +120,7 @@ export const listCommand = new Command() project, cycle, milestone, + label: labels, limit, pager, }, @@ -205,6 +211,10 @@ export const listCommand = new Command() milestoneId = await getMilestoneIdByName(milestone, projectId) } + const labelNames = labels && labels.length > 0 + ? labels.flat() + : undefined + const { Spinner } = await import("@std/cli/unstable-spinner") const showSpinner = shouldShowSpinner() const spinner = showSpinner ? new Spinner() : null @@ -221,6 +231,7 @@ export const listCommand = new Command() sort, cycleId, milestoneId, + labelNames, ) spinner?.stop() const issues = result.issues?.nodes || [] diff --git a/src/utils/linear.ts b/src/utils/linear.ts index cd4d2c0c..6020fe7f 100644 --- a/src/utils/linear.ts +++ b/src/utils/linear.ts @@ -422,6 +422,7 @@ export async function fetchIssuesForState( sortParam?: "manual" | "priority", cycleId?: string, milestoneId?: string, + labelNames?: string[], ) { const sort = sortParam ?? getOption("issue_sort") as "manual" | "priority" | undefined @@ -469,6 +470,18 @@ export async function fetchIssuesForState( filter.projectMilestone = { id: { eq: milestoneId } } } + if (labelNames && labelNames.length > 0) { + if (labelNames.length === 1) { + filter.labels = { some: { name: { eqIgnoreCase: labelNames[0] } } } + } else { + filter.labels = { + and: labelNames.map((name) => ({ + some: { name: { eqIgnoreCase: name } }, + })), + } + } + } + const query = gql(/* GraphQL */ ` query GetIssuesForState($sort: [IssueSortInput!], $filter: IssueFilter!, $first: Int, $after: String) { issues(filter: $filter, sort: $sort, first: $first, after: $after) { diff --git a/test/commands/issue/__snapshots__/issue-list.test.ts.snap b/test/commands/issue/__snapshots__/issue-list.test.ts.snap index 68b208a7..c67ce75d 100644 --- a/test/commands/issue/__snapshots__/issue-list.test.ts.snap +++ b/test/commands/issue/__snapshots__/issue-list.test.ts.snap @@ -23,6 +23,7 @@ Options: --project - Filter by project name --cycle - Filter by cycle name, number, or 'active' --milestone - Filter by project milestone name (requires --project) + -l, --label