Stabilize chainHead methods (#1538)

* Stabilize chainHead methods

Signed-off-by: Alexandru Vasile <alexandru.vasile@parity.io>

* Rename fn snake case

Signed-off-by: Alexandru Vasile <alexandru.vasile@parity.io>

* docs: Fix documentation

Signed-off-by: Alexandru Vasile <alexandru.vasile@parity.io>

---------

Signed-off-by: Alexandru Vasile <alexandru.vasile@parity.io>
This commit is contained in:
Alexandru Vasile
2024-04-19 12:27:50 +03:00
committed by GitHub
parent ac606cf625
commit c124e17336
6 changed files with 62 additions and 75 deletions
+1 -1
View File
@@ -105,7 +105,7 @@ impl<Hash> FollowStream<Hash> {
let methods = methods.clone(); let methods = methods.clone();
Box::pin(async move { Box::pin(async move {
// Make the RPC call: // Make the RPC call:
let stream = methods.chainhead_unstable_follow(true).await?; let stream = methods.chainhead_v1_follow(true).await?;
// Extract the subscription ID: // Extract the subscription ID:
let Some(sub_id) = stream.subscription_id().map(ToOwned::to_owned) else { let Some(sub_id) = stream.subscription_id().map(ToOwned::to_owned) else {
return Err(Error::Other( return Err(Error::Other(
@@ -282,7 +282,7 @@ impl<Hash: BlockHash> FollowStreamUnpin<Hash> {
let methods = methods.clone(); let methods = methods.clone();
let fut: UnpinFut = Box::pin(async move { let fut: UnpinFut = Box::pin(async move {
// We ignore any errors trying to unpin at the moment. // We ignore any errors trying to unpin at the moment.
let _ = methods.chainhead_unstable_unpin(&sub_id, hash).await; let _ = methods.chainhead_v1_unpin(&sub_id, hash).await;
}); });
fut fut
}); });
+4 -4
View File
@@ -160,7 +160,7 @@ impl<T: Config> UnstableBackend<T> {
async move { async move {
let res = methods let res = methods
.chainhead_unstable_header(&sub_id, block_ref.hash()) .chainhead_v1_header(&sub_id, block_ref.hash())
.await .await
.transpose()?; .transpose()?;
@@ -286,7 +286,7 @@ impl<T: Config + Send + Sync + 'static> Backend<T> for UnstableBackend<T> {
async fn block_header(&self, at: T::Hash) -> Result<Option<T::Header>, Error> { async fn block_header(&self, at: T::Hash) -> Result<Option<T::Header>, Error> {
let sub_id = get_subscription_id(&self.follow_handle).await?; let sub_id = get_subscription_id(&self.follow_handle).await?;
self.methods.chainhead_unstable_header(&sub_id, at).await self.methods.chainhead_v1_header(&sub_id, at).await
} }
async fn block_body(&self, at: T::Hash) -> Result<Option<Vec<Vec<u8>>>, Error> { async fn block_body(&self, at: T::Hash) -> Result<Option<Vec<Vec<u8>>>, Error> {
@@ -294,7 +294,7 @@ impl<T: Config + Send + Sync + 'static> Backend<T> for UnstableBackend<T> {
// Subscribe to the body response and get our operationId back. // Subscribe to the body response and get our operationId back.
let follow_events = self.follow_handle.subscribe().events(); let follow_events = self.follow_handle.subscribe().events();
let status = self.methods.chainhead_unstable_body(&sub_id, at).await?; let status = self.methods.chainhead_v1_body(&sub_id, at).await?;
let operation_id = match status { let operation_id = match status {
MethodResponse::LimitReached => { MethodResponse::LimitReached => {
return Err(RpcError::request_rejected("limit reached").into()) return Err(RpcError::request_rejected("limit reached").into())
@@ -645,7 +645,7 @@ impl<T: Config + Send + Sync + 'static> Backend<T> for UnstableBackend<T> {
let call_parameters = call_parameters.unwrap_or(&[]); let call_parameters = call_parameters.unwrap_or(&[]);
let status = self let status = self
.methods .methods
.chainhead_unstable_call(&sub_id, at, method, call_parameters) .chainhead_v1_call(&sub_id, at, method, call_parameters)
.await?; .await?;
let operation_id = match status { let operation_id = match status {
MethodResponse::LimitReached => { MethodResponse::LimitReached => {
+35 -44
View File
@@ -33,48 +33,48 @@ impl<T: Config> UnstableRpcMethods<T> {
} }
} }
/// Subscribe to `chainHead_unstable_follow` to obtain all reported blocks by the chain. /// Subscribe to `chainHead_v1_follow` to obtain all reported blocks by the chain.
/// ///
/// The subscription ID can be used to make queries for the /// The subscription ID can be used to make queries for the
/// block's body ([`chainhead_unstable_body`](UnstableRpcMethods::chainhead_unstable_follow)), /// block's body ([`chainHead_v1_body`](UnstableRpcMethods::chainhead_v1_follow)),
/// block's header ([`chainhead_unstable_header`](UnstableRpcMethods::chainhead_unstable_header)), /// block's header ([`chainHead_v1_header`](UnstableRpcMethods::chainhead_v1_header)),
/// block's storage ([`chainhead_unstable_storage`](UnstableRpcMethods::chainhead_unstable_storage)) and submitting /// block's storage ([`chainHead_v1_storage`](UnstableRpcMethods::chainhead_v1_storage)) and submitting
/// runtime API calls at this block ([`chainhead_unstable_call`](UnstableRpcMethods::chainhead_unstable_call)). /// runtime API calls at this block ([`chainHead_v1_call`](UnstableRpcMethods::chainhead_v1_call)).
/// ///
/// # Note /// # Note
/// ///
/// When the user is no longer interested in a block, the user is responsible /// When the user is no longer interested in a block, the user is responsible
/// for calling the [`chainhead_unstable_unpin`](UnstableRpcMethods::chainhead_unstable_unpin) method. /// for calling the [`chainHead_v1_unpin`](UnstableRpcMethods::chainhead_v1_unpin) method.
/// Failure to do so will result in the subscription being stopped by generating the `Stop` event. /// Failure to do so will result in the subscription being stopped by generating the `Stop` event.
pub async fn chainhead_unstable_follow( pub async fn chainhead_v1_follow(
&self, &self,
with_runtime: bool, with_runtime: bool,
) -> Result<FollowSubscription<T::Hash>, Error> { ) -> Result<FollowSubscription<T::Hash>, Error> {
let sub = self let sub = self
.client .client
.subscribe( .subscribe(
"chainHead_unstable_follow", "chainHead_v1_follow",
rpc_params![with_runtime], rpc_params![with_runtime],
"chainHead_unstable_unfollow", "chainHead_v1_unfollow",
) )
.await?; .await?;
Ok(FollowSubscription { sub, done: false }) Ok(FollowSubscription { sub, done: false })
} }
/// Resumes a storage fetch started with chainHead_unstable_storage after it has generated an /// Resumes a storage fetch started with chainHead_v1_storage after it has generated an
/// `operationWaitingForContinue` event. /// `operationWaitingForContinue` event.
/// ///
/// Has no effect if the operationId is invalid or refers to an operation that has emitted a /// Has no effect if the operationId is invalid or refers to an operation that has emitted a
/// `{"event": "operationInaccessible"` event, or if the followSubscription is invalid or stale. /// `{"event": "operationInaccessible"` event, or if the followSubscription is invalid or stale.
pub async fn chainhead_unstable_continue( pub async fn chainhead_v1_continue(
&self, &self,
follow_subscription: &str, follow_subscription: &str,
operation_id: &str, operation_id: &str,
) -> Result<(), Error> { ) -> Result<(), Error> {
self.client self.client
.request( .request(
"chainHead_unstable_continue", "chainHead_v1_continue",
rpc_params![follow_subscription, operation_id], rpc_params![follow_subscription, operation_id],
) )
.await?; .await?;
@@ -82,19 +82,19 @@ impl<T: Config> UnstableRpcMethods<T> {
Ok(()) Ok(())
} }
/// Stops an operation started with `chainHead_unstable_body`, `chainHead_unstable_call`, or /// Stops an operation started with `chainHead_v1_body`, `chainHead_v1_call`, or
/// `chainHead_unstable_storage¦. If the operation was still in progress, this interrupts it. /// `chainHead_v1_storage¦. If the operation was still in progress, this interrupts it.
/// If the operation was already finished, this call has no effect. /// If the operation was already finished, this call has no effect.
/// ///
/// Has no effect if the `followSubscription` is invalid or stale. /// Has no effect if the `followSubscription` is invalid or stale.
pub async fn chainhead_unstable_stop_operation( pub async fn chainhead_v1_stop_operation(
&self, &self,
follow_subscription: &str, follow_subscription: &str,
operation_id: &str, operation_id: &str,
) -> Result<(), Error> { ) -> Result<(), Error> {
self.client self.client
.request( .request(
"chainHead_unstable_stopOperation", "chainHead_v1_stopOperation",
rpc_params![follow_subscription, operation_id], rpc_params![follow_subscription, operation_id],
) )
.await?; .await?;
@@ -102,7 +102,7 @@ impl<T: Config> UnstableRpcMethods<T> {
Ok(()) Ok(())
} }
/// Call the `chainHead_unstable_body` method and return an operation ID to obtain the block's body. /// Call the `chainHead_v1_body` method and return an operation ID to obtain the block's body.
/// ///
/// The response events are provided on the `chainHead_follow` subscription and identified by /// The response events are provided on the `chainHead_follow` subscription and identified by
/// the returned operation ID. /// the returned operation ID.
@@ -110,30 +110,27 @@ impl<T: Config> UnstableRpcMethods<T> {
/// # Note /// # Note
/// ///
/// The subscription ID is obtained from an open subscription created by /// The subscription ID is obtained from an open subscription created by
/// [`chainhead_unstable_follow`](UnstableRpcMethods::chainhead_unstable_follow). /// [`chainHead_v1_follow`](UnstableRpcMethods::chainhead_v1_follow).
pub async fn chainhead_unstable_body( pub async fn chainhead_v1_body(
&self, &self,
subscription_id: &str, subscription_id: &str,
hash: T::Hash, hash: T::Hash,
) -> Result<MethodResponse, Error> { ) -> Result<MethodResponse, Error> {
let response = self let response = self
.client .client
.request( .request("chainHead_v1_body", rpc_params![subscription_id, hash])
"chainHead_unstable_body",
rpc_params![subscription_id, hash],
)
.await?; .await?;
Ok(response) Ok(response)
} }
/// Get the block's header using the `chainHead_unstable_header` method. /// Get the block's header using the `chainHead_v1_header` method.
/// ///
/// # Note /// # Note
/// ///
/// The subscription ID is obtained from an open subscription created by /// The subscription ID is obtained from an open subscription created by
/// [`chainhead_unstable_follow`](UnstableRpcMethods::chainhead_unstable_follow). /// [`chainHead_v1_follow`](UnstableRpcMethods::chainhead_v1_follow).
pub async fn chainhead_unstable_header( pub async fn chainhead_v1_header(
&self, &self,
subscription_id: &str, subscription_id: &str,
hash: T::Hash, hash: T::Hash,
@@ -141,10 +138,7 @@ impl<T: Config> UnstableRpcMethods<T> {
// header returned as hex encoded SCALE encoded bytes. // header returned as hex encoded SCALE encoded bytes.
let header: Option<Bytes> = self let header: Option<Bytes> = self
.client .client
.request( .request("chainHead_v1_header", rpc_params![subscription_id, hash])
"chainHead_unstable_header",
rpc_params![subscription_id, hash],
)
.await?; .await?;
let header = header let header = header
@@ -153,7 +147,7 @@ impl<T: Config> UnstableRpcMethods<T> {
Ok(header) Ok(header)
} }
/// Call the `chainhead_unstable_storage` method and return an operation ID to obtain the block's storage. /// Call the `chainHead_v1_storage` method and return an operation ID to obtain the block's storage.
/// ///
/// The response events are provided on the `chainHead_follow` subscription and identified by /// The response events are provided on the `chainHead_follow` subscription and identified by
/// the returned operation ID. /// the returned operation ID.
@@ -161,8 +155,8 @@ impl<T: Config> UnstableRpcMethods<T> {
/// # Note /// # Note
/// ///
/// The subscription ID is obtained from an open subscription created by /// The subscription ID is obtained from an open subscription created by
/// [`chainhead_unstable_follow`](UnstableRpcMethods::chainhead_unstable_follow). /// [`chainHead_v1_follow`](UnstableRpcMethods::chainhead_v1_follow).
pub async fn chainhead_unstable_storage( pub async fn chainhead_v1_storage(
&self, &self,
subscription_id: &str, subscription_id: &str,
hash: T::Hash, hash: T::Hash,
@@ -180,7 +174,7 @@ impl<T: Config> UnstableRpcMethods<T> {
let response = self let response = self
.client .client
.request( .request(
"chainHead_unstable_storage", "chainHead_v1_storage",
rpc_params![subscription_id, hash, items, child_key.map(to_hex)], rpc_params![subscription_id, hash, items, child_key.map(to_hex)],
) )
.await?; .await?;
@@ -188,7 +182,7 @@ impl<T: Config> UnstableRpcMethods<T> {
Ok(response) Ok(response)
} }
/// Call the `chainhead_unstable_storage` method and return an operation ID to obtain the runtime API result. /// Call the `chainHead_v1_storage` method and return an operation ID to obtain the runtime API result.
/// ///
/// The response events are provided on the `chainHead_follow` subscription and identified by /// The response events are provided on the `chainHead_follow` subscription and identified by
/// the returned operation ID. /// the returned operation ID.
@@ -196,8 +190,8 @@ impl<T: Config> UnstableRpcMethods<T> {
/// # Note /// # Note
/// ///
/// The subscription ID is obtained from an open subscription created by /// The subscription ID is obtained from an open subscription created by
/// [`chainhead_unstable_follow`](UnstableRpcMethods::chainhead_unstable_follow). /// [`chainHead_v1_follow`](UnstableRpcMethods::chainhead_v1_follow).
pub async fn chainhead_unstable_call( pub async fn chainhead_v1_call(
&self, &self,
subscription_id: &str, subscription_id: &str,
hash: T::Hash, hash: T::Hash,
@@ -207,7 +201,7 @@ impl<T: Config> UnstableRpcMethods<T> {
let response = self let response = self
.client .client
.request( .request(
"chainHead_unstable_call", "chainHead_v1_call",
rpc_params![subscription_id, hash, function, to_hex(call_parameters)], rpc_params![subscription_id, hash, function, to_hex(call_parameters)],
) )
.await?; .await?;
@@ -220,17 +214,14 @@ impl<T: Config> UnstableRpcMethods<T> {
/// # Note /// # Note
/// ///
/// The subscription ID is obtained from an open subscription created by /// The subscription ID is obtained from an open subscription created by
/// [`chainhead_unstable_follow`](UnstableRpcMethods::chainhead_unstable_follow). /// [`chainHead_v1_follow`](UnstableRpcMethods::chainhead_v1_follow).
pub async fn chainhead_unstable_unpin( pub async fn chainhead_v1_unpin(
&self, &self,
subscription_id: &str, subscription_id: &str,
hash: T::Hash, hash: T::Hash,
) -> Result<(), Error> { ) -> Result<(), Error> {
self.client self.client
.request( .request("chainHead_v1_unpin", rpc_params![subscription_id, hash])
"chainHead_unstable_unpin",
rpc_params![subscription_id, hash],
)
.await?; .await?;
Ok(()) Ok(())
+2 -6
View File
@@ -42,7 +42,7 @@ impl<T: Config> StorageItems<T> {
// Subscribe to events and make the initial request to get an operation ID. // Subscribe to events and make the initial request to get an operation ID.
let follow_events = follow_handle.subscribe().events(); let follow_events = follow_handle.subscribe().events();
let status = methods let status = methods
.chainhead_unstable_storage(&sub_id, at, queries, None) .chainhead_v1_storage(&sub_id, at, queries, None)
.await?; .await?;
let operation_id: Arc<str> = match status { let operation_id: Arc<str> = match status {
MethodResponse::LimitReached => { MethodResponse::LimitReached => {
@@ -59,11 +59,7 @@ impl<T: Config> StorageItems<T> {
let operation_id = operation_id.clone(); let operation_id = operation_id.clone();
let methods = methods.clone(); let methods = methods.clone();
Box::pin(async move { Box::pin(async move { methods.chainhead_v1_continue(&sub_id, &operation_id).await })
methods
.chainhead_unstable_continue(&sub_id, &operation_id)
.await
})
}) })
}; };
@@ -22,13 +22,13 @@ use subxt::{
use subxt_signer::sr25519::dev; use subxt_signer::sr25519::dev;
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_follow() { async fn chainhead_v1_follow() {
let ctx = test_context().await; let ctx = test_context().await;
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let legacy_rpc = ctx.legacy_rpc_methods().await; let legacy_rpc = ctx.legacy_rpc_methods().await;
// Check subscription with runtime updates set on false. // Check subscription with runtime updates set on false.
let mut blocks = rpc.chainhead_unstable_follow(false).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(false).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
// The initialized event should contain the finalized block hash. // The initialized event should contain the finalized block hash.
let finalized_block_hash = legacy_rpc.chain_get_finalized_head().await.unwrap(); let finalized_block_hash = legacy_rpc.chain_get_finalized_head().await.unwrap();
@@ -41,7 +41,7 @@ async fn chainhead_unstable_follow() {
); );
// Expect subscription to produce runtime versions. // Expect subscription to produce runtime versions.
let mut blocks = rpc.chainhead_unstable_follow(true).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(true).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
// The initialized event should contain the finalized block hash. // The initialized event should contain the finalized block hash.
let finalized_block_hash = legacy_rpc.chain_get_finalized_head().await.unwrap(); let finalized_block_hash = legacy_rpc.chain_get_finalized_head().await.unwrap();
@@ -62,11 +62,11 @@ async fn chainhead_unstable_follow() {
} }
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_body() { async fn chainhead_v1_body() {
let ctx = test_context().await; let ctx = test_context().await;
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let mut blocks = rpc.chainhead_unstable_follow(false).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(false).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
let hash = match event { let hash = match event {
FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(), FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(),
@@ -75,7 +75,7 @@ async fn chainhead_unstable_body() {
let sub_id = blocks.subscription_id().unwrap(); let sub_id = blocks.subscription_id().unwrap();
// Fetch the block's body. // Fetch the block's body.
let response = rpc.chainhead_unstable_body(sub_id, hash).await.unwrap(); let response = rpc.chainhead_v1_body(sub_id, hash).await.unwrap();
let operation_id = match response { let operation_id = match response {
MethodResponse::Started(started) => started.operation_id, MethodResponse::Started(started) => started.operation_id,
MethodResponse::LimitReached => panic!("Expected started response"), MethodResponse::LimitReached => panic!("Expected started response"),
@@ -90,12 +90,12 @@ async fn chainhead_unstable_body() {
} }
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_header() { async fn chainhead_v1_header() {
let ctx = test_context().await; let ctx = test_context().await;
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let legacy_rpc = ctx.legacy_rpc_methods().await; let legacy_rpc = ctx.legacy_rpc_methods().await;
let mut blocks = rpc.chainhead_unstable_follow(false).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(false).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
let hash = match event { let hash = match event {
FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(), FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(),
@@ -109,7 +109,7 @@ async fn chainhead_unstable_header() {
.unwrap() .unwrap()
.unwrap(); .unwrap();
let old_header = rpc let old_header = rpc
.chainhead_unstable_header(sub_id, hash) .chainhead_v1_header(sub_id, hash)
.await .await
.unwrap() .unwrap()
.unwrap(); .unwrap();
@@ -118,12 +118,12 @@ async fn chainhead_unstable_header() {
} }
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_storage() { async fn chainhead_v1_storage() {
let ctx = test_context().await; let ctx = test_context().await;
let api = ctx.client(); let api = ctx.client();
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let mut blocks = rpc.chainhead_unstable_follow(false).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(false).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
let hash = match event { let hash = match event {
FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(), FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(),
@@ -142,7 +142,7 @@ async fn chainhead_unstable_storage() {
// Fetch storage. // Fetch storage.
let response = rpc let response = rpc
.chainhead_unstable_storage(sub_id, hash, items, None) .chainhead_v1_storage(sub_id, hash, items, None)
.await .await
.unwrap(); .unwrap();
let operation_id = match response { let operation_id = match response {
@@ -164,11 +164,11 @@ async fn chainhead_unstable_storage() {
} }
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_call() { async fn chainhead_v1_call() {
let ctx = test_context().await; let ctx = test_context().await;
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let mut blocks = rpc.chainhead_unstable_follow(true).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(true).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
let hash = match event { let hash = match event {
FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(), FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(),
@@ -179,7 +179,7 @@ async fn chainhead_unstable_call() {
let alice_id = dev::alice().public_key().to_account_id(); let alice_id = dev::alice().public_key().to_account_id();
// Runtime API call. // Runtime API call.
let response = rpc let response = rpc
.chainhead_unstable_call( .chainhead_v1_call(
sub_id, sub_id,
hash, hash,
"AccountNonceApi_account_nonce", "AccountNonceApi_account_nonce",
@@ -201,11 +201,11 @@ async fn chainhead_unstable_call() {
} }
#[subxt_test] #[subxt_test]
async fn chainhead_unstable_unpin() { async fn chainhead_v1_unpin() {
let ctx = test_context().await; let ctx = test_context().await;
let rpc = ctx.unstable_rpc_methods().await; let rpc = ctx.unstable_rpc_methods().await;
let mut blocks = rpc.chainhead_unstable_follow(true).await.unwrap(); let mut blocks = rpc.chainhead_v1_follow(true).await.unwrap();
let event = blocks.next().await.unwrap().unwrap(); let event = blocks.next().await.unwrap().unwrap();
let hash = match event { let hash = match event {
FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(), FollowEvent::Initialized(init) => *init.finalized_block_hashes.last().unwrap(),
@@ -213,9 +213,9 @@ async fn chainhead_unstable_unpin() {
}; };
let sub_id = blocks.subscription_id().unwrap(); let sub_id = blocks.subscription_id().unwrap();
assert!(rpc.chainhead_unstable_unpin(sub_id, hash).await.is_ok()); assert!(rpc.chainhead_v1_unpin(sub_id, hash).await.is_ok());
// The block was already unpinned. // The block was already unpinned.
assert!(rpc.chainhead_unstable_unpin(sub_id, hash).await.is_err()); assert!(rpc.chainhead_v1_unpin(sub_id, hash).await.is_err());
} }
#[cfg(fullclient)] #[cfg(fullclient)]