# How to Contribute to the Universal Android Debloater Next Generation Project

> Learn how to contribute to the Universal Android Debloater Next Generation project. Fork the Rust workspace, edit the debloat list, test your changes, and submit a pull request.

- Repository: [Universal-Debloater-Alliance/universal-android-debloater-next-generation](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation)
- Tags: how-to-guide
- Published: 2026-06-18

---

**Contributing to UAD-NG requires forking the Rust workspace, editing the JSON debloat list in [`resources/assets/uad_lists.json`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/resources/assets/uad_lists.json), running `cargo test -p uad-core` to validate changes, and submitting a pull request with a Conventional Commit message.**

Universal Android Debloater Next Generation (UAD-NG) is an open-source Rust workspace that provides both a GUI and CLI for removing bloatware from Android devices. The project organizes its code into three specialized crates and stores its debloat definitions in a centralized JSON file. Whether you want to add a new package to the database or improve the tooling, this guide covers the exact workflow used by the maintainers.

## Understanding the Rust Workspace Architecture

UAD-NG is organized as a Cargo workspace defined in the root [`Cargo.toml`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/Cargo.toml). The codebase splits responsibilities across three distinct crates:

- **`uad-core`** – Contains the core logic for package metadata, ADB communication, and list loading. The main entry point is [`crates/uad-core/src/lib.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/lib.rs), with list parsing logic residing in [`crates/uad-core/src/uad_lists.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/uad_lists.rs).

- **`uad-gui`** – Implements the native graphical interface using the **iced** UI library. The application starts at [`crates/uad-gui/src/main.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-gui/src/main.rs).

- **`uad-cli`** – Provides the command-line interface that drives core functionality via ADB. Entry point is [`crates/uad-cli/src/main.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-cli/src/main.rs), with command implementations in [`crates/uad-cli/src/commands.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-cli/src/commands.rs).

The workspace uses **Rust 2024 edition** and depends on crates such as `clap`, `tokio`, and `iced`.

## Repository Structure and Key Files

Before contributing, familiarize yourself with these critical paths:

```

├─ Cargo.toml                ← Workspace definition and shared dependencies
├─ CONTRIBUTING.md           ← Official contribution guidelines (must read)
├─ resources/
│  └─ assets/uad_lists.json  ← Master debloat database (bundled at compile-time)
├─ crates/
│  ├─ uad-core/              ← Core library with ADB helpers
│  ├─ uad-gui/               ← GUI application
│  └─ uad-cli/               ← CLI application
└─ .github/workflows/ci.yml  ← CI pipeline requiring format, clippy, and test pass

```

The [`uad_lists.json`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/uad_lists.json) file serves as the canonical database. The `uad-core` crate loads it via `include_str!` for offline operation, or fetches remote updates from GitHub's raw content URL when online.

## Adding a New Package to the Debloat List

The most common contribution is adding a new Android package to the database. The JSON format follows the `Package` struct defined in [`crates/uad-core/src/uad_lists.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-core/src/uad_lists.rs):

```rust
#[derive(Deserialize, Debug, Clone, PartialEq, Hash, Eq)]
pub struct Package {
    pub list:        UadList,      // e.g., Aosp, Oem, Carrier, etc.
    pub description: String,
    dependencies:    Vec<String>,
    needed_by:       Vec<String>,
    labels:          Vec<String>,
    pub removal:    Removal,       // Recommended / Advanced / Unsafe / etc.
}

```

Follow these steps to propose a new package:

1. **Fork and branch** – Fork the repository on GitHub and create a branch following the trunk-based naming convention, such as `package/1234-add-my-app`.

2. **Edit the JSON** – Add your entry to [`resources/assets/uad_lists.json`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/resources/assets/uad_lists.json). Maintain alphabetical order for readability. Example entry:

   ```json
   "com.example.myapp": {
     "list": "Oem",
     "description": "My example app – safe to remove if you use an alternative.",
     "dependencies": [],
     "neededBy": [],
     "labels": [],
     "removal": "Recommended"
   }
   ```

