A collection of Rust crates for making Minecraft bots, clients, and tools.
Find a file
2022-04-30 17:55:18 -05:00
.vscode simplify error handling 2022-04-22 04:33:58 +00:00
azalea-auth upgrade aes and cfb8 2022-04-29 20:20:56 -05:00
azalea-brigadier simplify error handling 2022-04-22 04:33:58 +00:00
azalea-chat simplify error handling 2022-04-22 04:33:58 +00:00
azalea-client gitignore flamegraph stuff 2022-04-30 17:55:18 -05:00
azalea-core finish update recipes packet implementation 2022-04-26 19:38:07 -05:00
azalea-nbt fix warnings in azalea-nbt 2022-04-24 14:56:46 -05:00
azalea-protocol fix error that happens in linux + release mode 2022-04-30 16:56:59 -05:00
bot gitignore flamegraph stuff 2022-04-30 17:55:18 -05:00
.gitignore gitignore flamegraph stuff 2022-04-30 17:55:18 -05:00
.gitpod.yml simplify error handling 2022-04-22 04:33:58 +00:00
Cargo.lock Merge branch 'main' into chunk-packets 2022-04-29 20:22:26 -05:00
Cargo.toml gitignore flamegraph stuff 2022-04-30 17:55:18 -05:00
README.md Merge branch 'main' into chunk-packets 2022-04-29 20:22:26 -05:00

Azalea

A Rust library for creating Minecraft bots.

I named this Azalea because it sounds like a cool word and this is a cool library. This project was heavily inspired by PrismarineJS.

Goals

  • Do everything a vanilla client can do
  • Be easy to use
  • Bypass most/all anticheats
  • Support the latest Minecraft version
  • Be fast

Example code

Note that these doesn't work yet, it's just how I want the API to look.

use azalea::{Account, Event};

let account = Account::offline("bot");
// or let account = azalea::Account::microsoft("access token").await;

let bot = account.join("localhost".try_into().unwrap()).await.unwrap();

loop {
    match bot.next().await {
        Event::Message(m) {
            if m.username == bot.username { return };
            bot.chat(m.message).await;
        },
        Event::Kicked(m) {
            println!(m);
            bot.reconnect().await.unwrap();
        },
        _ => {}
    }
}
use azalea::{Bot, Event};

let bot = Bot::offline("bot");
// or let bot = azalea::Bot::microsoft("access token").await;

bot.join("localhost".try_into().unwrap()).await.unwrap();

loop {
    match bot.recv().await {
        Event::Message(m) {
            if m.username == bot.username { return };
            if m.message = "go" {
                bot.goto_goal(
                    pathfinder::Goals::NearXZ(5, azalea::BlockXZ(0, 0))
                ).await;
                let chest = bot.open_chest(&bot.world.find_one_block(|b| b.id == "minecraft:chest")).await.unwrap();
                bot.take_amount(&chest, 3, |i| i.id == "#minecraft:planks").await;
                // when rust adds async drop this won't be necessary
                chest.close().await;

                let crafting_table = bot.open_crafting_table(&bot.world.find_one_block(|b| b.id == "minecraft:crafting_table")).await.unwrap();
                bot.craft(&crafting_table, &bot.recipe_for("minecraft:sticks")).await?;
                let pickaxe = bot.craft(&crafting_table, &bot.recipe_for("minecraft:wooden_pickaxe")).await?;
                crafting_table.close().await;

                bot.hold(&pickaxe);
                loop {
                    if let Err(e) = bot.dig(bot.feet_coords().down(1)).await {
                        println!("{:?}", e);
                        break;
                    }
                }
            }
        },
        _ => {}
    }
}

You can use the azalea::Bots struct to control many bots as one unit.

use azalea::{Account, Accounts, Event, pathfinder};

#[tokio::main]
async fn main() {
    let accounts = Accounts::new();

    for i in 0..10 {
        accounts.add(Account::offline(format!("bot{}", i)));
    }

    let bots = accounts.join("localhost".try_into().unwrap()).await.unwrap();

    bots.goto(azalea::BlockCoord(0, 70, 0)).await;
    // or bots.goto_goal(pathfinder::Goals::Goto(azalea::BlockCoord(0, 70, 0))).await;

    // destroy the blocks in this area and then leave

    bots.fill(
        azalea::Selection::Range(
            azalea::BlockCoord(0, 0, 0),
            azalea::BlockCoord(16, 255, 16)
        ),
        azalea::block::Air
    ).await;
}