You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

将Firebase UserRecord写入Firestore文档的优化方法咨询

Better way to convert Firebase Auth UserRecord to plain object for Firestore set()?

I've written a Cloud Function that writes user data to Firestore when a new user is created. Here's my code:

const admin = require('firebase-admin');
const functions = require('firebase-functions');
admin.initializeApp(functions.config().firebase);
var db = admin.firestore();
exports.addNewUserToCollection = functions.auth.user().onCreate(event => {
  const user = event.data; // The Firebase user.
  // if we don't do this song and dance we get the following error
  // Error: Argument "data" is not a valid Document. Input is not a plain JavaScript object.
  var userData = JSON.parse(JSON.stringify(user));
  return db.collection('users').doc(user.uid).set(userData);
});

According to the official docs, event.data is a UserRecord object. When I log it to the console, it looks like a plain JavaScript object, but passing it directly to set() throws the error: "Error: Argument "data" is not a valid Document. Input is not a plain JavaScript object."

Right now I'm converting the data using JSON.stringify() followed by JSON.parse(), but I'm wondering if there's a cleaner, more efficient way to handle this?


Optimal Solutions

1. Use the built-in toJSON() method

Firebase's UserRecord object actually has a toJSON() method that returns a plain JavaScript object directly. This is the official and most efficient way to convert it—no need for the stringify/parse hack:

exports.addNewUserToCollection = functions.auth.user().onCreate(event => {
  const user = event.data;
  const userData = user.toJSON(); // Converts UserRecord to plain JS object
  return db.collection('users').doc(user.uid).set(userData);
});

This method is designed specifically for this use case, so it's more performant and cleaner than serializing/deserializing the entire object.

2. Manually extract required fields

If you don't need all the fields from the UserRecord (which is often the case), manually picking only the data you need is even better. This reduces the amount of data stored in Firestore and keeps your documents lean:

exports.addNewUserToCollection = functions.auth.user().onCreate(event => {
  const user = event.data;
  const userData = {
    uid: user.uid,
    email: user.email,
    displayName: user.displayName,
    photoURL: user.photoURL,
    createdAt: user.metadata.creationTime,
    lastSignInAt: user.metadata.lastSignInTime
    // Add any other fields you actually need
  };
  return db.collection('users').doc(user.uid).set(userData);
});

This approach gives you full control over what's stored, avoids including unnecessary metadata, and eliminates any conversion issues entirely.

Why the stringify/parse hack works (and why you shouldn't use it)

The JSON.stringify()/JSON.parse() trick works because it strips away any non-serializable properties and methods from the UserRecord object, leaving only plain data. However, it's inefficient (since it converts the object to a string and back) and can accidentally include fields you don't want. Using toJSON() or manual extraction is always preferable.

内容的提问来源于stack exchange,提问作者w--

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 03:22:48