Skip to content

Commit

Permalink
chore: release v0.4.0 (#31)
Browse files Browse the repository at this point in the history
  • Loading branch information
niklasad1 authored Apr 20, 2024
1 parent c54a5b7 commit 0a8e9fb
Show file tree
Hide file tree
Showing 6 changed files with 203 additions and 93 deletions.
14 changes: 14 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,20 @@ The format is based on [Keep a Changelog].

[Keep a Changelog]: http://keepachangelog.com/en/1.0.0/

## [v0.4.0] - 2023-04-20

A new release that makes the library support WASM and two feature flags, `native` and `web` are introduced
to select whether to compile the library for `native` or `web` but the default is still `native`.

Some other fixes were:
- Re-export all types in the public API
- Support other retry strategies for calls and subscriptions.
- Improve the reconnect API to know when the reconnection started and was completed.
- Provide an error type.
- Improve internal feature flag handling.

Thanks to [@seunlanlege](https://github.com/seunlanlege) who did the majority of the work
to get the library working for WASM.

## [v0.3.0] - 2023-02-08

Expand Down
23 changes: 13 additions & 10 deletions Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,27 +1,29 @@
[package]
name = "reconnecting-jsonrpsee-ws-client"
authors = ["Niklas Adolfsson <niklasadolfsson1@gmail.com>"]
version = "0.3.0"
version = "0.4.0"
edition = "2021"
rust-version = "1.70.0"
license = "MIT"
repository = "https://github.com/niklasad1/reconnecting-jsonrpsee-ws-client"
description = "jsonrpc-ws-client that reconnects automatically. Warning: It may lose subscription messages when reconnecting."
documentation = "https://docs.rs/reconnecting-jsonrpsee-ws-client"
keywords = ["jsonrpc", "json", "websocket"]
keywords = ["jsonrpc", "json", "websocket", "WASM"]
readme = "README.md"

[dependencies]
futures = { version = "0.3", default-features = false }
jsonrpsee = { version = "0.22.4", default-features = false }
jsonrpsee = { version = "0.22.4" }
serde_json = { version = "1", features = ["raw_value"], default-features = false }
tokio = { version = "1.37", features = ["sync"], default-features = false }
tracing = { version = "0.1", default-features = false }
thiserror = "1"
finito = "0.1"

# WASM
wasm-bindgen-futures = { version = "0.4.41", optional = true }

thiserror = "1"
finito = "0.1"

[features]
default = ["native"]
native = [
Expand All @@ -32,9 +34,7 @@ native = [
"jsonrpsee/ws-client",
]
web = [
"jsonrpsee/jsonrpsee-types",
"jsonrpsee/async-wasm-client",
"jsonrpsee/client-web-transport",
"jsonrpsee/wasm-client",
"wasm-bindgen-futures",
"finito/wasm-bindgen"
]
Expand All @@ -45,9 +45,12 @@ hyper = { version = "0.14", features = ["server", "tcp"] }
anyhow = "1"
tracing-subscriber = { version = "0.3.17", features = ["env-filter"] }

[build-dependencies]
cfg_aliases = "0.2.0"

[package.metadata.docs.rs]
all-features = true
features = ["default"]
rustdoc-args = ["--cfg", "docsrs"]

[package.metadata.playground]
all-features = true
features = ["default"]
59 changes: 52 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,16 +1,58 @@
# reconnecting-jsonrpsee-ws-client

Wrapper crate over the jsonrpsee ws client, which automatically reconnects
under the hood; without that, the user has to restart it manually by
re-transmitting pending calls and re-establish subscriptions that
were closed when the connection was terminated.
under the hood; without that, one has to restart it.
It supports a few retry strategies, such as exponential backoff, but it's also possible
to use custom strategies as long as it implements `Iterator<Item = Duration>`.


By default, the library is re-transmitting pending calls and re-establishing subscriptions that
were closed when the connection was terminated, but it's also possible to disable that
and manage it yourself.


For instance, you may not want to re-subscribe to a subscription
that has side effects or retries at all. Then the library exposes
`request_with_policy` and `subscribe_with_policy` to support that


```text
let mut sub = client
.subscribe_with_policy(
"subscribe_lo".to_string(),
rpc_params![],
"unsubscribe_lo".to_string(),
// Do not re-subscribe if the connection is closed.
CallRetryPolicy::Retry,
)
.await
.unwrap();
```


The tricky part is subscriptions, which may lose a few notifications
when it's re-connecting where it's not possible to know which ones.
when it's re-connecting, it's not possible to know which ones.


Lost subscription notifications may be very important to know in some cases,
and then this library is not recommended to use.


There is one way to determine how long a reconnection takes:

```text
// Print when the RPC client starts to reconnect.
loop {
rpc.reconnect_started().await;
let now = std::time::Instant::now();
rpc.reconnected().await;
println!(
"RPC client reconnection took `{} seconds`",
now.elapsed().as_secs()
);
}
```

## Example

```rust
Expand All @@ -20,13 +62,16 @@ use std::time::Duration;
async fn run() {
// Create a new client with with a reconnecting RPC client.
let client = Client::builder()
// Reconnect with exponential backoff.
.retry_policy(ExponentialBackoff::from_millis(100))
// Reconnect with exponential backoff and if fails more then
// 10 retries we give up and terminate.
.retry_policy(ExponentialBackoff::from_millis(100).take(10))
// Send period WebSocket pings/pongs every 6th second and
// if ACK:ed in 30 seconds then disconnect.
//
// This is just a way to ensure that the connection isn't
// idle if no message is sent that often
//
// This only works for native.
.enable_ws_ping(
PingConfig::new()
.ping_interval(Duration::from_secs(6))
Expand All @@ -53,4 +98,4 @@ async fn run() {
.unwrap();
let notif = sub.next().await.unwrap();
}
```
```
10 changes: 10 additions & 0 deletions build.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
use cfg_aliases::cfg_aliases;

fn main() {
// Setup cfg aliases
cfg_aliases! {
native : { all(feature = "native", not(feature = "web"), not(target_arch = "wasm32")) },
web : { all(feature = "web", target_arch = "wasm32", not(feature = "native")) },
not_supported: { not(any(native, web)) },
}
}
Loading

0 comments on commit 0a8e9fb

Please sign in to comment.