feat(auth): Firebase Auth Google Sign-In Integration - #24
Merged
Conversation
…ication - Add googleSchema Joi validator to authValidators.js and validate.js - Add googleAuth controller handler that verifies Firebase ID token via admin.auth().verifyIdToken() - Register POST /api/v1/auth/google route with validation and authLimiter - Add integration tests for the new endpoint
…port - Add findByFirebaseUid() to look up users by Firebase UID - Add findOrCreateByFirebaseUser() to idempotently link/create users from Google sign-in: queries by email first, updates firebaseUid if missing, or creates a new passwordless user document - Update User model schema descriptor to include firebaseUid field - Add comprehensive unit tests for all new functions
…tests - Update jwt.js: change default ACCESS_TOKEN_EXPIRY from 24h to 15m (matches architecture spec: accessToken exp: 15m, refreshToken exp: 7d) - Update .env.example: document JWT_EXPIRES_IN and JWT_REFRESH_EXPIRES_IN env vars so operators can override token lifetimes - Add __tests__/googleAuthJwt.test.js: dedicated integration tests for the JWT token generation step in the Google auth flow, covering: * Access + refresh token presence and structure in response * Token payload contains correct Firestore user ID * Access token expiry is shorter than refresh token expiry * setRefreshToken is called with the generated refresh token * Token can be verified with the correct secret * Correct token type separation (access vs refresh secrets)
…le auth payload for Google auth
- Verify authController.googleAuth persists refresh token via userService.setRefreshToken
- Confirm buildAuthPayload returns { token, refreshToken, user: { id, email, phone, verified } }
wrapped in sendSuccess as { data: { token, refreshToken, user } } — matches frontend authService
- Add dedicated __tests__/googleAuthRefreshToken.test.js covering:
* Refresh token is persisted in Firestore after successful Google sign-in
* Auth payload structure is frontend-compatible (data.token, data.refreshToken, data.user)
* Refresh token rotation works for Google-authenticated users
* Refresh token is cleared on logout for Google users
* Edge cases: missing idToken, expired Firebase token, email conflict
…, and validator Task 5: Update authController and routes to include the new Google auth endpoint. - authController.googleAuth: verifies Firebase ID token via Admin SDK, calls userService.findOrCreateByFirebaseUser, issues custom JWTs, persists refresh token in Firestore, returns standard auth payload - routes/auth.js: POST /auth/google wired to validate(googleSchema) + authController.googleAuth, covered by authLimiter (20 req/15min) - middleware/validate.js: googleSchema exported (idToken: string, min 1, required) - docs/API.md: added POST /auth/google endpoint documentation with request/response shapes, error codes, and frontend integration notes - __tests__/auth.test.js: comprehensive integration tests for all /auth/google scenarios (missing token, empty token, expired token, success, missing email, conflict, server error)
Tambeej
commented
Apr 3, 2026
Tambeej
left a comment
Owner
Author
There was a problem hiding this comment.
🤖 Code-Pilot Team Leader (adk)
✅ APPROVED
✅ Backend PR Review — Google Auth via Firebase
All 5 tasks have been implemented correctly and align with the architecture design. The code is well-structured, secure, and thoroughly tested.
Task Verification
| # | Task | Status |
|---|---|---|
| 1 | POST /api/auth/google endpoint with admin.auth().verifyIdToken() |
✅ |
| 2 | userService findOrCreateByFirebaseUser() with firebaseUid storage |
✅ |
| 3 | Custom access (15m) and refresh (7d) JWT generation | ✅ |
| 4 | Refresh token persisted in Firestore, frontend-compatible payload | ✅ |
| 5 | authController, routes, and validation updated | ✅ |
Security ✅
- Firebase ID token verified server-side only via Admin SDK
- Rate limiting applied via
authLimiteron/googleendpoint - Input validation via Joi schema
- No sensitive fields leaked (password, refreshToken, firebaseUid stripped by
toPublicUser) - Google-only accounts properly rejected for email/password login (GOOGLE_ACCOUNT error code)
- 409 Conflict for email already linked to a different Firebase UID
Architecture Alignment ✅
- Data flow matches architecture spec (steps 5–9)
- Three-path user resolution (returning Google user → email linking → new user) implemented correctly
- No breaking changes to existing email/password auth flow
Test Coverage ✅
- Integration tests: 7 new Google Auth test cases covering validation, auth failures, success, edge cases
- Unit tests: Comprehensive
findOrCreateByFirebaseUsertests covering all 3 paths, conflict detection, input validation - Firebase Admin SDK properly mocked
Minor Note (non-blocking)
googleSchemais defined in bothsrc/middleware/validate.jsandsrc/validators/authValidators.js. The route uses the one fromvalidate.js. The duplicate inauthValidators.jsis harmless but could be cleaned up in a future PR.
LGTM — well-implemented, secure, and thoroughly tested. 🚀
Reviewed at 2026-04-03 10:56:40 UTC
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Overview
This PR implements Firebase Authentication with Google provider for user sign-in and registration in the Morty backend.
Completed Tasks
POST
/api/auth/googleendpoint — Added a new endpoint that receives a Firebase ID token from the client and verifies it usingadmin.auth().verifyIdToken().Updated
userService— Extended the user service to create or retrieve a user by Firebase UID/email, and store thefirebaseUidfield in the Firestore user document.JWT token generation — Upon successful Firebase token verification, the backend generates custom access and refresh JWT tokens for the authenticated user.
Refresh token persistence — The refresh token is persisted in Firestore and the auth payload returned is fully compatible with the existing frontend auth flow.
Updated
authControllerand routes — TheauthControllerandsrc/routes/auth.jshave been updated to wire up the new/api/auth/googleendpoint.API Contract
Related
signInWithPopup/signInWithRedirect.