管理使用者

Firebase Admin SDK 提供的 API 可讓您以進階權限管理 Firebase Authentication 使用者。管理員使用者管理 API 可讓您透過程式輔助方式,在安全的伺服器環境中完成下列工作:

  • 建立新使用者時,不設限節流或速率限制。
  • 依據不同的條件 (例如 UID、電子郵件或電話號碼) 查詢使用者。
  • 批次列出指定專案的所有使用者。
  • 存取使用者中繼資料,包括帳戶建立日期和上次登入日期。
  • 不必提供現有密碼即可刪除使用者。
  • 更新使用者屬性 (包括密碼),無須以使用者身分登入。
  • 驗證電子郵件時,不必透過驗證電子郵件的額外動作流程。
  • 變更使用者的電子郵件地址,但不會傳送電子郵件連結來撤銷這些變更。
  • 使用電話號碼建立新使用者,不必經過簡訊驗證流程。
  • 無須完成簡訊驗證流程,就能變更使用者的電話號碼。
  • 在離線狀態下為使用者進行預設設定,然後稍後控制何時啟用。
  • 建立專屬於特定應用程式使用者管理系統的自訂使用者控制台。

事前準備

如要使用 Firebase Admin SDK 提供的使用者管理 API,您必須擁有服務帳戶。請按照設定說明操作,進一步瞭解如何初始化 Admin SDK。

擷取使用者資料

識別使用者的主要方法是透過 uid,也就是該使用者的專屬 ID。Admin SDK 提供一種方法,可根據使用者的 uid 擷取使用者個人資料資訊:

Node.js

getAuth()
  .getUser(uid)
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log(`Successfully fetched user data: ${userRecord.toJSON()}`);
  })
  .catch((error) => {
    console.log('Error fetching user data:', error);
  });

Java

UserRecord userRecord = FirebaseAuth.getInstance().getUser(uid);
// See the UserRecord reference doc for the contents of userRecord.
System.out.println("Successfully fetched user data: " + userRecord.getUid());

Python

from firebase_admin import auth

user = auth.get_user(uid)
print('Successfully fetched user data: {0}'.format(user.uid))

Go

// Get an auth client from the firebase.App
client, err := app.Auth(ctx)
if err != nil {
	log.Fatalf("error getting Auth client: %v\n", err)
}

u, err := client.GetUser(ctx, uid)
if err != nil {
	log.Fatalf("error getting user %s: %v\n", uid, err)
}
log.Printf("Successfully fetched user data: %v\n", u)

C#

UserRecord userRecord = await FirebaseAuth.DefaultInstance.GetUserAsync(uid);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully fetched user data: {userRecord.Uid}");

這個方法會針對提供給該方法的 uid 對應的使用者,傳回 UserRecord 物件。

如果提供的 uid 不屬於現有使用者,或是因其他原因無法擷取使用者,上述方法會擲回錯誤。如需完整的錯誤代碼清單 (包括說明和解決步驟),請參閱 Admin Auth API 錯誤

在某些情況下,您會取得使用者的電子郵件地址,而非 uid。Firebase Admin SDK 支援使用電子郵件查詢使用者資訊:

Node.js

getAuth()
  .getUserByEmail(email)
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log(`Successfully fetched user data: ${userRecord.toJSON()}`);
  })
  .catch((error) => {
    console.log('Error fetching user data:', error);
  });

Java

UserRecord userRecord = FirebaseAuth.getInstance().getUserByEmail(email);
// See the UserRecord reference doc for the contents of userRecord.
System.out.println("Successfully fetched user data: " + userRecord.getEmail());

Python

from firebase_admin import auth

user = auth.get_user_by_email(email)
print('Successfully fetched user data: {0}'.format(user.uid))

Go

u, err := client.GetUserByEmail(ctx, email)
if err != nil {
	log.Fatalf("error getting user by email %s: %v\n", email, err)
}
log.Printf("Successfully fetched user data: %v\n", u)

C#

UserRecord userRecord = await FirebaseAuth.DefaultInstance.GetUserByEmailAsync(email);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully fetched user data: {userRecord.Uid}");

