aboutsummaryrefslogtreecommitdiff
path: root/azalea-client/src
diff options
context:
space:
mode:
authorAdam Reisenauer <58893124+Mythbusters123@users.noreply.github.com>2023-06-24 18:09:43 -0400
committerGitHub <noreply@github.com>2023-06-24 17:09:43 -0500
commit5e4699688207b8ac722ae7f96c49428242f49a9d (patch)
tree52b0f9b8507fa380376dab81411cb74eed413c95 /azalea-client/src
parentfe687f9bdbdf3e0214ac4ac6da47a181e4dc23dd (diff)
downloadazalea-drasl-5e4699688207b8ac722ae7f96c49428242f49a9d.tar.xz
Add functions `auth_with_link_code`, `get_ms_link_code`, and `get_ms_auth_token`. (#88)
* Add option for grabbing authentication code for Microsoft seperately. Created two new functions, one that outputs the DeviceCodeResponse and one that uses this response to authenticate an actual account. * Added documentation and cleaned up function names. Still wondering about code repeition * reduce code duplication, more docs, cleanup * clippy --------- Co-authored-by: mat <git@matdoes.dev>
Diffstat (limited to 'azalea-client/src')
-rwxr-xr-xazalea-client/src/account.rs89
-rw-r--r--azalea-client/src/inventory.rs2
2 files changed, 77 insertions, 14 deletions
diff --git a/azalea-client/src/account.rs b/azalea-client/src/account.rs
index 5c6056c1..2d1b766c 100755
--- a/azalea-client/src/account.rs
+++ b/azalea-client/src/account.rs
@@ -4,6 +4,7 @@ use std::sync::Arc;
use crate::get_mc_dir;
use azalea_auth::certs::{Certificates, FetchCertificatesError};
+use azalea_auth::AccessTokenResponse;
use parking_lot::Mutex;
use thiserror::Error;
use uuid::Uuid;
@@ -55,8 +56,15 @@ pub struct Account {
/// The parameters that were passed for creating the associated [`Account`].
#[derive(Clone, Debug)]
pub enum AccountOpts {
- Offline { username: String },
- Microsoft { email: String },
+ Offline {
+ username: String,
+ },
+ Microsoft {
+ email: String,
+ },
+ MicrosoftWithAccessToken {
+ msa: Arc<Mutex<azalea_auth::cache::ExpiringValue<AccessTokenResponse>>>,
+ },
}
impl Account {
@@ -106,27 +114,82 @@ impl Account {
})
}
+ /// This will create an online-mode account through
+ /// [`azalea_auth::get_minecraft_token`] so you can have more control over
+ /// the authentication process (like doing your own caching or
+ /// displaying the Microsoft user code to the user in a different way).
+ ///
+ /// Note that this will not refresh the token when it expires.
+ ///
+ /// ```
+ /// # use azalea_client::Account;
+ /// # async fn example() -> Result<(), Box<dyn std::error::Error>> {
+ /// let client = reqwest::Client::new();
+ ///
+ /// let res = azalea_auth::get_ms_link_code(&client).await?;
+ /// println!(
+ /// "Go to {} and enter the code {}",
+ /// res.verification_uri, res.user_code
+ /// );
+ /// let msa = azalea_auth::get_ms_auth_token(&client, res).await?;
+ /// Account::with_microsoft_access_token(msa).await?;
+ /// # Ok(())
+ /// # }
+ /// ```
+ pub async fn with_microsoft_access_token(
+ mut msa: azalea_auth::cache::ExpiringValue<AccessTokenResponse>,
+ ) -> Result<Self, azalea_auth::AuthError> {
+ let client = reqwest::Client::new();
+
+ if msa.is_expired() {
+ log::trace!("refreshing Microsoft auth token");
+ msa = azalea_auth::refresh_ms_auth_token(&client, &msa.data.refresh_token).await?;
+ }
+
+ let msa_token = &msa.data.access_token;
+
+ let res = azalea_auth::get_minecraft_token(&client, msa_token).await?;
+
+ let profile = azalea_auth::get_profile(&client, &res.minecraft_access_token).await?;
+
+ Ok(Self {
+ username: profile.name,
+ access_token: Some(Arc::new(Mutex::new(res.minecraft_access_token))),
+ uuid: Some(profile.id),
+ account_opts: AccountOpts::MicrosoftWithAccessToken {
+ msa: Arc::new(Mutex::new(msa)),
+ },
+ certs: None,
+ })
+ }
/// Refresh the access_token for this account to be valid again.
///
/// This requires the `auth_opts` field to be set correctly (which is done
/// by default if you used the constructor functions). Note that if the
- /// Account is offline-mode, this function won't do anything.
+ /// Account is offline-mode then this function won't do anything.
pub async fn refresh(&self) -> Result<(), azalea_auth::AuthError> {
match &self.account_opts {
// offline mode doesn't need to refresh so just don't do anything lol
AccountOpts::Offline { .. } => Ok(()),
AccountOpts::Microsoft { email } => {
let new_account = Account::microsoft(email).await?;
- let access_token = self
- .access_token
- .as_ref()
- .expect("Access token should always be set for Microsoft accounts");
- let new_access_token = new_account
- .access_token
- .expect("Access token should always be set for Microsoft accounts")
- .lock()
- .clone();
- *access_token.lock() = new_access_token;
+ let access_token_mutex = self.access_token.as_ref().unwrap();
+ let new_access_token = new_account.access_token.unwrap().lock().clone();
+ *access_token_mutex.lock() = new_access_token;
+ Ok(())
+ }
+ AccountOpts::MicrosoftWithAccessToken { msa } => {
+ let msa_value = msa.lock().clone();
+ let new_account = Account::with_microsoft_access_token(msa_value).await?;
+
+ let access_token_mutex = self.access_token.as_ref().unwrap();
+ let new_access_token = new_account.access_token.unwrap().lock().clone();
+
+ *access_token_mutex.lock() = new_access_token;
+ let AccountOpts::MicrosoftWithAccessToken { msa: new_msa } =
+ new_account.account_opts else { unreachable!() };
+ *msa.lock() = new_msa.lock().clone();
+
Ok(())
}
}
diff --git a/azalea-client/src/inventory.rs b/azalea-client/src/inventory.rs
index f8c2b2a4..b7269ef1 100644
--- a/azalea-client/src/inventory.rs
+++ b/azalea-client/src/inventory.rs
@@ -79,7 +79,7 @@ pub struct InventoryComponent {
/// The item that is currently held by the cursor. `Slot::Empty` if nothing
/// is currently being held.
///
- /// This is different from [`Self::hotbar_selected_index`], which is the
+ /// This is different from [`Self::selected_hotbar_slot`], which is the
/// item that's selected in the hotbar.
pub carried: ItemSlot,
/// An identifier used by the server to track client inventory desyncs. This