Skip to content

Improve error handling for GitHub API requests#58

Closed
Rey-han-24 wants to merge 3 commits intoBeyteFlow:mainfrom
Rey-han-24:patch-1
Closed

Improve error handling for GitHub API requests#58
Rey-han-24 wants to merge 3 commits intoBeyteFlow:mainfrom
Rey-han-24:patch-1

Conversation

@Rey-han-24
Copy link
Copy Markdown

Refactor error handling for GitHub API calls to provide more specific responses for 404 and 403 errors.

🚀 BΞYTΞFLʘW | Pull Request Protocol

PR Type: Fix (Choose one: feat | fix | refactor | docs | perf)
Issue Link: Fixes # 37


📝 System Summary

Enhanced the repository verification pipeline by implementing a dedicated error-handling "gatekeeper" for GitHub API interactions. The system now distinguishes between invalid URLs, missing/private repositories (404), and rate-limiting issues (403), providing clear, actionable feedback to the user before initiating AI generation.

🛠️ Technical Changes

  • Logic change in app/api/generate/route.ts
  • New UI component added: ...
  • Database schema updated: ...
  • Status Code Mapping: Implemented specific NextResponse returns for 404 (Not Found) and 403 (Forbidden/Rate Limit) status codes.

🧪 Quality Assurance (QA)

  • Linting: Code style matches the BeyteFlow grid.
  • Build: npm run build executed without errors.
  • Testing: New logic has been verified and tested.
  • Dark Mode: UI is high-contrast and neon-optimized.

🖼️ Visual Evidence

If this PR affects the UI, drop a screenshot or GIF below:


📡 Developer Authorization

  • I have performed a self-review of my code.
  • My changes generate no new warnings in the console.
  • I have updated the documentation (if applicable).

Authorized by: @Rey-han-24
Timestamp: {{ 2/24/2026 }}


Refactor error handling for GitHub API calls to provide more specific responses for 404 and 403 errors.
Copilot AI review requested due to automatic review settings February 24, 2026 08:42
@vercel
Copy link
Copy Markdown
Contributor

vercel bot commented Feb 24, 2026

@Rey-han-24 is attempting to deploy a commit to the naheel0's projects Team on Vercel.

A member of the Team first needs to authorize it.

@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Feb 24, 2026

Caution

Review failed

The pull request is closed.

ℹ️ Recent review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 8c399e1 and 126e0a9.

📒 Files selected for processing (1)
  • src/app/api/generate/route.ts

📝 Walkthrough

Summary by CodeRabbit

  • Bug Fixes
    • Enhanced error handling with improved messaging when repository data retrieval fails during generation.

Walkthrough

Reworks async assignment and adds an explicit null/undefined check for fetched repository info, returning a 400 on failure; updates the README generation error message and adds defensive handling comments around Octokit helper results without changing exported/public signatures. (≤50 words)

Changes

Cohort / File(s) Summary
API route — generate
src/app/api/generate/route.ts
Replaces Promise.all destructuring with separate declarations and assignment; adds explicit null/undefined check for repoInfo and an early 400 JSON response; updates README generation error message text; adds defensive handling comment for possible empty Octokit results.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

Suggested labels

area: ai-logic, area: backend

Suggested reviewers

  • adithyanmkd

Poem

🐰 I hopped through promises, checked each hole,
If repo info’s empty I guard the whole,
A gentler message now warms the night —
Try again, dear dev, and all stays right. ✨

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly and concisely describes the main objective of the pull request: improving error handling for GitHub API requests, which directly matches the primary change in the changeset.
Description check ✅ Passed The description is directly related to the changeset, explaining the refactored error handling for GitHub API calls and its purpose in distinguishing between different error types before initiating AI generation.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
src/app/api/generate/route.ts (1)

65-66: Avoid error: any; use a type guard or Octokit's RequestError type.

If/when the dead-code issue above is fixed, error: any will bypass type safety. Octokit throws RequestError (from @octokit/request-error) which has a .status property. Also, error.message on line 66 will throw at runtime if error is not an object.