這個方法會針對對應至所提供電子郵件地址的使用者傳回 UserRecord 物件。

如果提供的電子郵件不屬於現有使用者,或是因其他原因無法擷取使用者,Admin SDK 就會擲回錯誤。如需錯誤代碼的完整清單,包括說明和解決步驟,請參閱「Admin Authentication API 錯誤」。

在其他情況下,您會取得使用者的電話號碼,而非 uid。Firebase Admin SDK 支援透過電話號碼查詢使用者資訊:

Node.js

getAuth()
  .getUserByPhoneNumber(phoneNumber)
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log(`Successfully fetched user data:  ${userRecord.toJSON()}`);
  })
  .catch((error) => {
    console.log('Error fetching user data:', error);
  });

Java

UserRecord userRecord = FirebaseAuth.getInstance().getUserByPhoneNumber(phoneNumber);
// See the UserRecord reference doc for the contents of userRecord.
System.out.println("Successfully fetched user data: " + userRecord.getPhoneNumber());

Python

from firebase_admin import auth

user = auth.get_user_by_phone_number(phone)
print('Successfully fetched user data: {0}'.format(user.uid))

Go

u, err := client.GetUserByPhoneNumber(ctx, phone)
if err != nil {
	log.Fatalf("error getting user by phone %s: %v\n", phone, err)
}
log.Printf("Successfully fetched user data: %v\n", u)

C#

UserRecord userRecord = await FirebaseAuth.DefaultInstance.GetUserByPhoneNumberAsync(phoneNumber);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully fetched user data: {userRecord.Uid}");

這個方法會針對提供的電話號碼對應使用者傳回 UserRecord 物件。

如果提供的電話號碼不屬於現有使用者,或是因其他原因無法擷取使用者,Admin SDK 就會擲回錯誤。如需錯誤代碼的完整清單,包括說明和解決步驟,請參閱「Admin Authentication API 錯誤」。

大量擷取使用者資料

Firebase Admin SDK 也允許根據您提供的 ID 擷取使用者清單。您可以透過使用者 ID、電子郵件或電話號碼識別使用者。單一呼叫最多可提供 100 個 ID。ID 可包含多種類型:

Node.js

getAuth()
  .getUsers([
    { uid: 'uid1' },
    { email: 'user2@example.com' },
    { phoneNumber: '+15555550003' },
    { providerId: 'google.com', providerUid: 'google_uid4' },
  ])
  .then((getUsersResult) => {
    console.log('Successfully fetched user data:');
    getUsersResult.users.forEach((userRecord) => {
      console.log(userRecord);
    });

    console.log('Unable to find users corresponding to these identifiers:');
    getUsersResult.notFound.forEach((userIdentifier) => {
      console.log(userIdentifier);
    });
  })
  .catch((error) => {
    console.log('Error fetching user data:', error);
  });

Java

GetUsersResult result = FirebaseAuth.getInstance().getUsersAsync(Arrays.asList(
    new UidIdentifier("uid1"),
    new EmailIdentifier("user2@example.com"),
    new PhoneIdentifier("+15555550003"),
    new ProviderIdentifier("google.com", "google_uid4"))).get();

System.out.println("Successfully fetched user data:");
for (UserRecord user : result.getUsers()) {
  System.out.println(user.getUid());
}

System.out.println("Unable to find users corresponding to these identifiers:");
for (UserIdentifier uid : result.getNotFound()) {
  System.out.println(uid);
}

Python

from firebase_admin import auth

result = auth.get_users([
    auth.UidIdentifier('uid1'),
    auth.EmailIdentifier('user2@example.com'),
    auth.PhoneIdentifier(+15555550003),
    auth.ProviderIdentifier('google.com', 'google_uid4')
])

print('Successfully fetched user data:')
for user in result.users:
    print(user.uid)

print('Unable to find users corresponding to these identifiers:')
for uid in result.not_found:
    print(uid)

Go