3. **Validate locally** – Run the core tests to verify JSON syntax:

   ```bash
   cargo test -p uad-core
   ```

   This executes the `test_parse_json` test in [`uad_lists.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/uad_lists.rs), which validates that the JSON remains syntactically correct.

4. **Commit with Conventional Commits** – Use the format specified in [`CONTRIBUTING.md`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/CONTRIBUTING.md):

   ```

   feat(package):: add com.example.myapp
   ```

5. **Open a Pull Request** – Use the PR template for package additions. The CI workflow ([`.github/workflows/ci.yml`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/.github/workflows/ci.yml)) automatically runs formatting, clippy, and tests across all three crates.

## Development Workflow and Testing

Use these commands to build, test, and validate your changes locally:

| Action | Command |
|--------|---------|
| Build all crates | `cargo build --workspace` |
| Run the CLI in debug mode | `cargo run -p uad-cli -- --help` |
| Run the GUI application | `cargo run -p uad-gui` |
| Run core unit tests | `cargo test -p uad-core` |
| Format code | `cargo fmt` |
| Lint with clippy | `cargo clippy --workspace -- -D warnings` |
| Force update debloat list | `cargo run -p uad-cli -- update` |
| Generate shell completions | `cargo run -p uad-cli -- completions bash > uad.bash` |

All CI checks must pass before merging. The pipeline enforces `cargo fmt` for formatting, `cargo clippy` for linting, and `cargo test` for validation.

## Programmatic List Updates

If you need to update the list from a script or batch-add packages, use the core library's loading logic:

```rust
use uad_core::uad_lists::{load_debloat_lists, PackageHashMap};

fn update_list(remote: bool) -> anyhow::Result<PackageHashMap> {
    // Setting remote=true fetches latest JSON from GitHub, falling back to bundled data
    load_debloat_lists(true).map_err(|e| anyhow::anyhow!("Failed to load: {:?}", e))
}

```

The CLI wraps this functionality in `commands::update_lists()` (located in [`crates/uad-cli/src/commands.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-cli/src/commands.rs)), accessible via `cargo run -p uad-cli -- update`.

## Summary

- **UAD-NG** is a Rust workspace with three crates: `uad-core` (logic), `uad-gui` (iced UI), and `uad-cli` (command-line tools).
- **Package contributions** require editing [`resources/assets/uad_lists.json`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/resources/assets/uad_lists.json) and passing the `test_parse_json` validation.
- **Development workflow** relies on standard Cargo commands (`cargo build --workspace`, `cargo test -p uad-core`).
- **Quality gates** include `cargo fmt`, `cargo clippy`, and the CI pipeline defined in [`.github/workflows/ci.yml`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/.github/workflows/ci.yml).
- **Commit standards** follow Conventional Commits (e.g., `feat(package):: add com.example.app`).

## Frequently Asked Questions

### What Rust version is required to build UAD-NG?

The project uses **Rust 2024 edition**. You should install the latest stable Rust toolchain via `rustup` to ensure compatibility with the workspace dependencies and edition features.

### How do I test package removals without affecting my device?

Use the CLI's dry-run mode. The `change_package_state` function in [`crates/uad-cli/src/commands.rs`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/crates/uad-cli/src/commands.rs) supports simulation:

```bash
cargo run -p uad-cli -- uninstall com.example.myapp --dry-run

```

This outputs the exact ADB command that would execute without actually running it.

### Can I contribute only to the CLI or GUI without touching the core?

Yes. Since the workspace separates concerns into distinct crates, you can modify `uad-cli` (in `crates/uad-cli/src/`) or `uad-gui` (in `crates/uad-gui/src/`) independently. However, any changes to shared logic in `uad-core` will affect both interfaces, so run `cargo test --workspace` to verify integration.

### Where do I find the commit message format requirements?

The [`CONTRIBUTING.md`](https://github.com/Universal-Debloater-Alliance/universal-android-debloater-next-generation/blob/main/CONTRIBUTING.md) file at the repository root defines the Conventional Commit specification used by the project. It requires lowercase types (e.g., `feat`, `fix`) and optional scope tags for categorizing changes (e.g., `feat(package)::`, `fix(gui)::`).