Suggested approach
-    } catch (error: any) {
-      console.error("GitHub API Error:", error.message);
-
-      // Handle 404 (Not Found / Typos)
-      if (error.status === 404) {
+    } catch (error: unknown) {
+      const status = error instanceof Error && 'status' in error ? (error as { status: number }).status : undefined;
+      const message = error instanceof Error ? error.message : "Unknown GitHub API error";
+      console.error("GitHub API Error:", message);
+
+      if (status === 404) {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/app/api/generate/route.ts` around lines 65 - 66, Replace the unsafe catch
signature and logging by using a proper error type guard: change the catch
parameter from "error: any" to "error: unknown" (or import RequestError from
`@octokit/request-error` and use it) and in the catch block check whether the
error is an instance of RequestError or an object with a "message" property;
then log a safe message including error.message and, if present, error.status
(and fallback to JSON.stringify or String(error) if neither is present) instead
of directly accessing error.message as in the "catch (error: any)" /
"console.error('GitHub API Error:', error.message)" lines so you avoid runtime
errors and surface Octokit RequestError.status when available.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/app/api/generate/route.ts`:
- Line 184: The response body returns an object with key "error" whose value
currently redundantly starts with "error: ". Update the route handler that
constructs the JSON error response (the generate API route) to remove the
"error: " prefix so the value reads "AI generation failed. Please try again in a
moment." — keep the same "error" key and only change the message string to avoid
the stuttered "error: error: ..." output.
- Around line 59-89: The try/catch in route.ts is dead because getRepoData and
getRepoContents swallow errors and never reject; change octokit helpers instead:
remove the internal try/catch in getRepoData and getRepoContents so they throw
on error (propagating status and message), then adjust callers in route.ts
(variables repoInfo, repoContents and the downstream logic that consumes them)
to handle possibly undefined/null responses and the thrown errors via the
existing try/catch block so the 404/403 NextResponse branches work as intended.

---

Nitpick comments:
In `@src/app/api/generate/route.ts`:
- Around line 65-66: Replace the unsafe catch signature and logging by using a
proper error type guard: change the catch parameter from "error: any" to "error:
unknown" (or import RequestError from `@octokit/request-error` and use it) and in
the catch block check whether the error is an instance of RequestError or an
object with a "message" property; then log a safe message including
error.message and, if present, error.status (and fallback to JSON.stringify or
String(error) if neither is present) instead of directly accessing error.message
as in the "catch (error: any)" / "console.error('GitHub API Error:',
error.message)" lines so you avoid runtime errors and surface Octokit
RequestError.status when available.

ℹ️ Review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 03e4ad4 and 8c399e1.

📒 Files selected for processing (1)
  • src/app/api/generate/route.ts

Comment on lines +59 to +89
let repoInfo, repoContents;
try {
[repoInfo, repoContents] = await Promise.all([
getRepoData(owner, repo),
getRepoContents(owner, repo),
]);
} catch (error: any) {
console.error("GitHub API Error:", error.message);

// Handle 404 (Not Found / Typos)
if (error.status === 404) {
return NextResponse.json(
{ error: "Repository not found. Please check the URL for typos or ensure the repo is public." },
{ status: 404 }
);
}

// Handle 403 (Rate limits or Private repos)
if (error.status === 403) {
return NextResponse.json(
{ error: "Access denied or GitHub API rate limit reached. Try again later." },
{ status: 403 }
);
}

// Generic fallback for other API issues
return NextResponse.json(
{ error: "Unable to reach GitHub. Please verify the repository exists and is accessible." },
{ status: 400 }
);
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Find octokit.ts
find . -name "octokit.ts" -o -name "*octokit*" | head -20

Repository: BeyteFlow/ReadmeGenAI

Length of output: 85


🏁 Script executed:

#!/bin/bash
# Check src/lib directory structure
ls -la src/lib/ 2>/dev/null | head -20

Repository: BeyteFlow/ReadmeGenAI

Length of output: 294


🏁 Script executed:

#!/bin/bash
# Search for getRepoData and getRepoContents definitions
rg -n "async.*getRepoData|function getRepoData" -A 20 --type ts

Repository: BeyteFlow/ReadmeGenAI

Length of output: 1100


🏁 Script executed:

#!/bin/bash
# Search for getRepoContents definition
rg -n "async.*getRepoContents|function getRepoContents" -A 20 --type ts

Repository: BeyteFlow/ReadmeGenAI

Length of output: 1015


Critical: This try/catch is dead code — getRepoData and getRepoContents never throw.

Looking at src/lib/octokit.ts, both functions have internal try/catch blocks that swallow errors:

  • getRepoData (lines 20–35) catches all errors and returns null
  • getRepoContents (lines 40–58) catches all errors and returns []

Since both promises always resolve successfully, Promise.all will never reject, so the catch block (including the 404 and 403 handling) will never execute.

To make this work, either:

  1. Remove the try/catch blocks in octokit.ts so errors propagate to the caller here, OR
  2. Modify the octokit helpers to return an error-aware result object (e.g., { data: null, error: {...} }) that preserves the status code, OR
  3. Check the null/[] return values here instead of trying to catch exceptions (though this loses the status code differentiation)

Option 1 is the simplest approach aligned with the PR's goal. After that change, update the type handling for repoInfo and repoContents downstream (lines 92–119) to account for the actual response types.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/app/api/generate/route.ts` around lines 59 - 89, The try/catch in
route.ts is dead because getRepoData and getRepoContents swallow errors and
never reject; change octokit helpers instead: remove the internal try/catch in
getRepoData and getRepoContents so they throw on error (propagating status and
message), then adjust callers in route.ts (variables repoInfo, repoContents and
the downstream logic that consumes them) to handle possibly undefined/null
responses and the thrown errors via the existing try/catch block so the 404/403
NextResponse branches work as intended.

Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Refactors the POST /api/generate endpoint’s GitHub repository fetch flow to provide more specific, user-facing error responses when GitHub API calls fail (notably 404 and 403), before proceeding to AI README generation.

Changes:

  • Wraps getRepoData / getRepoContents calls in a try/catch intended to map GitHub API failures to specific HTTP responses (404/403).
  • Adds a generic fallback response for other GitHub API failures.
  • Updates the AI generation failure message returned from the endpoint.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

// Generic fallback for other API issues
return NextResponse.json(
{ error: "Unable to reach GitHub. Please verify the repository exists and is accessible." },
{ status: 400 }
Copy link

Copilot AI Feb 24, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The generic fallback response uses HTTP 400, but failures talking to GitHub (timeouts, upstream errors, unexpected Octokit errors) are server-side / upstream issues rather than a bad client request. Returning a 5xx (often 502/503) would be more accurate and makes retries/monitoring behave correctly.

Suggested change
{ status: 400 }
{ status: 502 }

Copilot uses AI. Check for mistakes.
Rey-han-24 and others added 2 commits February 24, 2026 13:46
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
@Rey-han-24 Rey-han-24 closed this Feb 24, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants