chore: remove src/pages/api/repos/[owner]/[repo]/pulls/[number]/suggestions/apply.ts
swadhinbiswas committed 8 months ago
90f3dee
1 parent 7f9a0c7
commit 90f3dee
1 file changed
+0 -126
Showing 1 changed file+0-126
▼src/pages/api/repos/[owner]/[repo]/pulls/[number]/suggestions/apply.ts
+0-126
| @@ -1,126 +0,0 @@ | ||
1 | -/** | |
2 | - * Code Suggestions API | |
3 | - * Apply GitHub-style code suggestions to PR | |
4 | - */ | |
5 | - | |
6 | -import type { APIRoute } from "astro"; | |
7 | -import type { NodePgDatabase } from "drizzle-orm/node-postgres"; | |
8 | -import { eq } from "drizzle-orm"; | |
9 | -import { getDatabase, schema } from "@/db"; | |
10 | -import { getUserFromRequest } from "@/lib/auth"; | |
11 | -import { parseBody, unauthorized, badRequest, notFound, success, serverError } from "@/lib/api"; | |
12 | -import { z } from "zod"; | |
13 | -import { simpleGit } from "simple-git"; | |
14 | -import * as fs from "fs"; | |
15 | -import * as path from "path"; | |
16 | - | |
17 | -const applySuggestionSchema = z.object({ | |
18 | - commentIds: z.array(z.string()), | |
19 | - commitMessage: z.string().optional(), | |
20 | -}); | |
21 | - | |
22 | -// POST /api/repos/:owner/:repo/pulls/:number/suggestions/apply - Apply suggestions | |
23 | -import { withErrorHandler } from "@/lib/errors"; | |
24 | -import { logger } from "@/lib/logger"; | |
25 | - | |
26 | -// ... existing imports ... | |
27 | - | |
28 | -// POST /api/repos/:owner/:repo/pulls/:number/suggestions/apply - Apply suggestions | |
29 | -export const POST: APIRoute = withErrorHandler(async ({ params, request }) => { | |
30 | - const tokenPayload = await getUserFromRequest(request); | |
31 | - if (!tokenPayload) { | |
32 | - return unauthorized(); | |
33 | - } | |
34 | - | |
35 | - const parsed = await parseBody(request, applySuggestionSchema); | |
36 | - if ("error" in parsed) return parsed.error; | |
37 | - | |
38 | - const { owner, repo, number } = params; | |
39 | - const { commentIds, commitMessage } = parsed.data; | |
40 | - | |
41 | - const db = getDatabase() as NodePgDatabase<typeof schema>; | |
42 | - | |
43 | - // Find PR | |
44 | - const pr = await db.query.pullRequests.findFirst({ | |
45 | - where: eq(schema.pullRequests.number, parseInt(number as string)), | |
46 | - with: { repository: true }, | |
47 | - }); | |
48 | - | |
49 | - if (!pr || pr.repository?.ownerId !== owner) { | |
50 | - return notFound("Pull request not found"); | |
51 | - } | |
52 | - | |
53 | - // Get comments with suggestions | |
54 | - const comments = await db.query.pullRequestComments.findMany({ | |
55 | - where: (c, { inArray }) => inArray(c.id, commentIds), | |
56 | - }); | |
57 | - | |
58 | - const suggestions: Array<{ | |
59 | - path: string; | |
60 | - line: number; | |
61 | - code: string; | |
62 | - }> = []; | |
63 | - | |
64 | - // Extract suggestions from comment bodies | |
65 | - for (const comment of comments) { | |
66 | - if (!comment.path || !comment.line) continue; | |
67 | - | |
68 | - // Parse ```suggestion blocks | |
69 | - const suggestionMatch = comment.body.match(/```suggestion\n([\s\S]*?)\n```/); | |
70 | - if (suggestionMatch) { | |
71 | - suggestions.push({ | |
72 | - path: comment.path, | |
73 | - line: comment.line, | |
74 | - code: suggestionMatch[1], | |
75 | - }); | |
76 | - } | |
77 | - } | |
78 | - | |
79 | - if (suggestions.length === 0) { | |
80 | - return badRequest("No suggestions found in comments"); | |
81 | - } | |
82 | - | |
83 | - // Apply suggestions (simplified - in production would need proper git integration) | |
84 | - const git = simpleGit(); | |
85 | - const repoPath = pr.repository.diskPath || `/repos/${owner}/${repo}`; | |
86 | - | |
87 | - // Checkout PR branch | |
88 | - await git.cwd(repoPath); | |
89 | - await git.checkout(pr.headBranch); | |
90 | - | |
91 | - let appliedCount = 0; | |
92 | - for (const suggestion of suggestions) { | |
93 | - try { | |
94 | - const filePath = path.join(repoPath, suggestion.path); | |
95 | - const content = fs.readFileSync(filePath, "utf-8"); | |
96 | - const lines = content.split("\n"); | |
97 | - | |
98 | - // Replace line with suggestion | |
99 | - lines[suggestion.line - 1] = suggestion.code; | |
100 | - | |
101 | - fs.writeFileSync(filePath, lines.join("\n")); | |
102 | - appliedCount++; | |
103 | - } catch (err) { | |
104 | - logger.error({ err, path: suggestion.path }, "Failed to apply suggestion"); | |
105 | - } | |
106 | - } | |
107 | - | |
108 | - if (appliedCount > 0) { | |
109 | - // Commit changes | |
110 | - await git.add("."); | |
111 | - await git.commit( | |
112 | - commitMessage || `Apply ${appliedCount} code suggestion${appliedCount > 1 ? "s" : ""}` | |
113 | - ); | |
114 | - | |
115 | - // Push to remote | |
116 | - await git.push("origin", pr.headBranch); | |
117 | - } | |
118 | - | |
119 | - logger.info({ userId: tokenPayload.userId, repoId: pr.repository.id, prId: pr.id, appliedCount }, "Applied code suggestions"); | |
120 | - | |
121 | - return success({ | |
122 | - message: `Applied ${appliedCount} suggestion${appliedCount > 1 ? "s" : ""}`, | |
123 | - applied: appliedCount, | |
124 | - total: suggestions.length, | |
125 | - }); | |
126 | -}); | |
127 | 0 | |