getUsersResult, err := client.GetUsers(ctx, []auth.UserIdentifier{
	auth.UIDIdentifier{UID: "uid1"},
	auth.EmailIdentifier{Email: "user@example.com"},
	auth.PhoneIdentifier{PhoneNumber: "+15555551234"},
	auth.ProviderIdentifier{ProviderID: "google.com", ProviderUID: "google_uid1"},
})
if err != nil {
	log.Fatalf("error retriving multiple users: %v\n", err)
}

log.Printf("Successfully fetched user data:")
for _, u := range getUsersResult.Users {
	log.Printf("%v", u)
}

log.Printf("Unable to find users corresponding to these identifiers:")
for _, id := range getUsersResult.NotFound {
	log.Printf("%v", id)
}

C#

GetUsersResult result = await FirebaseAuth.DefaultInstance.GetUsersAsync(
    new List<UserIdentifier>
    {
        new UidIdentifier("uid1"),
        new EmailIdentifier("user2@example.com"),
        new PhoneIdentifier("+15555550003"),
        new ProviderIdentifier("google.com", "google_uid4"),
    });

Console.WriteLine("Successfully fetched user data:");
foreach (UserRecord user in result.Users)
{
    Console.WriteLine($"User: {user.Uid}");
}

Console.WriteLine("Unable to find users corresponding to these identifiers:");
foreach (UserIdentifier uid in result.NotFound)
{
    Console.WriteLine($"{uid}");
}

這個方法會傳回與輸入清單相同大小的清單,每個項目都包含對應的 UserRecord,或是指出無法查詢該 ID 的原因的錯誤。如需錯誤代碼的完整清單,包括說明和解決步驟,請參閱「Admin Authentication API 錯誤」。

新增使用者

Admin SDK 提供一種方法,可讓您建立新的 Firebase Authentication 使用者。這個方法會接受包含設定檔資訊的物件,並納入新建立的使用者帳戶:

Node.js

getAuth()
  .createUser({
    email: 'user@example.com',
    emailVerified: false,
    phoneNumber: '+11234567890',
    password: 'secretPassword',
    displayName: 'John Doe',
    photoURL: 'http://www.example.com/12345678/photo.png',
    disabled: false,
  })
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log('Successfully created new user:', userRecord.uid);
  })
  .catch((error) => {
    console.log('Error creating new user:', error);
  });

Java

CreateRequest request = new CreateRequest()
    .setEmail("user@example.com")
    .setEmailVerified(false)
    .setPassword("secretPassword")
    .setPhoneNumber("+11234567890")
    .setDisplayName("John Doe")
    .setPhotoUrl("http://www.example.com/12345678/photo.png")
    .setDisabled(false);

UserRecord userRecord = FirebaseAuth.getInstance().createUser(request);
System.out.println("Successfully created new user: " + userRecord.getUid());

Python

user = auth.create_user(
    email='user@example.com',
    email_verified=False,
    phone_number='+15555550100',
    password='secretPassword',
    display_name='John Doe',
    photo_url='http://www.example.com/12345678/photo.png',
    disabled=False)
print('Sucessfully created new user: {0}'.format(user.uid))

Go

params := (&auth.UserToCreate{}).
	Email("user@example.com").
	EmailVerified(false).
	PhoneNumber("+15555550100").
	Password("secretPassword").
	DisplayName("John Doe").
	PhotoURL("http://www.example.com/12345678/photo.png").
	Disabled(false)
u, err := client.CreateUser(ctx, params)
if err != nil {
	log.Fatalf("error creating user: %v\n", err)
}
log.Printf("Successfully created user: %v\n", u)

C#

UserRecordArgs args = new UserRecordArgs()
{
    Email = "user@example.com",
    EmailVerified = false,
    PhoneNumber = "+11234567890",
    Password = "secretPassword",
    DisplayName = "John Doe",
    PhotoUrl = "http://www.example.com/12345678/photo.png",
    Disabled = false,
};
UserRecord userRecord = await FirebaseAuth.DefaultInstance.CreateUserAsync(args);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully created new user: {userRecord.Uid}");

