# How Universal Android Debloater Next Generation Supports Multi-User Android Devices and User Enumeration

> Discover how Universal Android Debloater Next Generation manages multi-user devices with per-user package control via ADB. Protects work profiles and supports all user profiles.

- Repository: [Universal-Debloater-Alliance/universal-android-debloater-next-generation](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation)
- Tags: deep-dive
- Published: 2026-06-20

---

**Universal Android Debloater Next Generation (UAD-NG) treats every connected device as a `Phone` struct containing a `Vec<User>` populated via ADB queries, enabling granular per-user package management while automatically protecting work-profile users and supporting bulk operations across all device profiles.**

Managing Android devices with multiple user profiles requires careful handling of user IDs, protected system accounts, and cross-user package dependencies. The Universal Android Debloater Next Generation (UAD-NG) implements a robust multi-user architecture in its Rust codebase, modeling each device as a structured object that enumerates all Android users before executing any debloating commands. This design allows administrators to target specific users or apply changes globally while preventing accidental modification of protected work profiles.

## Core Data Structures for Multi-User Devices

UAD-NG defines its multi-user capabilities through two primary structures located in [`crates/uad-core/src/sync.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/sync.rs).

The **`Phone`** struct represents the physical device and contains a `user_list: Vec<User>` field that holds all enumerated accounts. When a device connects, the application populates this vector by querying the Android Package Manager through ADB.

The **`User`** struct tracks individual Android users with three critical fields:

- **`id`**: The actual Android user ID (integer) used in ADB commands
- **`index`**: The position within the user_list vector for UI reference
- **`protected`**: A boolean flag indicating system or work-profile users that cannot be modified

```rust
use uad_core::sync::{Phone, User};

fn printable_users(phone: &Phone) -> Vec<String> {
    phone.user_list
        .iter()
        .filter(|u| !u.protected)          // hide work‑profile or system users
        .map(|u| format!("user {} (index {})", u.id, u.index))
        .collect()
}

```

## Enumerating Android Users via ADB

User enumeration occurs immediately upon device detection. The system queries ADB using package manager commands to discover all valid user profiles on the device.

According to the source code in [`crates/uad-core/src/adb.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/adb.rs), the enumeration process runs `pm list users` or validates users via `pm list packages --user <id>` to test each potential ID. Successful queries populate the `Phone.user_list` with `User` structs, while failed queries indicate protected or invalid user slots.

This enumeration enables the GUI in [`crates/uad-gui/src/views/list.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-gui/src/views/list.rs) to display a radio-button pick-list populated from `selected_device.user_list.clone()`, allowing operators to select specific targets before executing commands.

## Detecting Multi-User Capability

Not all Android devices support multiple users. UAD-NG implements version-gated detection through the `supports_multi_user(dev: &Phone) -> bool` function in [`crates/uad-core/src/sync.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/sync.rs).

The function checks if `dev.android_sdk >= 21`, corresponding to Android Lollipop (API level 21). When this returns false, the UI disables the multi-user toggle in [`crates/uad-gui/src/views/settings.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-gui/src/views/settings.rs), preventing operators from attempting unsupported operations on older devices.

```rust
use uad_core::sync::{Phone, supports_multi_user};

let phone = Phone::default();               // Filled elsewhere after ADB detection
if supports_multi_user(&phone) {
    println!("Device may have multiple users (SDK ≥ 21)");
}

```

## Building User-Specific ADB Commands

When executing package operations, UAD-NG constructs ADB commands that include the `--user` flag to target specific profiles. The `user_flag(user: Option<User>) -> String` function in [`crates/uad-core/src/sync.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/sync.rs) returns `--user <id>` when a user is specified, or an empty string for device-wide operations.

The `apply_pkg_state_commands` function receives the `selected_user: User` and builds per-user command sequences. If **Multi-User Mode** is enabled via the settings checkbox (`self.device.multi_user_mode`), the system iterates through all non-protected users in `user_list` and dispatches the same command to each, effectively debloating all profiles simultaneously.

```rust
use uad_core::sync::{apply_pkg_state_commands, request_builder, user_flag, User};

let user = User { id: 10, index: 2, protected: false };
let commands = apply_pkg_state_commands(&core_pkg, PackageState::Uninstalled, user, &phone);
let adb_cmds = request_builder(&commands, &core_pkg.name, Some(user));
// adb_cmds now contain strings like "pm uninstall --user 10 com.example.app"

```

## Protecting System and Work-Profile Users

UAD-NG safeguards critical user profiles through the `is_protected_user(user_id, device_serial)` function in [`crates/uad-core/src/sync.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/sync.rs). This validation attempts to run `pm list packages -s --user <id>`; if the call fails, the user is marked as protected (typically indicating a work profile or restricted system user).

Protected users are filtered from the selection UI in [`crates/uad-gui/src/views/list.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-gui/src/views/list.rs) and are automatically excluded from bulk operations even when Multi-User Mode is active. This prevents accidental modification of corporate work profiles or restricted accounts that could violate MDM policies or brick the device.

## Detecting Cross-User Behavior

Android packages often exhibit cross-user dependencies where removing an app from one profile affects its availability in others. UAD-NG monitors these interactions through the `detect_cross_user_behavior` function in [`crates/uad-core/src/sync.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/sync.rs).

After package operations complete, the system checks whether the package appears or disappears on other user profiles. When cross-user restoration or uninstallation is detected, the application warns the operator, providing visibility into system-wide package changes that might otherwise appear unexpected.

## Summary

- **Device Modeling**: UAD-NG represents devices as `Phone` structs containing a vector of `User` structs, enabling structured multi-user management.
- **User Enumeration**: The system queries ADB via `pm list users` and `pm list packages --user` commands in [`crates/uad-core/src/adb.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/adb.rs) to populate the user list.
- **Version Detection**: Multi-user support is gated by `supports_multi_user`, which verifies `android_sdk >= 21` before enabling related UI features.
- **Command Construction**: The `user_flag` and `apply_pkg_state_commands` functions inject `--user <id>` flags into ADB commands for precise targeting.
- **Protection Mechanisms**: Work-profile and system users are identified via `is_protected_user` and automatically excluded from modification operations.
- **Cross-User Awareness**: The `detect_cross_user_behavior` function monitors package state changes across profiles to prevent unintended side effects.

## Frequently Asked Questions

### How does UAD-NG handle work profile users?

Work profile users are detected as protected accounts through the `is_protected_user` function, which attempts to list packages for the specific user ID and marks the user as protected if the ADB call fails. These users are hidden from the selection UI and excluded from bulk operations to prevent corporate policy violations or device instability.

### What Android version is required for multi-user support in UAD-NG?

UAD-NG requires Android Lollipop (API level 21) or higher for multi-user capabilities. The `supports_multi_user` function checks the device's `android_sdk` field, and the GUI disables the "Affect all users" checkbox on devices running older versions.

### Can I apply debloating actions to all users at once?

Yes. When you enable the **"Affect all the users of the device"** checkbox in [`crates/uad-gui/src/views/settings.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-gui/src/views/settings.rs), UAD-NG iterates through all non-protected users in `Phone.user_list` and dispatches the same ADB command to each user ID, appending the `--user` flag to each invocation.

### How does the application detect if a package operation affected other users?

After executing commands, UAD-NG runs `detect_cross_user_behavior` to check if the target package's state changed on other user profiles. If the package disappeared from or appeared on additional users, the system reports cross-user uninstallation or restoration, alerting you to system-wide changes.