196 lines
5.2 KiB
TypeScript
196 lines
5.2 KiB
TypeScript
import { tool } from "@opencode-ai/plugin";
|
|
import { $ } from "bun";
|
|
|
|
export const issueList = tool({
|
|
description:
|
|
"List issues with filters for state, labels, assignee, milestone, and author",
|
|
args: {
|
|
state: tool.schema
|
|
.enum(["open", "closed", "all"])
|
|
.default("open")
|
|
.describe("Filter by state"),
|
|
labels: tool.schema
|
|
.string()
|
|
.optional()
|
|
.describe("Comma-separated list of labels to match"),
|
|
assignee: tool.schema
|
|
.string()
|
|
.optional()
|
|
.describe("Filter by assignee username"),
|
|
milestone: tool.schema
|
|
.string()
|
|
.optional()
|
|
.describe("Filter by milestone name"),
|
|
author: tool.schema
|
|
.string()
|
|
.optional()
|
|
.describe("Filter by author username"),
|
|
limit: tool.schema
|
|
.number()
|
|
.default(30)
|
|
.describe("Number of issues to return"),
|
|
keyword: tool.schema
|
|
.string()
|
|
.optional()
|
|
.describe("Search keyword in title and body"),
|
|
},
|
|
async execute(args, context) {
|
|
try {
|
|
let cmd = $`tea issue list --output json --state ${args.state} --limit ${args.limit ?? 30}`;
|
|
|
|
if (args.labels && args.labels.length > 0) {
|
|
cmd = cmd`--labels ${args.labels}`;
|
|
}
|
|
|
|
if (args.assignee && args.assignee.length > 0) {
|
|
cmd = cmd`--assignee ${args.assignee}`;
|
|
}
|
|
|
|
if (args.milestone && args.milestone.length > 0) {
|
|
cmd = cmd`--milestones ${args.milestone}`;
|
|
}
|
|
|
|
if (args.author && args.author.length > 0) {
|
|
cmd = cmd`--author ${args.author}`;
|
|
}
|
|
|
|
if (args.keyword && args.keyword.length > 0) {
|
|
cmd = cmd`--keyword ${args.keyword}`;
|
|
}
|
|
|
|
return await cmd.text();
|
|
} catch (error: any) {
|
|
return {
|
|
error: "Failed to list issues",
|
|
message: error.message,
|
|
stderr: error.stderr?.toString(),
|
|
};
|
|
}
|
|
},
|
|
});
|
|
|
|
export const issueCreate = tool({
|
|
description:
|
|
"Create a new issue with title, body, labels, milestone, and assignees",
|
|
args: {
|
|
title: tool.schema.string().describe("Issue title"),
|
|
body: tool.schema.string().optional().describe("Issue description/body"),
|
|
labels: tool.schema
|
|
.array(tool.schema.string())
|
|
.optional()
|
|
.describe("Comma-separated list of label names"),
|
|
milestone: tool.schema.string().optional().describe("Milestone name"),
|
|
assignees: tool.schema
|
|
.array(tool.schema.string())
|
|
.optional()
|
|
.describe("Comma-separated list of assignee usernames"),
|
|
},
|
|
async execute(args, context) {
|
|
try {
|
|
let cmd = $`tea issue create --output json --title ${args.title}`;
|
|
|
|
if (args.body) {
|
|
cmd = cmd`--body ${args.body}`;
|
|
}
|
|
|
|
if (args.labels) {
|
|
cmd = cmd`--labels ${args.labels.join(",")}`;
|
|
}
|
|
|
|
if (args.milestone) {
|
|
cmd = cmd`--milestone ${args.milestone}`;
|
|
}
|
|
|
|
if (args.assignees) {
|
|
cmd = cmd`--assignee ${args.assignees.join(",")}`;
|
|
}
|
|
|
|
return await cmd.text();
|
|
} catch (error: any) {
|
|
return {
|
|
error: "Failed to create issue",
|
|
message: error.message,
|
|
stderr: error.stderr?.toString(),
|
|
};
|
|
}
|
|
},
|
|
});
|
|
|
|
export const issueEdit = tool({
|
|
description:
|
|
"Update an existing issue with partial updates to title, body, labels, milestone, or assignees",
|
|
args: {
|
|
issueNumber: tool.schema.number().describe("Issue number"),
|
|
title: tool.schema.string().optional().describe("New title"),
|
|
body: tool.schema.string().optional().describe("New description/body"),
|
|
labels: tool.schema
|
|
.array(tool.schema.string())
|
|
.optional()
|
|
.describe("New comma-separated list of label names"),
|
|
milestone: tool.schema.string().optional().describe("New milestone name"),
|
|
assignees: tool.schema
|
|
.array(tool.schema.string())
|
|
.optional()
|
|
.describe("New comma-separated list of assignee usernames"),
|
|
state: tool.schema
|
|
.enum(["open", "closed"])
|
|
.optional()
|
|
.describe("New state"),
|
|
},
|
|
async execute(args, context) {
|
|
try {
|
|
let cmd = $`tea issue edit --output json ${args.issueNumber}`;
|
|
|
|
if (args.title) {
|
|
cmd = cmd`--title ${args.title}`;
|
|
}
|
|
|
|
if (args.body) {
|
|
cmd = cmd`--body ${args.body}`;
|
|
}
|
|
|
|
if (args.labels) {
|
|
cmd = cmd`--labels ${args.labels.join(",")}`;
|
|
}
|
|
|
|
if (args.milestone) {
|
|
cmd = cmd`--milestone ${args.milestone}`;
|
|
}
|
|
|
|
if (args.assignees) {
|
|
cmd = cmd`--assignee ${args.assignees.join(",")}`;
|
|
}
|
|
|
|
if (args.state) {
|
|
cmd = cmd`--state ${args.state}`;
|
|
}
|
|
|
|
return await cmd.text();
|
|
} catch (error: any) {
|
|
return {
|
|
error: "Failed to edit issue",
|
|
message: error.message,
|
|
stderr: error.stderr?.toString(),
|
|
};
|
|
}
|
|
},
|
|
});
|
|
|
|
export const issueDetails = tool({
|
|
description:
|
|
"Get detailed information about a specific issue including dependencies and comments",
|
|
args: {
|
|
issueNumber: tool.schema.number().describe("Issue number"),
|
|
},
|
|
async execute(args, context) {
|
|
try {
|
|
return await $`tea issue ${args.issueNumber} --output json --comments`.text();
|
|
} catch (error: any) {
|
|
return {
|
|
error: "Failed to get issue details",
|
|
message: error.message,
|
|
stderr: error.stderr?.toString(),
|
|
};
|
|
}
|
|
},
|
|
}); |