根據預設,Firebase Authentication 會為新使用者產生隨機 uid。如果您想為新使用者指定自己的 uid,可以將其納入傳遞至使用者建立方法的引數:

Node.js

getAuth()
  .createUser({
    uid: 'some-uid',
    email: 'user@example.com',
    phoneNumber: '+11234567890',
  })
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log('Successfully created new user:', userRecord.uid);
  })
  .catch((error) => {
    console.log('Error creating new user:', error);
  });

Java

CreateRequest request = new CreateRequest()
    .setUid("some-uid")
    .setEmail("user@example.com")
    .setPhoneNumber("+11234567890");

UserRecord userRecord = FirebaseAuth.getInstance().createUser(request);
System.out.println("Successfully created new user: " + userRecord.getUid());

Python

user = auth.create_user(
    uid='some-uid', email='user@example.com', phone_number='+15555550100')
print('Sucessfully created new user: {0}'.format(user.uid))

Go

params := (&auth.UserToCreate{}).
	UID(uid).
	Email("user@example.com").
	PhoneNumber("+15555550100")
u, err := client.CreateUser(ctx, params)
if err != nil {
	log.Fatalf("error creating user: %v\n", err)
}
log.Printf("Successfully created user: %v\n", u)

C#

UserRecordArgs args = new UserRecordArgs()
{
    Uid = "some-uid",
    Email = "user@example.com",
    PhoneNumber = "+11234567890",
};
UserRecord userRecord = await FirebaseAuth.DefaultInstance.CreateUserAsync(args);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully created new user: {userRecord.Uid}");

您可以提供下列任意組合的屬性:

表 1. 建立使用者作業支援的屬性

屬性 類型 說明
uid 字串 要指派給新建立使用者的 uid。長度必須介於 1 到 128 個半形字元之間 (含)。如未提供,系統會自動產生隨機 uid。較短的 uid 效能較佳。
email 字串 使用者的主要電子郵件地址。請輸入有效的電子郵件地址。
emailVerified 布林值 使用者的主要電子郵件地址是否已驗證。如未提供,則預設為 false
phoneNumber 字串 使用者的主要電話號碼。必須是符合 E.164 規格的有效電話號碼。
password 字串 使用者未經雜湊處理的原始密碼。長度不得少於六個字元。
displayName 字串 使用者的顯示名稱。
photoURL 字串 使用者的相片網址。
disabled 布林值 使用者是否已停用。true 代表已停用;false 代表已啟用。如未提供,預設值為 false

使用者建立方法會針對新建立的使用者傳回 UserRecord 物件。

如果提供的 uid、電子郵件或電話號碼已由現有使用者使用,或是因其他原因無法建立使用者,上述方法就會失敗並傳回錯誤。如需錯誤代碼的完整清單 (包括說明和解決步驟),請參閱「管理員 Authentication API 錯誤」。

更新使用者

Firebase Admin SDK 可協助您修改現有使用者的資料。您必須指定 uid 和要為該使用者更新的屬性:

Node.js

getAuth()
  .updateUser(uid, {
    email: 'modifiedUser@example.com',
    phoneNumber: '+11234567890',
    emailVerified: true,
    password: 'newPassword',
    displayName: 'Jane Doe',
    photoURL: 'http://www.example.com/12345678/photo.png',
    disabled: true,
  })
  .then((userRecord) => {
    // See the UserRecord reference doc for the contents of userRecord.
    console.log('Successfully updated user', userRecord.toJSON());
  })
  .catch((error) => {
    console.log('Error updating user:', error);
  });

Java

UpdateRequest request = new UpdateRequest(uid)
    .setEmail("user@example.com")
    .setPhoneNumber("+11234567890")
    .setEmailVerified(true)
    .setPassword("newPassword")
    .setDisplayName("Jane Doe")
    .setPhotoUrl("http://www.example.com/12345678/photo.png")
    .setDisabled(true);

UserRecord userRecord = FirebaseAuth.getInstance().updateUser(request);
System.out.println("Successfully updated user: " + userRecord.getUid());

