Add a stringified credential option for LedgerStorage (#24314)
* add a stringified credential option for LedgerStorage * fix clippy::useless-format warning * change CredentialOption to enum CredentialType * rename credential_option to credential_type * restore LedgerStorage new fn signature * fmt Co-authored-by: Tyera Eulberg <tyera@solana.com>
This commit is contained in:
parent
e146e860e2
commit
aea17c35ae
|
@ -16,6 +16,7 @@ use {
|
||||||
},
|
},
|
||||||
solana_ledger::{blockstore::Blockstore, blockstore_db::AccessType},
|
solana_ledger::{blockstore::Blockstore, blockstore_db::AccessType},
|
||||||
solana_sdk::{clock::Slot, pubkey::Pubkey, signature::Signature},
|
solana_sdk::{clock::Slot, pubkey::Pubkey, signature::Signature},
|
||||||
|
solana_storage_bigtable::CredentialType,
|
||||||
solana_transaction_status::{
|
solana_transaction_status::{
|
||||||
BlockEncodingOptions, ConfirmedBlock, EncodeError, TransactionDetails,
|
BlockEncodingOptions, ConfirmedBlock, EncodeError, TransactionDetails,
|
||||||
UiTransactionEncoding,
|
UiTransactionEncoding,
|
||||||
|
@ -642,16 +643,18 @@ pub fn bigtable_process_command(ledger_path: &Path, matches: &ArgMatches<'_>) {
|
||||||
instance_name,
|
instance_name,
|
||||||
..solana_storage_bigtable::LedgerStorageConfig::default()
|
..solana_storage_bigtable::LedgerStorageConfig::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let credential_path = Some(value_t_or_exit!(
|
let credential_path = Some(value_t_or_exit!(
|
||||||
arg_matches,
|
arg_matches,
|
||||||
"reference_credential",
|
"reference_credential",
|
||||||
String
|
String
|
||||||
));
|
));
|
||||||
|
|
||||||
let ref_instance_name =
|
let ref_instance_name =
|
||||||
value_t_or_exit!(arg_matches, "reference_instance_name", String);
|
value_t_or_exit!(arg_matches, "reference_instance_name", String);
|
||||||
let ref_config = solana_storage_bigtable::LedgerStorageConfig {
|
let ref_config = solana_storage_bigtable::LedgerStorageConfig {
|
||||||
read_only: false,
|
read_only: false,
|
||||||
credential_path,
|
credential_type: CredentialType::Filepath(credential_path),
|
||||||
instance_name: ref_instance_name,
|
instance_name: ref_instance_name,
|
||||||
..solana_storage_bigtable::LedgerStorageConfig::default()
|
..solana_storage_bigtable::LedgerStorageConfig::default()
|
||||||
};
|
};
|
||||||
|
|
|
@ -37,6 +37,7 @@ use {
|
||||||
native_token::lamports_to_sol, pubkey::Pubkey,
|
native_token::lamports_to_sol, pubkey::Pubkey,
|
||||||
},
|
},
|
||||||
solana_send_transaction_service::send_transaction_service::{self, SendTransactionService},
|
solana_send_transaction_service::send_transaction_service::{self, SendTransactionService},
|
||||||
|
solana_storage_bigtable::CredentialType,
|
||||||
std::{
|
std::{
|
||||||
collections::HashSet,
|
collections::HashSet,
|
||||||
net::SocketAddr,
|
net::SocketAddr,
|
||||||
|
@ -385,7 +386,7 @@ impl JsonRpcService {
|
||||||
let bigtable_config = solana_storage_bigtable::LedgerStorageConfig {
|
let bigtable_config = solana_storage_bigtable::LedgerStorageConfig {
|
||||||
read_only: !enable_bigtable_ledger_upload,
|
read_only: !enable_bigtable_ledger_upload,
|
||||||
timeout,
|
timeout,
|
||||||
credential_path: None,
|
credential_type: CredentialType::Filepath(None),
|
||||||
instance_name: bigtable_instance_name.clone(),
|
instance_name: bigtable_instance_name.clone(),
|
||||||
};
|
};
|
||||||
runtime
|
runtime
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
pub use goauth::scopes::Scope;
|
pub use goauth::scopes::Scope;
|
||||||
/// A module for managing a Google API access token
|
/// A module for managing a Google API access token
|
||||||
use {
|
use {
|
||||||
|
crate::CredentialType,
|
||||||
goauth::{
|
goauth::{
|
||||||
auth::{JwtClaims, Token},
|
auth::{JwtClaims, Token},
|
||||||
credentials::Credentials,
|
credentials::Credentials,
|
||||||
|
@ -8,6 +9,7 @@ use {
|
||||||
log::*,
|
log::*,
|
||||||
smpl_jwt::Jwt,
|
smpl_jwt::Jwt,
|
||||||
std::{
|
std::{
|
||||||
|
str::FromStr,
|
||||||
sync::{
|
sync::{
|
||||||
atomic::{AtomicBool, Ordering},
|
atomic::{AtomicBool, Ordering},
|
||||||
{Arc, RwLock},
|
{Arc, RwLock},
|
||||||
|
@ -27,6 +29,10 @@ fn load_credentials(filepath: Option<String>) -> Result<Credentials, String> {
|
||||||
.map_err(|err| format!("Failed to read GCP credentials from {}: {}", path, err))
|
.map_err(|err| format!("Failed to read GCP credentials from {}: {}", path, err))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn load_stringified_credentials(credential: String) -> Result<Credentials, String> {
|
||||||
|
Credentials::from_str(&credential).map_err(|err| format!("{}", err))
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct AccessToken {
|
pub struct AccessToken {
|
||||||
credentials: Credentials,
|
credentials: Credentials,
|
||||||
|
@ -36,8 +42,12 @@ pub struct AccessToken {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AccessToken {
|
impl AccessToken {
|
||||||
pub async fn new(scope: Scope, credential_filepath: Option<String>) -> Result<Self, String> {
|
pub async fn new(scope: Scope, credential_type: CredentialType) -> Result<Self, String> {
|
||||||
let credentials = load_credentials(credential_filepath)?;
|
let credentials = match credential_type {
|
||||||
|
CredentialType::Filepath(fp) => load_credentials(fp)?,
|
||||||
|
CredentialType::Stringified(s) => load_stringified_credentials(s)?,
|
||||||
|
};
|
||||||
|
|
||||||
if let Err(err) = credentials.rsa_key() {
|
if let Err(err) = credentials.rsa_key() {
|
||||||
Err(format!("Invalid rsa key: {}", err))
|
Err(format!("Invalid rsa key: {}", err))
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -4,7 +4,7 @@ use {
|
||||||
crate::{
|
crate::{
|
||||||
access_token::{AccessToken, Scope},
|
access_token::{AccessToken, Scope},
|
||||||
compression::{compress_best, decompress},
|
compression::{compress_best, decompress},
|
||||||
root_ca_certificate,
|
root_ca_certificate, CredentialType,
|
||||||
},
|
},
|
||||||
backoff::{future::retry, ExponentialBackoff},
|
backoff::{future::retry, ExponentialBackoff},
|
||||||
log::*,
|
log::*,
|
||||||
|
@ -125,7 +125,7 @@ impl BigTableConnection {
|
||||||
instance_name: &str,
|
instance_name: &str,
|
||||||
read_only: bool,
|
read_only: bool,
|
||||||
timeout: Option<Duration>,
|
timeout: Option<Duration>,
|
||||||
credential_path: Option<String>,
|
credential_type: CredentialType,
|
||||||
) -> Result<Self> {
|
) -> Result<Self> {
|
||||||
match std::env::var("BIGTABLE_EMULATOR_HOST") {
|
match std::env::var("BIGTABLE_EMULATOR_HOST") {
|
||||||
Ok(endpoint) => {
|
Ok(endpoint) => {
|
||||||
|
@ -148,7 +148,7 @@ impl BigTableConnection {
|
||||||
} else {
|
} else {
|
||||||
Scope::BigTableData
|
Scope::BigTableData
|
||||||
},
|
},
|
||||||
credential_path,
|
credential_type,
|
||||||
)
|
)
|
||||||
.await
|
.await
|
||||||
.map_err(Error::AccessToken)?;
|
.map_err(Error::AccessToken)?;
|
||||||
|
|
|
@ -364,11 +364,17 @@ impl From<LegacyTransactionByAddrInfo> for TransactionByAddrInfo {
|
||||||
|
|
||||||
pub const DEFAULT_INSTANCE_NAME: &str = "solana-ledger";
|
pub const DEFAULT_INSTANCE_NAME: &str = "solana-ledger";
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub enum CredentialType {
|
||||||
|
Filepath(Option<String>),
|
||||||
|
Stringified(String),
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct LedgerStorageConfig {
|
pub struct LedgerStorageConfig {
|
||||||
pub read_only: bool,
|
pub read_only: bool,
|
||||||
pub timeout: Option<std::time::Duration>,
|
pub timeout: Option<std::time::Duration>,
|
||||||
pub credential_path: Option<String>,
|
pub credential_type: CredentialType,
|
||||||
pub instance_name: String,
|
pub instance_name: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -377,7 +383,7 @@ impl Default for LedgerStorageConfig {
|
||||||
Self {
|
Self {
|
||||||
read_only: true,
|
read_only: true,
|
||||||
timeout: None,
|
timeout: None,
|
||||||
credential_path: None,
|
credential_type: CredentialType::Filepath(None),
|
||||||
instance_name: DEFAULT_INSTANCE_NAME.to_string(),
|
instance_name: DEFAULT_INSTANCE_NAME.to_string(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -397,7 +403,7 @@ impl LedgerStorage {
|
||||||
Self::new_with_config(LedgerStorageConfig {
|
Self::new_with_config(LedgerStorageConfig {
|
||||||
read_only,
|
read_only,
|
||||||
timeout,
|
timeout,
|
||||||
credential_path,
|
credential_type: CredentialType::Filepath(credential_path),
|
||||||
..LedgerStorageConfig::default()
|
..LedgerStorageConfig::default()
|
||||||
})
|
})
|
||||||
.await
|
.await
|
||||||
|
@ -407,19 +413,27 @@ impl LedgerStorage {
|
||||||
let LedgerStorageConfig {
|
let LedgerStorageConfig {
|
||||||
read_only,
|
read_only,
|
||||||
timeout,
|
timeout,
|
||||||
credential_path,
|
|
||||||
instance_name,
|
instance_name,
|
||||||
|
credential_type,
|
||||||
} = config;
|
} = config;
|
||||||
let connection = bigtable::BigTableConnection::new(
|
let connection = bigtable::BigTableConnection::new(
|
||||||
instance_name.as_str(),
|
instance_name.as_str(),
|
||||||
read_only,
|
read_only,
|
||||||
timeout,
|
timeout,
|
||||||
credential_path,
|
credential_type,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
Ok(Self { connection })
|
Ok(Self { connection })
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn new_with_stringified_credential(credential: String) -> Result<Self> {
|
||||||
|
Self::new_with_config(LedgerStorageConfig {
|
||||||
|
credential_type: CredentialType::Stringified(credential),
|
||||||
|
..LedgerStorageConfig::default()
|
||||||
|
})
|
||||||
|
.await
|
||||||
|
}
|
||||||
|
|
||||||
/// Return the available slot that contains a block
|
/// Return the available slot that contains a block
|
||||||
pub async fn get_first_available_block(&self) -> Result<Option<Slot>> {
|
pub async fn get_first_available_block(&self) -> Result<Option<Slot>> {
|
||||||
debug!("LedgerStorage::get_first_available_block request received");
|
debug!("LedgerStorage::get_first_available_block request received");
|
||||||
|
|
Loading…
Reference in New Issue