Skip to content
Open
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
100 changes: 1 addition & 99 deletions src/index.ts
Original file line number Diff line number Diff line change
@@ -1,18 +1,15 @@
import { LinearClient, LinearClientOptions } from "@linear/sdk";
import { commitExists, getCommitContextsBetweenShas, getCurrentGitInfo, getRepoInfo } from "./git";
import { extractLinearIssueIdentifiersForCommit, extractPullRequestNumbersForCommit } from "./extractors";
import { scanCommits } from "./scan";
import {
Release,
AccessKeyLatestReleaseResponse,
AccessKeyPipelineSettingsResponse,
AccessKeySyncReleaseResponse,
AccessKeyCompleteReleaseResponse,
AccessKeyUpdateByPipelineResponse,
CommitContext,
DebugSink,
IssueReference,
IssueSource,
PullRequestSource,
RepoInfo,
} from "./types";
import { getCLIWarnings, parseCLIArgs } from "./args";
Expand Down Expand Up @@ -122,101 +119,6 @@ async function apiRequest<T>(query: string, variables?: Record<string, unknown>)
return withRetry(() => linearClient.client.rawRequest(query, variables)) as Promise<T>;
}

function scanCommits(
commits: CommitContext[],
includePaths: string[] | null,
): {
issueReferences: IssueReference[];
prNumbers: number[];
debugSink: DebugSink;
} {
const seen = new Map<string, IssueReference>();
const prNumbersSet = new Set<number>();
const debugSink: DebugSink = {
inspectedShas: [],
issues: {},
pullRequests: [],
includePaths,
};

for (const commit of commits) {
debugSink.inspectedShas.push(commit.sha);

const fromBranch = extractLinearIssueIdentifiersForCommit({
sha: commit.sha,
branchName: commit.branchName,
message: null,
});

for (const key of fromBranch) {
if (!debugSink.issues[key]) {
debugSink.issues[key] = [];
}

const source: IssueSource = {
sha: commit.sha,
source: "branch_name",
value: commit.branchName ?? "",
};
debugSink.issues[key].push(source);

if (seen.has(key)) {
continue;
}

seen.set(key, { identifier: key, commitSha: commit.sha });
log(`Detected issue key ${key} from branch name "${commit.branchName ?? ""}"`);
}

const fromMessage = extractLinearIssueIdentifiersForCommit({
sha: commit.sha,
branchName: null,
message: commit.message,
});

for (const key of fromMessage) {
if (!debugSink.issues[key]) {
debugSink.issues[key] = [];
}

const source: IssueSource = {
sha: commit.sha,
source: "commit_message",
value: commit.message ?? "",
};
debugSink.issues[key].push(source);

if (seen.has(key)) {
continue;
}

seen.set(key, { identifier: key, commitSha: commit.sha });
log(`Detected issue key ${key} from commit message "${commit.message ?? ""}"`);
}

// Extract PR numbers from commit message
const prNumbers = extractPullRequestNumbersForCommit(commit);
for (const prNumber of prNumbers) {
if (!prNumbersSet.has(prNumber)) {
prNumbersSet.add(prNumber);
const prSource: PullRequestSource = {
sha: commit.sha,
number: prNumber,
value: commit.message ?? "",
};
debugSink.pullRequests.push(prSource);
log(`Found pull request number ${prNumber} in commit ${commit.sha}`);
}
}
}

return {
issueReferences: Array.from(seen.values()),
prNumbers: Array.from(prNumbersSet),
debugSink,
};
}

async function syncCommand(): Promise<{
release: { id: string; name: string; version?: string; url?: string };
} | null> {
Expand Down
96 changes: 96 additions & 0 deletions src/scan.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
import { extractLinearIssueIdentifiersForCommit, extractPullRequestNumbersForCommit } from "./extractors";
import { log } from "./log";
import { CommitContext, DebugSink, IssueReference, IssueSource, PullRequestSource } from "./types";

export function scanCommits(
commits: CommitContext[],
includePaths: string[] | null,
): {
issueReferences: IssueReference[];
prNumbers: number[];
debugSink: DebugSink;
} {
const seen = new Map<string, IssueReference>();
const prNumbersSet = new Set<number>();
const debugSink: DebugSink = {
inspectedShas: [],
issues: {},
pullRequests: [],
includePaths,
};

for (const commit of commits) {
debugSink.inspectedShas.push(commit.sha);

const fromBranch = extractLinearIssueIdentifiersForCommit({
sha: commit.sha,
branchName: commit.branchName,
message: null,
});

for (const key of fromBranch) {
if (!debugSink.issues[key]) {
debugSink.issues[key] = [];
}

const source: IssueSource = {
sha: commit.sha,
source: "branch_name",
value: commit.branchName ?? "",
};
debugSink.issues[key].push(source);

if (seen.has(key)) {
continue;
}

seen.set(key, { identifier: key, commitSha: commit.sha });
log(`Detected issue key ${key} from branch name "${commit.branchName ?? ""}"`);
}

const fromMessage = extractLinearIssueIdentifiersForCommit({
sha: commit.sha,
branchName: null,
message: commit.message,
});

for (const key of fromMessage) {
if (!debugSink.issues[key]) {
debugSink.issues[key] = [];
}

const source: IssueSource = {
sha: commit.sha,
source: "commit_message",
value: commit.message ?? "",
};
debugSink.issues[key].push(source);

if (seen.has(key)) {
continue;
}

seen.set(key, { identifier: key, commitSha: commit.sha });
log(`Detected issue key ${key} from commit message "${commit.message ?? ""}"`);
}

for (const prNumber of extractPullRequestNumbersForCommit(commit)) {
if (!prNumbersSet.has(prNumber)) {
prNumbersSet.add(prNumber);
const prSource: PullRequestSource = {
sha: commit.sha,
number: prNumber,
value: commit.message ?? "",
};
debugSink.pullRequests.push(prSource);
log(`Found pull request number ${prNumber} in commit ${commit.sha}`);
}
}
}

return {
issueReferences: Array.from(seen.values()),
prNumbers: Array.from(prNumbersSet),
debugSink,
};
}