Python

user = auth.update_user(
    uid,
    email='user@example.com',
    phone_number='+15555550100',
    email_verified=True,
    password='newPassword',
    display_name='John Doe',
    photo_url='http://www.example.com/12345678/photo.png',
    disabled=True)
print('Sucessfully updated user: {0}'.format(user.uid))

Go

params := (&auth.UserToUpdate{}).
	Email("user@example.com").
	EmailVerified(true).
	PhoneNumber("+15555550100").
	Password("newPassword").
	DisplayName("John Doe").
	PhotoURL("http://www.example.com/12345678/photo.png").
	Disabled(true)
u, err := client.UpdateUser(ctx, uid, params)
if err != nil {
	log.Fatalf("error updating user: %v\n", err)
}
log.Printf("Successfully updated user: %v\n", u)

C#

UserRecordArgs args = new UserRecordArgs()
{
    Uid = uid,
    Email = "modifiedUser@example.com",
    PhoneNumber = "+11234567890",
    EmailVerified = true,
    Password = "newPassword",
    DisplayName = "Jane Doe",
    PhotoUrl = "http://www.example.com/12345678/photo.png",
    Disabled = true,
};
UserRecord userRecord = await FirebaseAuth.DefaultInstance.UpdateUserAsync(args);
// See the UserRecord reference doc for the contents of userRecord.
Console.WriteLine($"Successfully updated user: {userRecord.Uid}");

您可提供下列屬性的任意組合:

表 2. 更新使用者作業支援的屬性

屬性 類型 說明
email 字串 使用者的新主要電子郵件地址。必須是有效的電子郵件地址。
emailVerified 布林值 使用者的主要電子郵件地址是否已驗證。如未提供,則預設為 false
phoneNumber 字串 使用者新的主要電話號碼。必須是符合 E.164 規格的有效電話號碼。將其設為 null,即可清除使用者現有的電話號碼。
password 字串 使用者新的原始未經雜湊處理的密碼。長度不得少於 6 個字元。
displayName 字串 | null 使用者的新顯示名稱。將其設為 null,即可清除使用者的現有顯示名稱。
photoURL 字串 | null 使用者的新相片網址。將其設為 null,即可清除使用者現有的相片網址。如果不是 null,則必須是有效的網址。
disabled 布林值 使用者是否已停用。true 代表已停用;false 代表已啟用。

更新使用者方法會在更新成功完成時傳回更新的 UserRecord 物件。

如果提供的 uid 與現有使用者不符、提供的電子郵件或電話號碼已由現有使用者使用,或是使用者因其他原因無法更新,上述方法就會失敗並傳回錯誤。如需錯誤代碼的完整清單 (包括說明和解決步驟),請參閱「Admin Authentication API 錯誤」。

刪除使用者

Firebase Admin SDK 可讓您根據 uid 刪除現有使用者:

Node.js

getAuth()
  .deleteUser(uid)
  .then(() => {
    console.log('Successfully deleted user');
  })
  .catch((error) => {
    console.log('Error deleting user:', error);
  });

Java

FirebaseAuth.getInstance().deleteUser(uid);
System.out.println("Successfully deleted user.");

Python

auth.delete_user(uid)
print('Successfully deleted user')

Go

err := client.DeleteUser(ctx, uid)
if err != nil {
	log.Fatalf("error deleting user: %v\n", err)
}
log.Printf("Successfully deleted user: %s\n", uid)

C#

await FirebaseAuth.DefaultInstance.DeleteUserAsync(uid);
Console.WriteLine("Successfully deleted user.");

刪除作業完成後,delete user 方法會傳回空白結果。

如果提供的 uid 未對應至現有使用者,或使用者因其他原因而無法刪除,刪除使用者方法會擲回錯誤。如需錯誤代碼的完整清單,包括說明和解決步驟,請參閱「Admin Authentication API 錯誤」。

刪除多位使用者

