Fix snap server (backport #23140) (#23193)

* test-validator: use `JsonRpcConfig::default_for_test` for consistency

(cherry picked from commit f7118258d6)

# Conflicts:
#	core/src/test_validator.rs

* rpc: make `getGenesisHash` part of minimal api

(cherry picked from commit 4213ece7bd)

# Conflicts:
#	rpc/src/rpc.rs

* rpc: genericize client constructors

(cherry picked from commit aeda27433f)

# Conflicts:
#	client/src/http_sender.rs

* validator: invert vote account sanity check arg

(cherry picked from commit de30699fa5)

# Conflicts:
#	validator/src/bootstrap.rs
#	validator/src/main.rs

Co-authored-by: Trent Nelson <trent@solana.com>
This commit is contained in:
mergify[bot]
2022-02-17 01:49:48 +00:00
committed by GitHub
parent 586f55e6c1
commit a352613c75
6 changed files with 44 additions and 31 deletions

View File

@ -37,14 +37,14 @@ impl HttpSender {
/// ///
/// The URL is an HTTP URL, usually for port 8899, as in /// The URL is an HTTP URL, usually for port 8899, as in
/// "http://localhost:8899". The sender has a default timeout of 30 seconds. /// "http://localhost:8899". The sender has a default timeout of 30 seconds.
pub fn new(url: String) -> Self { pub fn new<U: ToString>(url: U) -> Self {
Self::new_with_timeout(url, Duration::from_secs(30)) Self::new_with_timeout(url, Duration::from_secs(30))
} }
/// Create an HTTP RPC sender. /// Create an HTTP RPC sender.
/// ///
/// The URL is an HTTP URL, usually for port 8899. /// The URL is an HTTP URL, usually for port 8899.
pub fn new_with_timeout(url: String, timeout: Duration) -> Self { pub fn new_with_timeout<U: ToString>(url: U, timeout: Duration) -> Self {
// `reqwest::blocking::Client` panics if run in a tokio async context. Shuttle the // `reqwest::blocking::Client` panics if run in a tokio async context. Shuttle the
// request to a different tokio thread to avoid this // request to a different tokio thread to avoid this
let client = Arc::new( let client = Arc::new(
@ -58,7 +58,7 @@ impl HttpSender {
Self { Self {
client, client,
url, url: url.to_string(),
request_id: AtomicU64::new(0), request_id: AtomicU64::new(0),
stats: RwLock::new(RpcTransportStats::default()), stats: RwLock::new(RpcTransportStats::default()),
} }

View File

@ -75,13 +75,13 @@ pub struct MockSender {
/// from [`RpcRequest`] to a JSON [`Value`] response, Any entries in this map /// from [`RpcRequest`] to a JSON [`Value`] response, Any entries in this map
/// override the default behavior for the given request. /// override the default behavior for the given request.
impl MockSender { impl MockSender {
pub fn new(url: String) -> Self { pub fn new<U: ToString>(url: U) -> Self {
Self::new_with_mocks(url, Mocks::default()) Self::new_with_mocks(url, Mocks::default())
} }
pub fn new_with_mocks(url: String, mocks: Mocks) -> Self { pub fn new_with_mocks<U: ToString>(url: U, mocks: Mocks) -> Self {
Self { Self {
url, url: url.to_string(),
mocks: RwLock::new(mocks), mocks: RwLock::new(mocks),
} }
} }

View File

@ -190,7 +190,7 @@ impl RpcClient {
/// let url = "http://localhost:8899".to_string(); /// let url = "http://localhost:8899".to_string();
/// let client = RpcClient::new(url); /// let client = RpcClient::new(url);
/// ``` /// ```
pub fn new(url: String) -> Self { pub fn new<U: ToString>(url: U) -> Self {
Self::new_with_commitment(url, CommitmentConfig::default()) Self::new_with_commitment(url, CommitmentConfig::default())
} }
@ -213,7 +213,7 @@ impl RpcClient {
/// let commitment_config = CommitmentConfig::processed(); /// let commitment_config = CommitmentConfig::processed();
/// let client = RpcClient::new_with_commitment(url, commitment_config); /// let client = RpcClient::new_with_commitment(url, commitment_config);
/// ``` /// ```
pub fn new_with_commitment(url: String, commitment_config: CommitmentConfig) -> Self { pub fn new_with_commitment<U: ToString>(url: U, commitment_config: CommitmentConfig) -> Self {
Self::new_sender( Self::new_sender(
HttpSender::new(url), HttpSender::new(url),
RpcClientConfig::with_commitment(commitment_config), RpcClientConfig::with_commitment(commitment_config),
@ -239,7 +239,7 @@ impl RpcClient {
/// let timeout = Duration::from_secs(1); /// let timeout = Duration::from_secs(1);
/// let client = RpcClient::new_with_timeout(url, timeout); /// let client = RpcClient::new_with_timeout(url, timeout);
/// ``` /// ```
pub fn new_with_timeout(url: String, timeout: Duration) -> Self { pub fn new_with_timeout<U: ToString>(url: U, timeout: Duration) -> Self {
Self::new_sender( Self::new_sender(
HttpSender::new_with_timeout(url, timeout), HttpSender::new_with_timeout(url, timeout),
RpcClientConfig::with_commitment(CommitmentConfig::default()), RpcClientConfig::with_commitment(CommitmentConfig::default()),
@ -268,8 +268,8 @@ impl RpcClient {
/// commitment_config, /// commitment_config,
/// ); /// );
/// ``` /// ```
pub fn new_with_timeout_and_commitment( pub fn new_with_timeout_and_commitment<U: ToString>(
url: String, url: U,
timeout: Duration, timeout: Duration,
commitment_config: CommitmentConfig, commitment_config: CommitmentConfig,
) -> Self { ) -> Self {
@ -311,8 +311,8 @@ impl RpcClient {
/// confirm_transaction_initial_timeout, /// confirm_transaction_initial_timeout,
/// ); /// );
/// ``` /// ```
pub fn new_with_timeouts_and_commitment( pub fn new_with_timeouts_and_commitment<U: ToString>(
url: String, url: U,
timeout: Duration, timeout: Duration,
commitment_config: CommitmentConfig, commitment_config: CommitmentConfig,
confirm_transaction_initial_timeout: Duration, confirm_transaction_initial_timeout: Duration,
@ -346,7 +346,7 @@ impl RpcClient {
/// let url = "fails".to_string(); /// let url = "fails".to_string();
/// let successful_client = RpcClient::new_mock(url); /// let successful_client = RpcClient::new_mock(url);
/// ``` /// ```
pub fn new_mock(url: String) -> Self { pub fn new_mock<U: ToString>(url: U) -> Self {
Self::new_sender( Self::new_sender(
MockSender::new(url), MockSender::new(url),
RpcClientConfig::with_commitment(CommitmentConfig::default()), RpcClientConfig::with_commitment(CommitmentConfig::default()),
@ -380,7 +380,7 @@ impl RpcClient {
/// let url = "succeeds".to_string(); /// let url = "succeeds".to_string();
/// let client = RpcClient::new_mock_with_mocks(url, mocks); /// let client = RpcClient::new_mock_with_mocks(url, mocks);
/// ``` /// ```
pub fn new_mock_with_mocks(url: String, mocks: Mocks) -> Self { pub fn new_mock_with_mocks<U: ToString>(url: U, mocks: Mocks) -> Self {
Self::new_sender( Self::new_sender(
MockSender::new_with_mocks(url, mocks), MockSender::new_with_mocks(url, mocks),
RpcClientConfig::with_commitment(CommitmentConfig::default()), RpcClientConfig::with_commitment(CommitmentConfig::default()),

View File

@ -95,10 +95,7 @@ impl Default for TestValidatorGenesis {
fee_rate_governor: FeeRateGovernor::default(), fee_rate_governor: FeeRateGovernor::default(),
ledger_path: Option::<PathBuf>::default(), ledger_path: Option::<PathBuf>::default(),
rent: Rent::default(), rent: Rent::default(),
rpc_config: JsonRpcConfig { rpc_config: JsonRpcConfig::default_for_test(),
full_api: true,
..JsonRpcConfig::default()
},
rpc_ports: Option::<(u16, u16)>::default(), rpc_ports: Option::<(u16, u16)>::default(),
warp_slot: Option::<Slot>::default(), warp_slot: Option::<Slot>::default(),
no_bpf_jit: bool::default(), no_bpf_jit: bool::default(),

View File

@ -2318,6 +2318,9 @@ pub mod rpc_minimal {
commitment: Option<CommitmentConfig>, commitment: Option<CommitmentConfig>,
) -> Result<EpochInfo>; ) -> Result<EpochInfo>;
#[rpc(meta, name = "getGenesisHash")]
fn get_genesis_hash(&self, meta: Self::Metadata) -> Result<String>;
#[rpc(meta, name = "getHealth")] #[rpc(meta, name = "getHealth")]
fn get_health(&self, meta: Self::Metadata) -> Result<String>; fn get_health(&self, meta: Self::Metadata) -> Result<String>;
@ -2396,6 +2399,11 @@ pub mod rpc_minimal {
Ok(bank.get_epoch_info()) Ok(bank.get_epoch_info())
} }
fn get_genesis_hash(&self, meta: Self::Metadata) -> Result<String> {
debug!("get_genesis_hash rpc request received");
Ok(meta.genesis_hash.to_string())
}
fn get_health(&self, meta: Self::Metadata) -> Result<String> { fn get_health(&self, meta: Self::Metadata) -> Result<String> {
match meta.health.check() { match meta.health.check() {
RpcHealthStatus::Ok => Ok("ok".to_string()), RpcHealthStatus::Ok => Ok("ok".to_string()),
@ -2591,9 +2599,6 @@ pub mod rpc_full {
block: Slot, block: Slot,
) -> Result<RpcBlockCommitment<BlockCommitmentArray>>; ) -> Result<RpcBlockCommitment<BlockCommitmentArray>>;
#[rpc(meta, name = "getGenesisHash")]
fn get_genesis_hash(&self, meta: Self::Metadata) -> Result<String>;
#[rpc(meta, name = "getRecentBlockhash")] #[rpc(meta, name = "getRecentBlockhash")]
fn get_recent_blockhash( fn get_recent_blockhash(
&self, &self,
@ -3001,11 +3006,6 @@ pub mod rpc_full {
Ok(meta.get_block_commitment(block)) Ok(meta.get_block_commitment(block))
} }
fn get_genesis_hash(&self, meta: Self::Metadata) -> Result<String> {
debug!("get_genesis_hash rpc request received");
Ok(meta.genesis_hash.to_string())
}
fn get_recent_blockhash( fn get_recent_blockhash(
&self, &self,
meta: Self::Metadata, meta: Self::Metadata,

View File

@ -745,7 +745,7 @@ struct RpcBootstrapConfig {
no_snapshot_fetch: bool, no_snapshot_fetch: bool,
only_known_rpc: bool, only_known_rpc: bool,
max_genesis_archive_unpacked_size: u64, max_genesis_archive_unpacked_size: u64,
no_check_vote_account: bool, check_vote_account: Option<String>,
} }
impl Default for RpcBootstrapConfig { impl Default for RpcBootstrapConfig {
@ -755,7 +755,7 @@ impl Default for RpcBootstrapConfig {
no_snapshot_fetch: true, no_snapshot_fetch: true,
only_known_rpc: true, only_known_rpc: true,
max_genesis_archive_unpacked_size: MAX_GENESIS_ARCHIVE_UNPACKED_SIZE, max_genesis_archive_unpacked_size: MAX_GENESIS_ARCHIVE_UNPACKED_SIZE,
no_check_vote_account: true, check_vote_account: None,
} }
} }
} }
@ -976,7 +976,8 @@ fn rpc_bootstrap(
} }
}) })
.map(|_| { .map(|_| {
if !validator_config.voting_disabled && !bootstrap_config.no_check_vote_account { if let Some(url) = bootstrap_config.check_vote_account.as_ref() {
let rpc_client = RpcClient::new(url);
check_vote_account( check_vote_account(
&rpc_client, &rpc_client,
&identity_keypair.pubkey(), &identity_keypair.pubkey(),
@ -1172,8 +1173,18 @@ pub fn main() {
.takes_value(false) .takes_value(false)
.conflicts_with("no_voting") .conflicts_with("no_voting")
.requires("entrypoint") .requires("entrypoint")
.hidden(true)
.help("Skip the RPC vote account sanity check") .help("Skip the RPC vote account sanity check")
) )
.arg(
Arg::with_name("check_vote_account")
.long("check-vote-account")
.takes_value(true)
.value_name("RPC_URL")
.requires("entrypoint")
.conflicts_with_all(&["no_check_vote_account", "no_voting"])
.help("Sanity check vote account state at startup. The JSON RPC endpoint at RPC_URL must expose `--full-rpc-api`")
)
.arg( .arg(
Arg::with_name("restricted_repair_only_mode") Arg::with_name("restricted_repair_only_mode")
.long("restricted-repair-only-mode") .long("restricted-repair-only-mode")
@ -2310,10 +2321,15 @@ pub fn main() {
let init_complete_file = matches.value_of("init_complete_file"); let init_complete_file = matches.value_of("init_complete_file");
if matches.is_present("no_check_vote_account") {
info!("vote account sanity checks are no longer performed by default. --no-check-vote-account is deprecated and can be removed from the command line");
}
let rpc_bootstrap_config = RpcBootstrapConfig { let rpc_bootstrap_config = RpcBootstrapConfig {
no_genesis_fetch: matches.is_present("no_genesis_fetch"), no_genesis_fetch: matches.is_present("no_genesis_fetch"),
no_snapshot_fetch: matches.is_present("no_snapshot_fetch"), no_snapshot_fetch: matches.is_present("no_snapshot_fetch"),
no_check_vote_account: matches.is_present("no_check_vote_account"), check_vote_account: matches
.value_of("check_vote_account")
.map(|url| url.to_string()),
only_known_rpc: matches.is_present("only_known_rpc"), only_known_rpc: matches.is_present("only_known_rpc"),
max_genesis_archive_unpacked_size: value_t_or_exit!( max_genesis_archive_unpacked_size: value_t_or_exit!(
matches, matches,