Load the token from the keychain, refresh the token if it is expired and return it
(
database: &Database,
telemetry: Option<&crate::telemetry::TelemetryThread>,
)
| 318 | |
| 319 | /// Load the token from the keychain, refresh the token if it is expired and return it |
| 320 | pub async fn load( |
| 321 | database: &Database, |
| 322 | telemetry: Option<&crate::telemetry::TelemetryThread>, |
| 323 | ) -> Result<Option<Self>, AuthError> { |
| 324 | // Can't use #[cfg(test)] without breaking lints, and we don't want to require |
| 325 | // authentication in order to run ChatSession tests. Hence, adding this here with cfg!(test) |
| 326 | if cfg!(test) && !is_integ_test() { |
| 327 | return Ok(Some(Self { |
| 328 | access_token: Secret("test_access_token".to_string()), |
| 329 | expires_at: time::OffsetDateTime::now_utc() + time::Duration::minutes(60), |
| 330 | refresh_token: Some(Secret("test_refresh_token".to_string())), |
| 331 | region: Some(OIDC_BUILDER_ID_REGION.to_string()), |
| 332 | start_url: Some(START_URL.to_string()), |
| 333 | oauth_flow: OAuthFlow::DeviceCode, |
| 334 | scopes: Some(SCOPES.iter().map(|s| (*s).to_owned()).collect()), |
| 335 | })); |
| 336 | } |
| 337 | |
| 338 | trace!("loading builder id token from the secret store"); |
| 339 | match database.get_secret(Self::SECRET_KEY).await { |
| 340 | Ok(Some(secret)) => { |
| 341 | let token: Option<Self> = serde_json::from_str(&secret.0)?; |
| 342 | match token { |
| 343 | Some(token) => { |
| 344 | let region = token.region.clone().map_or(OIDC_BUILDER_ID_REGION, Region::new); |
| 345 | let client = client(region.clone()); |
| 346 | |
| 347 | if token.is_expired() { |
| 348 | trace!("token is expired, refreshing"); |
| 349 | token.refresh_token(&client, database, ®ion, telemetry).await |
| 350 | } else { |
| 351 | trace!(?token, "found a valid token"); |
| 352 | Ok(Some(token)) |
| 353 | } |
| 354 | }, |
| 355 | None => { |
| 356 | debug!("secret stored in the database was empty"); |
| 357 | Ok(None) |
| 358 | }, |
| 359 | } |
| 360 | }, |
| 361 | Ok(None) => { |
| 362 | debug!("no secret found in the database"); |
| 363 | Ok(None) |
| 364 | }, |
| 365 | Err(err) => { |
| 366 | error!(%err, "Error getting builder id token from keychain"); |
| 367 | Err(err)? |
| 368 | }, |
| 369 | } |
| 370 | } |
| 371 | |
| 372 | /// Refresh the access token |
| 373 | pub async fn refresh_token( |
no test coverage detected