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

feat: add QUIC transport to the chat example #3635

Merged
merged 8 commits into from
Mar 24, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
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 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion examples/chat-example/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,5 @@ async-std = { version = "1.12", features = ["attributes"] }
async-trait = "0.1"
env_logger = "0.10.0"
futures = "0.3.27"
libp2p = { path = "../../libp2p", features = ["async-std", "dns", "gossipsub", "mdns", "mplex", "noise", "macros", "tcp", "websocket", "yamux"] }
libp2p = { path = "../../libp2p", features = ["async-std", "gossipsub", "mdns", "mplex", "noise", "macros", "tcp", "yamux"] }
libp2p-quic = { path = "../../transports/quic", features = ["async-std"] }
50 changes: 34 additions & 16 deletions examples/chat-example/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,34 +46,50 @@
//! event and remove the expired peer from the list of known peers.

use async_std::io;
use futures::{prelude::*, select};
use futures::{future::Either, prelude::*, select};
use libp2p::{
gossipsub, identity, mdns,
core::{muxing::StreamMuxerBox, transport::OrTransport, upgrade},
gossipsub, identity, mdns, noise,
swarm::NetworkBehaviour,
swarm::{SwarmBuilder, SwarmEvent},
PeerId,
tcp, yamux, PeerId, Transport,
};
use libp2p_quic as quic;
use std::collections::hash_map::DefaultHasher;
use std::error::Error;
use std::hash::{Hash, Hasher};
use std::time::Duration;

// We create a custom network behaviour that combines Gossipsub and Mdns.
#[derive(NetworkBehaviour)]
struct MyBehaviour {
gossipsub: gossipsub::Behaviour,
mdns: mdns::async_io::Behaviour,
}
thomaseizinger marked this conversation as resolved.
Show resolved Hide resolved

#[async_std::main]
async fn main() -> Result<(), Box<dyn Error>> {
// Create a random PeerId
let local_key = identity::Keypair::generate_ed25519();
let local_peer_id = PeerId::from(local_key.public());
let id_keys = identity::Keypair::generate_ed25519();
let local_peer_id = PeerId::from(id_keys.public());
println!("Local peer id: {local_peer_id}");

// Set up an encrypted DNS-enabled TCP Transport over the Mplex protocol.
let transport = libp2p::development_transport(local_key.clone()).await?;

// We create a custom network behaviour that combines Gossipsub and Mdns.
#[derive(NetworkBehaviour)]
struct MyBehaviour {
gossipsub: gossipsub::Behaviour,
mdns: mdns::async_io::Behaviour,
}
let tcp_transport = tcp::async_io::Transport::new(tcp::Config::default().nodelay(true))
.upgrade(upgrade::Version::V1)
.authenticate(
noise::NoiseAuthenticated::xx(&id_keys).expect("signing libp2p-noise static keypair"),
)
.multiplex(yamux::YamuxConfig::default())
.timeout(std::time::Duration::from_secs(20))
.boxed();
let quic_transport = quic::async_std::Transport::new(quic::Config::new(&id_keys));
let transport = OrTransport::new(quic_transport, tcp_transport)
.map(|either_output, _| match either_output {
Either::Left((peer_id, muxer)) => (peer_id, StreamMuxerBox::new(muxer)),
Either::Right((peer_id, muxer)) => (peer_id, StreamMuxerBox::new(muxer)),
})
thomaseizinger marked this conversation as resolved.
Show resolved Hide resolved
.boxed();

// To content-address message, we can take the hash of message and use it as an ID.
let message_id_fn = |message: &gossipsub::Message| {
Expand All @@ -92,14 +108,12 @@ async fn main() -> Result<(), Box<dyn Error>> {

// build a gossipsub network behaviour
let mut gossipsub = gossipsub::Behaviour::new(
gossipsub::MessageAuthenticity::Signed(local_key),
gossipsub::MessageAuthenticity::Signed(id_keys),
gossipsub_config,
)
.expect("Correct configuration");

// Create a Gossipsub topic
let topic = gossipsub::IdentTopic::new("test-net");

// subscribes to our topic
gossipsub.subscribe(&topic)?;

Expand All @@ -114,6 +128,7 @@ async fn main() -> Result<(), Box<dyn Error>> {
let mut stdin = io::BufReader::new(io::stdin()).lines().fuse();

// Listen on all interfaces and whatever port the OS assigns
swarm.listen_on("/ip4/0.0.0.0/udp/0/quic-v1".parse()?)?;
swarm.listen_on("/ip4/0.0.0.0/tcp/0".parse()?)?;

println!("Enter messages via STDIN and they will be sent to connected peers using Gossipsub");
Expand Down Expand Up @@ -149,6 +164,9 @@ async fn main() -> Result<(), Box<dyn Error>> {
"Got message: '{}' with id: {id} from peer: {peer_id}",
String::from_utf8_lossy(&message.data),
),
SwarmEvent::NewListenAddr { address, .. } => {
println!("Local node is listening on {address}");
}
_ => {}
}
}
Expand Down