I am building a web application with nextjs 14 in the client, nodejs/express in server, and firestore database. My application is working fine but i had no experience with firestore and now i have a complaint from firebase saying that i need to update my security rules, that i notice too late in my development and realize that i should use the firebase Oauth from the beginning but i didn’t I also wanted to make use of a hibrid aproach using some of next’s new features (app router) for my auth but still managing my apis in my node server so this was my approach
[…nextauth]/route.ts
import NextAuth from 'next-auth/next';
import GoogleProvider from 'next-auth/providers/google';
import { NextAuthOptions } from 'next-auth';
import { db } from '../../../../../firebase';
import { doc, setDoc, getDoc, serverTimestamp } from 'firebase/firestore';
const GOOGLE_CLIENT_ID = process.env.GOOGLE_CLIENT_ID!;
const GOOGLE_CLIENT_SECRET = process.env.GOOGLE_CLIENT_SECRET!;
const authOptions: NextAuthOptions = {
session: {
strategy: 'jwt',
},
providers: [
GoogleProvider({
clientId: GOOGLE_CLIENT_ID,
clientSecret: GOOGLE_CLIENT_SECRET,
}),
],
callbacks: {
async signIn({ user, account, profile }) {
if (!profile?.email) {
throw new Error('No profile');
}
const userData = {
name: profile.name || user.name,
email: profile.email,
bio: '',
wishlist: [],
eventsParticipated: [],
isActive: true,
hasCompletedProfile: false,
invitationStatus: 'pending',
privacySettings: {
showEmail: false,
showWishlist: true,
},
createdAt: serverTimestamp(),
updatedAt: serverTimestamp(),
};
const userRef = doc(db, 'users', profile.email);
try {
const userSnap = await getDoc(userRef);
if (!userSnap.exists()) {
await setDoc(userRef, userData);
} else {
await setDoc(userRef, userData, { merge: true });
}
} catch (error) {
console.error('Error updating user in Firestore', error);
throw new Error('Error updating user data');
}
return true;
},
},
};
export const handler = NextAuth(authOptions);
export { handler as GET, handler as POST };
i made a custom user model and create the firebase collection users in my db once a user login with google
Then the problem came when i tried to implement security rules to my db
the db doesn’t know about my next-auth google provider.
I tried to use the firestore adapter
//same code above plus @firebase-adapter and cert form firebase/app imports
const authOptions: NextAuthOptions = {
session: {
strategy: 'jwt',
},
providers: [
GoogleProvider({
clientId: GOOGLE_CLIENT_ID,
clientSecret: GOOGLE_CLIENT_SECRET,
}),
],
adapter: FirestoreAdapter({
credential: cert({
projectId: serviceAccount.project_id,
clientEmail: serviceAccount.client_email,
privateKey: serviceAccount.private_key!.replace(/\n/g, 'n'),
}),
}),
callbacks: {
async signIn({ user, account, profile }) {
if (!profile?.email) {
throw new Error('No profile');
}
//same code below
In my node server i was already using firestore-admin from the begining so i decide to share the same service-account.json like this
import serviceAccount from '../../../../../../server/service-account.json';
and when i tested i had the following error from google
i tried also to eliminate the conflict removing the callback option but the error persist, it only works again if i remove the adapter, and now i only have 5 days left to update my security rules. can someone enlight me ? i have been researching about this issue 3 days now. (this is a personal project)
I was expecting that my database update with the session collection and the account collection and from there be able to update my security rules.