Firebase Admin SDK 也可以一次刪除多位使用者。不過,請注意,使用 deleteUsers(uids) 等方法一次刪除多位使用者,並不會觸發 Cloud Functions for FirebaseonDelete() 事件處理常式。這是因為批次刪除不會針對每位使用者觸發使用者刪除事件。如果您希望系統為每位刪除的使用者觸發使用者刪除事件,請逐一刪除使用者。

Node.js

getAuth()
  .deleteUsers([uid1, uid2, uid3])
  .then((deleteUsersResult) => {
    console.log(`Successfully deleted ${deleteUsersResult.successCount} users`);
    console.log(`Failed to delete ${deleteUsersResult.failureCount} users`);
    deleteUsersResult.errors.forEach((err) => {
      console.log(err.error.toJSON());
    });
  })
  .catch((error) => {
    console.log('Error deleting users:', error);
  });

Java

DeleteUsersResult result = FirebaseAuth.getInstance().deleteUsersAsync(
    Arrays.asList("uid1", "uid2", "uid3")).get();

System.out.println("Successfully deleted " + result.getSuccessCount() + " users");
System.out.println("Failed to delete " + result.getFailureCount() + " users");
for (ErrorInfo error : result.getErrors()) {
  System.out.println("error #" + error.getIndex() + ", reason: " + error.getReason());
}

Python

from firebase_admin import auth

result = auth.delete_users(["uid1", "uid2", "uid3"])

print('Successfully deleted {0} users'.format(result.success_count))
print('Failed to delete {0} users'.format(result.failure_count))
for err in result.errors:
    print('error #{0}, reason: {1}'.format(result.index, result.reason))

Go

deleteUsersResult, err := client.DeleteUsers(ctx, []string{"uid1", "uid2", "uid3"})
if err != nil {
	log.Fatalf("error deleting users: %v\n", err)
}

log.Printf("Successfully deleted %d users", deleteUsersResult.SuccessCount)
log.Printf("Failed to delete %d users", deleteUsersResult.FailureCount)
for _, err := range deleteUsersResult.Errors {
	log.Printf("%v", err)
}

C#

DeleteUsersResult result = await FirebaseAuth.DefaultInstance.DeleteUsersAsync(new List<string>
    {
        "uid1",
        "uid2",
        "uid3",
    });

Console.WriteLine($"Successfully deleted {result.SuccessCount} users.");
Console.WriteLine($"Failed to delete {result.FailureCount} users.");

foreach (ErrorInfo err in result.Errors)
{
    Console.WriteLine($"Error #{err.Index}, reason: {err.Reason}");
}

刪除使用者方法會傳回無法刪除使用者失敗的清單。如需完整的錯誤代碼清單 (包括說明和解決步驟),請參閱「Admin Authentication API 錯誤」。

列出所有使用者

Firebase Admin SDK 可讓您分批擷取完整的使用者清單:

Node.js

const listAllUsers = (nextPageToken) => {
  // List batch of users, 1000 at a time.
  getAuth()
    .listUsers(1000, nextPageToken)
    .then((listUsersResult) => {
      listUsersResult.users.forEach((userRecord) => {
        console.log('user', userRecord.toJSON());
      });
      if (listUsersResult.pageToken) {
        // List next batch of users.
        listAllUsers(listUsersResult.pageToken);
      }
    })
    .catch((error) => {
      console.log('Error listing users:', error);
    });
};
// Start listing users from the beginning, 1000 at a time.
listAllUsers();

Java

// Start listing users from the beginning, 1000 at a time.
ListUsersPage page = FirebaseAuth.getInstance().listUsers(null);
while (page != null) {
  for (ExportedUserRecord user : page.getValues()) {
    System.out.println("User: " + user.getUid());
  }
  page = page.getNextPage();
}

// Iterate through all users. This will still retrieve users in batches,
// buffering no more than 1000 users in memory at a time.
page = FirebaseAuth.getInstance().listUsers(null);
for (ExportedUserRecord user : page.iterateAll()) {
  System.out.println("User: " + user.getUid());
}

Python

# Start listing users from the beginning, 1000 at a time.
page = auth.list_users()
while page:
    for user in page.users:
        print('User: ' + user.uid)
    # Get next batch of users.
    page = page.get_next_page()

