fix: use buildUrl utility in issues module

This commit is contained in:
Peter M. Elias
2024-12-28 03:34:59 -08:00
parent 10f0aec693
commit dac0b7cc34

View File

@@ -1,41 +1,43 @@
import { z } from "zod";
import { githubRequest, buildUrl } from "../common/utils.js";
import {
GitHubIssueSchema,
GitHubLabelSchema,
GitHubIssueAssigneeSchema,
GitHubMilestoneSchema,
} from "../common/types.js";
// Schema definitions
export const GetIssueSchema = z.object({
owner: z.string(),
repo: z.string(),
issue_number: z.number(),
});
export const IssueCommentSchema = z.object({
owner: z.string(),
repo: z.string(),
issue_number: z.number(),
body: z.string(),
});
export const CreateIssueOptionsSchema = z.object({
title: z.string().describe("Issue title"),
body: z.string().optional().describe("Issue body/description"),
assignees: z.array(z.string()).optional().describe("Array of usernames to assign"),
milestone: z.number().optional().describe("Milestone number to assign"),
labels: z.array(z.string()).optional().describe("Array of label names"),
title: z.string(),
body: z.string().optional(),
assignees: z.array(z.string()).optional(),
milestone: z.number().optional(),
labels: z.array(z.string()).optional(),
});
export const CreateIssueSchema = z.object({
owner: z.string().describe("Repository owner (username or organization)"),
repo: z.string().describe("Repository name"),
title: z.string().describe("Issue title"),
body: z.string().optional().describe("Issue body/description"),
assignees: z.array(z.string()).optional().describe("Array of usernames to assign"),
labels: z.array(z.string()).optional().describe("Array of label names"),
milestone: z.number().optional().describe("Milestone number to assign"),
owner: z.string(),
repo: z.string(),
...CreateIssueOptionsSchema.shape,
});
export const ListIssuesOptionsSchema = z.object({
owner: z.string(),
repo: z.string(),
state: z.enum(['open', 'closed', 'all']).optional(),
direction: z.enum(["asc", "desc"]).optional(),
labels: z.array(z.string()).optional(),
sort: z.enum(['created', 'updated', 'comments']).optional(),
direction: z.enum(['asc', 'desc']).optional(),
since: z.string().optional(), // ISO 8601 timestamp
page: z.number().optional(),
per_page: z.number().optional()
per_page: z.number().optional(),
since: z.string().optional(),
sort: z.enum(["created", "updated", "comments"]).optional(),
state: z.enum(["open", "closed", "all"]).optional(),
});
export const UpdateIssueOptionsSchema = z.object({
@@ -44,108 +46,63 @@ export const UpdateIssueOptionsSchema = z.object({
issue_number: z.number(),
title: z.string().optional(),
body: z.string().optional(),
state: z.enum(['open', 'closed']).optional(),
labels: z.array(z.string()).optional(),
assignees: z.array(z.string()).optional(),
milestone: z.number().optional()
milestone: z.number().optional(),
labels: z.array(z.string()).optional(),
state: z.enum(["open", "closed"]).optional(),
});
export const IssueCommentSchema = z.object({
owner: z.string(),
repo: z.string(),
issue_number: z.number(),
body: z.string()
});
export async function getIssue(owner: string, repo: string, issue_number: number) {
return githubRequest(`https://api.github.com/repos/${owner}/${repo}/issues/${issue_number}`);
}
export const GetIssueSchema = z.object({
owner: z.string().describe("Repository owner (username or organization)"),
repo: z.string().describe("Repository name"),
issue_number: z.number().describe("Issue number")
});
export async function addIssueComment(
owner: string,
repo: string,
issue_number: number,
body: string
) {
return githubRequest(`https://api.github.com/repos/${owner}/${repo}/issues/${issue_number}/comments`, {
method: "POST",
body: { body },
});
}
// Type exports
export type CreateIssueOptions = z.infer<typeof CreateIssueOptionsSchema>;
export type ListIssuesOptions = z.infer<typeof ListIssuesOptionsSchema>;
export type UpdateIssueOptions = z.infer<typeof UpdateIssueOptionsSchema>;
// Function implementations
export async function createIssue(
owner: string,
repo: string,
options: CreateIssueOptions
options: z.infer<typeof CreateIssueOptionsSchema>
) {
const response = await githubRequest(
return githubRequest(
`https://api.github.com/repos/${owner}/${repo}/issues`,
{
method: "POST",
body: options,
}
);
return GitHubIssueSchema.parse(response);
}
export async function listIssues(
owner: string,
repo: string,
options: Omit<ListIssuesOptions, 'owner' | 'repo'>
options: Omit<z.infer<typeof ListIssuesOptionsSchema>, "owner" | "repo">
) {
const url = buildUrl(`https://api.github.com/repos/${owner}/${repo}/issues`, options);
const response = await githubRequest(url);
return z.array(GitHubIssueSchema).parse(response);
return githubRequest(
buildUrl(`https://api.github.com/repos/${owner}/${repo}/issues`, options)
);
}
export async function updateIssue(
owner: string,
repo: string,
issueNumber: number,
options: Omit<UpdateIssueOptions, 'owner' | 'repo' | 'issue_number'>
issue_number: number,
options: Omit<z.infer<typeof UpdateIssueOptionsSchema>, "owner" | "repo" | "issue_number">
) {
const response = await githubRequest(
`https://api.github.com/repos/${owner}/${repo}/issues/${issueNumber}`,
return githubRequest(
`https://api.github.com/repos/${owner}/${repo}/issues/${issue_number}`,
{
method: "PATCH",
body: options
body: options,
}
);
return GitHubIssueSchema.parse(response);
}
export async function addIssueComment(
owner: string,
repo: string,
issueNumber: number,
body: string
) {
const response = await githubRequest(
`https://api.github.com/repos/${owner}/${repo}/issues/${issueNumber}/comments`,
{
method: "POST",
body: { body }
}
);
return z.object({
id: z.number(),
node_id: z.string(),
url: z.string(),
html_url: z.string(),
body: z.string(),
user: GitHubIssueAssigneeSchema,
created_at: z.string(),
updated_at: z.string(),
}).parse(response);
}
export async function getIssue(
owner: string,
repo: string,
issueNumber: number
) {
const response = await githubRequest(
`https://api.github.com/repos/${owner}/${repo}/issues/${issueNumber}`
);
return GitHubIssueSchema.parse(response);
}
}