Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

use subxt-signer to reduce the number of deps #720

Merged
merged 5 commits into from
Dec 5, 2023
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1,822 changes: 738 additions & 1,084 deletions Cargo.lock

Large diffs are not rendered by default.

9 changes: 7 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -23,15 +23,20 @@ tokio = { version = "1.34", features = ["macros", "rt-multi-thread", "sync", "si
pin-project-lite = "0.2"

# subxt
subxt = { version = "0.32.1", features = ["substrate-compat"] }
scale-value = "0.12.0"
subxt = "0.32.1"
subxt-signer = { version = "0.32.1", features = ["subxt"] }

# polkadot-sdk
frame-election-provider-support = "26.0.0"
pallet-election-provider-multi-phase = "25.0.0"
sp-npos-elections = "24.0.0"
frame-support = "26.0.0"
sp-npos-elections = "24.0.0"
# Both `sp-runtime` and `sp-core` has plenty of dependencies
# and because `pallet-election-provider-multi-phase` is depending
# on them it's not much we can do it about it.
sp-runtime = "29.0.0"
sp-core = "26.0.0"

# prometheus
prometheus = "0.13"
Expand Down
24 changes: 15 additions & 9 deletions src/commands/dry_run.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,18 @@

//! The dry-run command.

use pallet_election_provider_multi_phase::RawSolution;

use crate::{
client::Client, epm, error::Error, helpers::storage_at, opt::Solver, prelude::*,
signer::Signer, static_types,
client::Client,
epm,
error::Error,
helpers::{signer_from_seed_or_path, storage_at},
opt::Solver,
prelude::*,
static_types,
};
use clap::Parser;
use codec::Encode;
use pallet_election_provider_multi_phase::RawSolution;

#[derive(Debug, Clone, Parser)]
#[cfg_attr(test, derive(PartialEq))]
Expand Down Expand Up @@ -99,19 +103,21 @@ where
// If an account seed or path is provided, then do a dry run to the node. Otherwise,
// we've logged the solution above and we do nothing else.
if let Some(seed_or_path) = &config.seed_or_path {
let signer = Signer::new(seed_or_path)?;
let signer = signer_from_seed_or_path(seed_or_path)?;
let account_info = storage
.fetch(&runtime::storage().system().account(signer.account_id()))
.fetch(&runtime::storage().system().account(signer.public_key().to_account_id()))
.await?
.ok_or(Error::AccountDoesNotExists)?;

log::info!(target: LOG_TARGET, "Loaded account {}, {:?}", signer, account_info);
log::info!(target: LOG_TARGET, "Loaded account {:?}, {:?}", signer, account_info);
niklasad1 marked this conversation as resolved.
Show resolved Hide resolved

let nonce = client.rpc_system_account_next_index(signer.account_id()).await?;
let nonce = client
.rpc_system_account_next_index(&signer.public_key().to_account_id())
.await?;
let tx = epm::signed_solution(raw_solution)?;
let xt = client.chain_api().tx().create_signed_with_nonce(
&tx,
&*signer,
&signer,
nonce,
Default::default(),
)?;
Expand Down
17 changes: 16 additions & 1 deletion src/commands/emergency_solution.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ use crate::{
use clap::Parser;
use codec::Encode;
use sp_core::hexdisplay::HexDisplay;
use sp_npos_elections::Support;
use std::io::Write;
use subxt::tx::TxPayload;

Expand Down Expand Up @@ -74,7 +75,21 @@ where
let encoded_size = ready_solution.encoded_size();
let score = ready_solution.score;

let mut supports = ready_solution.supports.into_inner();
// subxt doesn't implement `scale_info::TypeInfo` for AccountId32
// that's why all AccountId32's below are converted to the inner array.
let mut supports: Vec<_> = ready_solution
.supports
.into_inner()
.into_iter()
.map(|(a, s)| {
let supports = Support {
voters: s.voters.into_iter().map(|(a, w)| (a.0, w)).collect(),
total: s.total,
};

(a.0, supports)
})
.collect();

// maybe truncate.
if let Some(force_winner_count) = config.force_winner_count {
Expand Down
24 changes: 12 additions & 12 deletions src/commands/monitor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,10 @@ use crate::{
client::Client,
epm,
error::Error,
helpers::{kill_main_task_if_critical_err, TimedFuture},
helpers::{kill_main_task_if_critical_err, signer_from_seed_or_path, TimedFuture},
opt::Solver,
prelude::*,
prometheus,
signer::Signer,
static_types,
prometheus, static_types,
};
use clap::Parser;
use codec::{Decode, Encode};
Expand Down Expand Up @@ -170,10 +168,10 @@ where
+ 'static,
T::Solution: Send,
{
let signer = Signer::new(&config.seed_or_path)?;
let signer = signer_from_seed_or_path(&config.seed_or_path)?;

let account_info = {
let addr = runtime::storage().system().account(signer.account_id());
let addr = runtime::storage().system().account(signer.public_key().to_account_id());
client
.chain_api()
.storage()
Expand All @@ -184,7 +182,7 @@ where
.ok_or(Error::AccountDoesNotExists)?
};

log::info!(target: LOG_TARGET, "Loaded account {}, {:?}", signer, account_info);
log::info!(target: LOG_TARGET, "Loaded account {:?}, {:?}", signer, account_info);

if config.dry_run {
// if we want to try-run, ensure the node supports it.
Expand Down Expand Up @@ -242,7 +240,7 @@ where
.storage()
.at_latest()
.await?
.fetch(&runtime::storage().system().account(signer.account_id()))
.fetch(&runtime::storage().system().account(signer.public_key().to_account_id()))
.await?
.ok_or(Error::AccountDoesNotExists)?;
// this is lossy but fine for now.
Expand Down Expand Up @@ -271,7 +269,9 @@ where
// NOTE: as we try to send at each block then the nonce is used guard against
// submitting twice. Because once a solution has been accepted on chain
// the "next transaction" at a later block but with the same nonce will be rejected
let nonce = client.rpc_system_account_next_index(signer.account_id()).await?;
let nonce = client
.rpc_system_account_next_index(&signer.public_key().to_account_id())
.await?;

ensure_signed_phase(client.chain_api(), block_hash)
.inspect_err(|e| {
Expand Down Expand Up @@ -300,7 +300,7 @@ where
ensure_no_previous_solution::<T::Solution>(
client.chain_api(),
block_hash,
&signer.account_id().0.into(),
&signer.public_key().0.into(),
)
.inspect_err(|e| {
log::debug!(
Expand Down Expand Up @@ -382,7 +382,7 @@ where
ensure_no_previous_solution::<T::Solution>(
client.chain_api(),
best_head,
&signer.account_id().0.into(),
&signer.public_key().0.into(),
)
.inspect_err(|e| {
log::debug!(
Expand Down Expand Up @@ -526,7 +526,7 @@ async fn submit_and_watch_solution<T: MinerConfig + Send + Sync + 'static>(

let xt = client.chain_api().tx().create_signed_with_nonce(
&tx,
&*signer,
&signer,
nonce as u64,
Default::default(),
)?;
Expand Down
8 changes: 4 additions & 4 deletions src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,6 @@
// You should have received a copy of the GNU General Public License
// along with Polkadot. If not, see <http://www.gnu.org/licenses/>.

use crate::prelude::*;

#[derive(thiserror::Error, Debug)]
pub enum Error {
#[error("Failed to parse log directive: `{0}´")]
Expand All @@ -26,8 +24,10 @@ pub enum Error {
RpcError(#[from] jsonrpsee::core::Error),
#[error("subxt error: `{0}`")]
Subxt(#[from] subxt::Error),
#[error("Crypto error: `{0:?}`")]
Crypto(sp_core::crypto::SecretStringError),
#[error("SecretUri error: `{0}`")]
SecretUri(#[from] subxt_signer::SecretUriError),
#[error("Keypair error: `{0}`")]
Keypair(#[from] subxt_signer::sr25519::Error),
#[error("Codec error: `{0}`")]
Codec(#[from] codec::Error),
#[error("Incorrect phase")]
Expand Down
31 changes: 31 additions & 0 deletions src/helpers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ use serde::Deserialize;
use std::{
future::Future,
pin::Pin,
str::FromStr,
task::{Context, Poll},
time::{Duration, Instant},
};
Expand Down Expand Up @@ -152,3 +153,33 @@ pub async fn storage_at(
api.storage().at_latest().await.map_err(Into::into)
}
}

pub fn signer_from_seed_or_path(seed_or_path: &str) -> Result<Signer, Error> {
use subxt_signer::SecretUri;

let seed_or_path = seed_or_path.trim();

let unchecked_secret = match std::fs::read(seed_or_path) {
Ok(s) => String::from_utf8(s).map_err(|e| Error::Other(e.to_string()))?,
Err(_) => seed_or_path.to_string(),
};

// Check if the secret is an URI such as //Alice
let secret = SecretUri::from_str(&unchecked_secret)?;
Signer::from_uri(&secret).map_err(Into::into)
}

#[cfg(test)]
#[test]
fn signer_parsing_works() {
assert!(signer_from_seed_or_path("//Alice").is_ok());
assert!(signer_from_seed_or_path(
"0x1122334455667788112233445566778811223344556677881122334455667788"
)
.is_ok());
assert!(signer_from_seed_or_path(
"1122334455667788112233445566778811223344556677881122334455667788"
)
.is_err());
assert!(signer_from_seed_or_path("0x0").is_err());
}
1 change: 0 additions & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,5 +24,4 @@ pub mod helpers;
pub mod opt;
pub mod prelude;
pub mod prometheus;
pub mod signer;
pub mod static_types;
1 change: 0 additions & 1 deletion src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,6 @@ mod helpers;
mod opt;
mod prelude;
mod prometheus;
mod signer;
mod static_types;

use clap::Parser;
Expand Down
3 changes: 1 addition & 2 deletions src/opt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,8 @@
use crate::error::Error;

use clap::*;
use serde::{Deserialize, Serialize};
use serde::{de::DeserializeOwned, Deserialize, Serialize};
use sp_npos_elections::BalancingConfig;
use sp_runtime::DeserializeOwned;
use std::{collections::HashMap, fmt, str::FromStr};
use subxt::backend::legacy::rpc_methods as subxt_rpc;

Expand Down
16 changes: 6 additions & 10 deletions src/prelude.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,17 +22,18 @@

// re-exports.
pub use pallet_election_provider_multi_phase::{Miner, MinerConfig};
pub use subxt::ext::sp_core;
/// The account id type.
pub type AccountId = sp_runtime::AccountId32;
pub type AccountId = subxt::utils::AccountId32;
/// The header type. We re-export it here, but we can easily get it from block as well.
pub type Header =
subxt::config::substrate::SubstrateHeader<u32, subxt::config::substrate::BlakeTwo256>;
/// The header type. We re-export it here, but we can easily get it from block as well.
pub type Hash = sp_core::H256;
pub type Hash = subxt::utils::H256;
/// Balance type
pub type Balance = u128;
pub use subxt::ext::sp_runtime::traits::{Block as BlockT, Header as HeaderT};
/// Signer type
/// The key pair type being used. We "strongly" assume sr25519 for simplicity.
pub type Signer = subxt_signer::sr25519::Keypair;

/// Default URI to connect to.
///
Expand All @@ -42,17 +43,12 @@ pub const DEFAULT_URI: &str = "ws://127.0.0.1:9944";
pub const DEFAULT_PROMETHEUS_PORT: u16 = 9999;
/// The logging target.
pub const LOG_TARGET: &str = "polkadot-staking-miner";

/// The key pair type being used. We "strongly" assume sr25519 for simplicity.
pub type Pair = sp_core::sr25519::Pair;

/// The accuracy that we use for election computation.
pub type Accuracy = sp_runtime::Perbill;

/// Rpc client.
pub type RpcClient = subxt::backend::legacy::LegacyRpcMethods<subxt::PolkadotConfig>;
/// Subxt client used by the staking miner on all chains.
pub type ChainClient = subxt::OnlineClient<subxt::PolkadotConfig>;

/// Config used by the staking-miner
pub type Config = subxt::PolkadotConfig;

Expand Down
76 changes: 0 additions & 76 deletions src/signer.rs

This file was deleted.