SCRUM-154: initialize user accounts + VSCode account linking branch#46
Conversation
There was a problem hiding this comment.
Pull request overview
Adds a new codescape-web/ Create React App frontend that authenticates via Supabase (GitHub OAuth) and imports/link GitHub repositories containing a .codescape file into Supabase.
Changes:
- Bootstraps a CRA TypeScript app under
codescape-web/(public assets, tsconfig, test setup). - Adds Supabase client initialization and GitHub OAuth sign-in/sign-out UI.
- Implements
importUserReposto fetch GitHub repos, detect.codescape, and upsertlinked_reposrows.
Reviewed changes
Copilot reviewed 16 out of 22 changed files in this pull request and generated 9 comments.
Show a summary per file
| File | Description |
|---|---|
| codescape-web/tsconfig.json | TypeScript compiler configuration for the CRA app. |
| codescape-web/src/setupTests.ts | Jest DOM testing-library setup. |
| codescape-web/src/reportWebVitals.ts | CRA web-vitals reporting helper. |
| codescape-web/src/react-app-env.d.ts | CRA TypeScript ambient type reference. |
| codescape-web/src/logo.svg | CRA default logo asset. |
| codescape-web/src/lib/supabase.ts | Creates and exports the Supabase client using env vars. |
| codescape-web/src/lib/repos.ts | GitHub repo scan + .codescape parsing + Supabase upsert logic. |
| codescape-web/src/index.tsx | React app bootstrap and render entrypoint. |
| codescape-web/src/index.css | Base global styles. |
| codescape-web/src/App.tsx | Auth flow UI and triggers repo import after GitHub sign-in. |
| codescape-web/src/App.test.tsx | CRA test scaffold for the App component. |
| codescape-web/src/App.css | CRA default App styles. |
| codescape-web/public/robots.txt | CRA default robots config. |
| codescape-web/public/manifest.json | CRA default PWA manifest. |
| codescape-web/public/logo512.png | CRA default icon asset. |
| codescape-web/public/logo192.png | CRA default icon asset. |
| codescape-web/public/index.html | CRA HTML template. |
| codescape-web/public/favicon.ico | CRA default favicon. |
| codescape-web/package.json | Frontend dependencies and scripts (CRA + Supabase). |
| codescape-web/README.md | CRA default README content. |
| codescape-web/.gitignore | Standard CRA ignores, including .env*. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| const response = await fetch('https://api.github.com/user/repos?per_page=100', { | ||
| headers: { | ||
| Authorization: `Bearer ${githubToken}`, | ||
| Accept: 'application/vnd.github.v3+json' | ||
| } | ||
| }) |
There was a problem hiding this comment.
Fetching only per_page=100 will miss repositories for users with more than 100 repos. Implement pagination (via Link header or page parameter loop) so all repos are considered.
| for (const repo of repos) { | ||
| const codescapeResponse = await fetch( | ||
| `https://api.github.com/repos/${repo.full_name}/contents/.codescape`, | ||
| { | ||
| headers: { | ||
| Authorization: `Bearer ${githubToken}`, | ||
| Accept: 'application/vnd.github.v3+json' | ||
| } | ||
| } | ||
| ) |
There was a problem hiding this comment.
This loop does sequential network requests (one GitHub request per repo, plus Supabase upsert), which will be slow and more likely to hit GitHub rate limits. Consider using a concurrency-limited queue / Promise.allSettled with a small pool, and treat 404 for .codescape as a normal skip while handling other non-2xx responses.
| useEffect(() => { | ||
| // Get current session on load | ||
| supabase.auth.getSession().then(({ data: { session } }) => { | ||
| setSession(session) | ||
| }) | ||
|
|
||
| // Listen for auth changes. Do not await Supabase (or other supabase.* calls) inside this | ||
| // callback — it can deadlock the auth lock while OAuth completes. Defer import instead. | ||
| const { data: { subscription } } = supabase.auth.onAuthStateChange((event, session) => { | ||
| setSession(session) | ||
|
|
||
| if (event === 'SIGNED_IN' && session) { | ||
| const githubToken = session.provider_token | ||
| const userId = session.user.id | ||
| if (githubToken) { |
There was a problem hiding this comment.
importUserRepos is only triggered on the SIGNED_IN event; users who already have an active session on page load won’t import/sync repos. If sync-on-load is intended, also handle the initial session event (or trigger a sync when getSession() returns a session).
| @@ -0,0 +1,44 @@ | |||
| import { supabase } from './supabase' | |||
|
|
|||
| export async function importUserRepos(githubToken: string, userId: string) { | |||
There was a problem hiding this comment.
importUserRepos introduces non-trivial behavior (GitHub API pagination/error handling, .codescape parsing, Supabase writes) but currently has no automated tests. Given the project already has a test harness (App.test.tsx), consider adding unit tests with mocked fetch/Supabase to cover success and failure paths (rate limit, invalid .codescape, upsert error).
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
No description provided.