[Security] Redact sensitive user data from client-visible responses (#7077)
Some checks are pending
Build Desktop / Configure (push) Waiting to run
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Debian, DEB, 13) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Debian, DEB, skip, 12) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Fedora, RPM, 44) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Fedora, RPM, skip, 43) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Servatrice_Debian, DEB, yes, skip, 12) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Ubuntu, DEB, 26.04) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (Ubuntu, DEB, skip, 24.04) (push) Blocked by required conditions
Build Desktop / ${{ matrix.distro }} ${{ matrix.version }} (yes, Arch, skip) (push) Blocked by required conditions
Build Desktop / ${{ matrix.os }} ${{ matrix.target }}${{ matrix.soc == 'Intel' && ' Intel' || '' }}${{ matrix.type == 'Debug' && ' Debug' || '' }} (7d, Ninja, 1, macOS, -macOS14, qtimageformats qtmultimedia qtwebsockets, 6.11.0, macos-14, Apple, 14, Release, 1, 15.4) (push) Blocked by required conditions
Build Desktop / ${{ matrix.os }} ${{ matrix.target }}${{ matrix.soc == 'Intel' && ' Intel' || '' }}${{ matrix.type == 'Debug' && ' Debug' || '' }} (7d, Ninja, 1, macOS, -macOS15, qtimageformats qtmultimedia qtwebsockets, 6.11.0, macos-15, Apple, 15, Release, 1, 16.4) (push) Blocked by required conditions
Build Desktop / ${{ matrix.os }} ${{ matrix.target }}${{ matrix.soc == 'Intel' && ' Intel' || '' }}${{ matrix.type == 'Debug' && ' Debug' || '' }} (7d, Ninja, 1, macOS, 13, -macOS13_Intel, qtimageformats qtmultimedia qtwebsockets, 6.11.0, macos-15-intel, Intel, 13, Re… (push) Blocked by required conditions
Build Desktop / ${{ matrix.os }} ${{ matrix.target }}${{ matrix.soc == 'Intel' && ' Intel' || '' }}${{ matrix.type == 'Debug' && ' Debug' || '' }} (7d, Ninja, macOS, qtimageformats qtmultimedia qtwebsockets, 6.11.0, macos-15, Apple, 15, Debug, 1, 16.4) (push) Blocked by required conditions
Build Desktop / ${{ matrix.os }} ${{ matrix.target }}${{ matrix.soc == 'Intel' && ' Intel' || '' }}${{ matrix.type == 'Debug' && ' Debug' || '' }} (Visual Studio 18 2026, x64, 1, Windows, -Win10, qtimageformats qtmultimedia qtwebsockets, 6.11.0, windows-2025, 10, Rele… (push) Blocked by required conditions
Build Docker Image / amd64 & arm64 (push) Waiting to run

The getUserInfo command for a user that is not currently online returned
the full database record, including the account id, the email address
and the stored client id, to any logged-in requester. Mirror the
redaction already applied to online users via copyUserInfo(): the id and
email are only ever exposed to the account owner, and the client id only
to moderators.

The buddy/ignore add-to-list event likewise returned the target user's
email address and client id to the requester. The list entry only needs
the public profile fields, so strip the email and client id from it as
well.

Co-authored-by: Lukas Brübach <Bruebach.Lukas@bdosecurity.de>
This commit is contained in:
BruebachL
2026-08-08 17:32:39 +02:00
committed by GitHub
parent 0d14fb77a0
commit 27fb5e51de
2 changed files with 13 additions and 0 deletions

View File

@@ -685,6 +685,15 @@ Response::ResponseCode Server_ProtocolHandler::cmdGetUserInfo(const Command_GetU
ServerInfo_User_Container *infoSource = server->findUser(userName);
if (!infoSource) {
re->mutable_user_info()->CopyFrom(databaseInterface->getUserData(userName, true));
// The user is not currently online. Mirror the redaction that
// copyUserInfo() applies to online users: the id and email address
// are only ever visible to the account owner, and the client id
// only to moderators.
re->mutable_user_info()->clear_id();
re->mutable_user_info()->clear_email();
if (!(userInfo->user_level() & ServerInfo_User::IsModerator)) {
re->mutable_user_info()->clear_clientid();
}
} else {
re->mutable_user_info()->CopyFrom(
infoSource->copyUserInfo(true, false, userInfo->user_level() & ServerInfo_User::IsModerator));

View File

@@ -325,6 +325,10 @@ Response::ResponseCode AbstractServerSocketInterface::cmdAddToList(const Command
Event_AddToList event;
event.set_list_name(cmd.list());
event.mutable_user_info()->CopyFrom(databaseInterface->getUserData(user));
// The buddy/ignore list entry is only used to display the user's basic
// profile: never leak the target's email address or client id.
event.mutable_user_info()->clear_email();
event.mutable_user_info()->clear_clientid();
rc.enqueuePreResponseItem(ServerMessage::SESSION_EVENT, prepareSessionEvent(event));
return Response::RespOk;