mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-05-31 02:51:01 +00:00
Support authors api. (#134)
This commit is contained in:
+9
-3
@@ -43,12 +43,14 @@ use jsonrpsee::{
|
||||
};
|
||||
use sc_network::config::TransportConfig;
|
||||
pub use sc_service::{
|
||||
config::DatabaseConfig,
|
||||
config::{
|
||||
DatabaseConfig,
|
||||
KeystoreConfig,
|
||||
},
|
||||
Error as ServiceError,
|
||||
};
|
||||
use sc_service::{
|
||||
config::{
|
||||
KeystoreConfig,
|
||||
NetworkConfiguration,
|
||||
TaskType,
|
||||
},
|
||||
@@ -119,6 +121,8 @@ pub struct SubxtClientConfig<C: ChainSpec + 'static, S: AbstractService> {
|
||||
pub copyright_start_year: i32,
|
||||
/// Database configuration.
|
||||
pub db: DatabaseConfig,
|
||||
/// Keystore configuration.
|
||||
pub keystore: KeystoreConfig,
|
||||
/// Service builder.
|
||||
pub builder: fn(Configuration) -> Result<S, sc_service::Error>,
|
||||
/// Chain specification.
|
||||
@@ -216,7 +220,7 @@ fn start_subxt_client<C: ChainSpec + 'static, S: AbstractService>(
|
||||
})
|
||||
.into(),
|
||||
database: config.db,
|
||||
keystore: KeystoreConfig::InMemory,
|
||||
keystore: config.keystore,
|
||||
max_runtime_instances: 8,
|
||||
announce_block: true,
|
||||
dev_key_seed: config.role.into(),
|
||||
@@ -342,6 +346,7 @@ mod tests {
|
||||
path: tmp.path().into(),
|
||||
cache_size: 64,
|
||||
},
|
||||
keystore: KeystoreConfig::InMemory,
|
||||
builder: test_node::service::new_light,
|
||||
chain_spec,
|
||||
role: Role::Light,
|
||||
@@ -372,6 +377,7 @@ mod tests {
|
||||
path: tmp.path().into(),
|
||||
cache_size: 128,
|
||||
},
|
||||
keystore: KeystoreConfig::InMemory,
|
||||
builder: test_node::service::new_full,
|
||||
chain_spec: test_node::chain_spec::development_config(),
|
||||
role: Role::Authority(AccountKeyring::Alice),
|
||||
|
||||
+79
-6
@@ -52,9 +52,12 @@ use codec::Decode;
|
||||
use futures::future;
|
||||
use jsonrpsee::client::Subscription;
|
||||
use sc_rpc_api::state::ReadProof;
|
||||
use sp_core::storage::{
|
||||
StorageChangeSet,
|
||||
StorageKey,
|
||||
use sp_core::{
|
||||
storage::{
|
||||
StorageChangeSet,
|
||||
StorageKey,
|
||||
},
|
||||
Bytes,
|
||||
};
|
||||
pub use sp_runtime::traits::SignedExtension;
|
||||
use sp_version::RuntimeVersion;
|
||||
@@ -425,6 +428,41 @@ impl<T: Runtime> Client<T> {
|
||||
let decoder = self.events_decoder::<C>();
|
||||
self.submit_and_watch_extrinsic(extrinsic, decoder).await
|
||||
}
|
||||
|
||||
/// Insert a key into the keystore.
|
||||
pub async fn insert_key(
|
||||
&self,
|
||||
key_type: String,
|
||||
suri: String,
|
||||
public: Bytes,
|
||||
) -> Result<(), Error> {
|
||||
self.rpc.insert_key(key_type, suri, public).await
|
||||
}
|
||||
|
||||
/// Generate new session keys and returns the corresponding public keys.
|
||||
pub async fn rotate_keys(&self) -> Result<Bytes, Error> {
|
||||
self.rpc.rotate_keys().await
|
||||
}
|
||||
|
||||
/// Checks if the keystore has private keys for the given session public keys.
|
||||
///
|
||||
/// `session_keys` is the SCALE encoded session keys object from the runtime.
|
||||
///
|
||||
/// Returns `true` iff all private keys could be found.
|
||||
pub async fn has_session_keys(&self, session_keys: Bytes) -> Result<bool, Error> {
|
||||
self.rpc.has_session_keys(session_keys).await
|
||||
}
|
||||
|
||||
/// Checks if the keystore has private keys for the given public key and key type.
|
||||
///
|
||||
/// Returns `true` if a private key could be found.
|
||||
pub async fn has_key(
|
||||
&self,
|
||||
public_key: Bytes,
|
||||
key_type: String,
|
||||
) -> Result<bool, Error> {
|
||||
self.rpc.has_key(public_key, key_type).await
|
||||
}
|
||||
}
|
||||
|
||||
/// Wraps an already encoded byte vector, prevents being encoded as a raw byte vector as part of
|
||||
@@ -456,6 +494,7 @@ mod tests {
|
||||
use sp_runtime::MultiSignature;
|
||||
use substrate_subxt_client::{
|
||||
DatabaseConfig,
|
||||
KeystoreConfig,
|
||||
Role,
|
||||
SubxtClient,
|
||||
SubxtClientConfig,
|
||||
@@ -464,7 +503,9 @@ mod tests {
|
||||
|
||||
pub(crate) type TestRuntime = crate::NodeTemplateRuntime;
|
||||
|
||||
pub(crate) async fn test_client() -> (Client<TestRuntime>, TempDir) {
|
||||
pub(crate) async fn test_client_with(
|
||||
key: AccountKeyring,
|
||||
) -> (Client<TestRuntime>, TempDir) {
|
||||
env_logger::try_init().ok();
|
||||
let tmp = TempDir::new("subxt-").expect("failed to create tempdir");
|
||||
let config = SubxtClientConfig {
|
||||
@@ -473,12 +514,16 @@ mod tests {
|
||||
author: "substrate subxt",
|
||||
copyright_start_year: 2020,
|
||||
db: DatabaseConfig::RocksDb {
|
||||
path: tmp.path().into(),
|
||||
path: tmp.path().join("db"),
|
||||
cache_size: 128,
|
||||
},
|
||||
keystore: KeystoreConfig::Path {
|
||||
path: tmp.path().join("keystore"),
|
||||
password: None,
|
||||
},
|
||||
builder: test_node::service::new_full,
|
||||
chain_spec: test_node::chain_spec::development_config(),
|
||||
role: Role::Authority(AccountKeyring::Alice),
|
||||
role: Role::Authority(key),
|
||||
};
|
||||
let client = ClientBuilder::new()
|
||||
.set_client(SubxtClient::new(config).expect("Error creating subxt client"))
|
||||
@@ -488,6 +533,34 @@ mod tests {
|
||||
(client, tmp)
|
||||
}
|
||||
|
||||
pub(crate) async fn test_client() -> (Client<TestRuntime>, TempDir) {
|
||||
test_client_with(AccountKeyring::Alice).await
|
||||
}
|
||||
|
||||
#[async_std::test]
|
||||
async fn test_insert_key() {
|
||||
// Bob is not an authority, so block production should be disabled.
|
||||
let (client, _tmp) = test_client_with(AccountKeyring::Bob).await;
|
||||
let mut blocks = client.subscribe_blocks().await.unwrap();
|
||||
// get the genesis block.
|
||||
assert_eq!(blocks.next().await.number, 0);
|
||||
let public = AccountKeyring::Alice.public().as_array_ref().to_vec();
|
||||
client
|
||||
.insert_key(
|
||||
"aura".to_string(),
|
||||
"//Alice".to_string(),
|
||||
public.clone().into(),
|
||||
)
|
||||
.await
|
||||
.unwrap();
|
||||
assert!(client
|
||||
.has_key(public.clone().into(), "aura".to_string())
|
||||
.await
|
||||
.unwrap());
|
||||
// Alice is an authority, so blocks should be produced.
|
||||
assert_eq!(blocks.next().await.number, 1);
|
||||
}
|
||||
|
||||
#[async_std::test]
|
||||
async fn test_tx_transfer_balance() {
|
||||
let mut signer = PairSigner::new(AccountKeyring::Alice.pair());
|
||||
|
||||
+47
@@ -396,6 +396,53 @@ impl<T: Runtime> Rpc<T> {
|
||||
}
|
||||
unreachable!()
|
||||
}
|
||||
|
||||
/// Insert a key into the keystore.
|
||||
pub async fn insert_key(
|
||||
&self,
|
||||
key_type: String,
|
||||
suri: String,
|
||||
public: Bytes,
|
||||
) -> Result<(), Error> {
|
||||
let params = Params::Array(vec![
|
||||
to_json_value(key_type)?,
|
||||
to_json_value(suri)?,
|
||||
to_json_value(public)?,
|
||||
]);
|
||||
self.client.request("author_insertKey", params).await?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Generate new session keys and returns the corresponding public keys.
|
||||
pub async fn rotate_keys(&self) -> Result<Bytes, Error> {
|
||||
Ok(self
|
||||
.client
|
||||
.request("author_rotateKeys", Params::None)
|
||||
.await?)
|
||||
}
|
||||
|
||||
/// Checks if the keystore has private keys for the given session public keys.
|
||||
///
|
||||
/// `session_keys` is the SCALE encoded session keys object from the runtime.
|
||||
///
|
||||
/// Returns `true` iff all private keys could be found.
|
||||
pub async fn has_session_keys(&self, session_keys: Bytes) -> Result<bool, Error> {
|
||||
let params = Params::Array(vec![to_json_value(session_keys)?]);
|
||||
Ok(self.client.request("author_hasSessionKeys", params).await?)
|
||||
}
|
||||
|
||||
/// Checks if the keystore has private keys for the given public key and key type.
|
||||
///
|
||||
/// Returns `true` if a private key could be found.
|
||||
pub async fn has_key(
|
||||
&self,
|
||||
public_key: Bytes,
|
||||
key_type: String,
|
||||
) -> Result<bool, Error> {
|
||||
let params =
|
||||
Params::Array(vec![to_json_value(public_key)?, to_json_value(key_type)?]);
|
||||
Ok(self.client.request("author_hasKey", params).await?)
|
||||
}
|
||||
}
|
||||
|
||||
/// Captures data for when an extrinsic is successfully included in a block
|
||||
|
||||
Reference in New Issue
Block a user