# Iterate through all users. This will still retrieve users in batches,
# buffering no more than 1000 users in memory at a time.
for user in auth.list_users().iterate_all():
    print('User: ' + user.uid)

Go

// Note, behind the scenes, the Users() iterator will retrive 1000 Users at a time through the API
iter := client.Users(ctx, "")
for {
	user, err := iter.Next()
	if err == iterator.Done {
		break
	}
	if err != nil {
		log.Fatalf("error listing users: %s\n", err)
	}
	log.Printf("read user user: %v\n", user)
}

// Iterating by pages 100 users at a time.
// Note that using both the Next() function on an iterator and the NextPage()
// on a Pager wrapping that same iterator will result in an error.
pager := iterator.NewPager(client.Users(ctx, ""), 100, "")
for {
	var users []*auth.ExportedUserRecord
	nextPageToken, err := pager.NextPage(&users)
	if err != nil {
		log.Fatalf("paging error %v\n", err)
	}
	for _, u := range users {
		log.Printf("read user user: %v\n", u)
	}
	if nextPageToken == "" {
		break
	}
}

C#

// Start listing users from the beginning, 1000 at a time.
var pagedEnumerable = FirebaseAuth.DefaultInstance.ListUsersAsync(null);
var responses = pagedEnumerable.AsRawResponses().GetAsyncEnumerator();
while (await responses.MoveNextAsync())
{
    ExportedUserRecords response = responses.Current;
    foreach (ExportedUserRecord user in response.Users)
    {
        Console.WriteLine($"User: {user.Uid}");
    }
}

// Iterate through all users. This will still retrieve users in batches,
// buffering no more than 1000 users in memory at a time.
var enumerator = FirebaseAuth.DefaultInstance.ListUsersAsync(null).GetAsyncEnumerator();
while (await enumerator.MoveNextAsync())
{
    ExportedUserRecord user = enumerator.Current;
    Console.WriteLine($"User: {user.Uid}");
}

每批結果都包含使用者清單,以及用於列出下一批使用者的下一頁權杖。當所有使用者都已列出時,系統不會傳回 pageToken

如果未指定 maxResults 欄位,系統會使用每批 1000 位使用者的預設值。這也是一次最多可列出的使用者人數。任何大於上限的值都會擲回引數錯誤。如果未指定 pageToken,作業會從頭開始列出使用者,並依 uid 排序。

如需錯誤代碼的完整清單,包括說明和解決步驟,請參閱「Admin Authentication API 錯誤」。

列出使用者的密碼雜湊

如果用於產生要求 OAuth 存取權權杖的使用者/服務帳戶具有 firebaseauth.configs.getHashConfig 權限,這個 API 也會針對使用密碼的使用者,傳回 Firebase Auth 後端經過雜湊處理的 passwordSaltpasswordHash。否則,系統不會設定 passwordHashpasswordSalt

由於密碼雜湊具有敏感性,因此 Firebase Admin SDK 服務帳戶預設不會具備 firebaseauth.configs.getHashConfig 權限。您無法直接為使用者/服務帳戶新增權限,但可以建立自訂 IAM 角色間接執行這項操作。

如何建立自訂身分與存取權管理角色:

  1. 前往 Google Cloud 控制台的「IAM 與管理」面板中的「角色」頁面。
  2. 在頁面頂端的下拉式選單中選取專案。
  3. 按一下「建立角色」
  4. 按一下「新增權限」
  5. 搜尋 firebaseauth.configs.getHashConfig 權限,然後選取該核取方塊。
  6. 按一下「新增」
  7. 按一下「CREATE」,完成建立新角色。

在 IAM 頁面中,將建立的自訂角色新增至使用者/服務帳戶:

  1. 在「IAM 與管理」面板中,選取「身分與存取權管理」
  2. 從成員清單中選取要編輯的服務或使用者帳戶。
  3. 按一下「新增其他角色」
  4. 搜尋先前建立的新自訂角色。
  5. 按一下 [儲存]