Skip to content

Commit bb40137

Browse files
authored
Merge pull request #794 from openmina/feat/p2p/webrtc/signaling
P2p WebRTC: peer discovery and p2p based signaling
2 parents f734ab0 + 6ef444f commit bb40137

File tree

72 files changed

+2685
-129
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

72 files changed

+2685
-129
lines changed

.github/workflows/ci.yaml

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,7 @@ jobs:
284284
needs:
285285
- k8s-peers
286286
- build-tests
287-
# - build-tests-webrtc
287+
- build-tests-webrtc
288288
runs-on: ubuntu-20.04
289289
container:
290290
image: minaprotocol/mina-daemon:3.0.0-dc6bf78-focal-devnet
@@ -309,6 +309,7 @@ jobs:
309309
- connection_discovery_rust_as_seed
310310
- connection_discovery_rust_to_ocaml_via_seed
311311
- connection_discovery_rust_to_ocaml
312+
- webrtc_p2p_signaling
312313
# - webrtc_single_node
313314
# - webrtc_multi_node
314315
fail-fast: false
@@ -331,6 +332,12 @@ jobs:
331332
with:
332333
pattern: tests*
333334
merge-multiple: true
335+
336+
- name: Download tests
337+
uses: actions/download-artifact@v4
338+
with:
339+
pattern: tests-webrtc*
340+
merge-multiple: true
334341

335342
- name: Setup permissions
336343
run: |

.github/workflows/lint.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ jobs:
1717
sudo apt install -y protobuf-compiler
1818
- uses: actions-rs/toolchain@v1
1919
with:
20-
toolchain: 1.79
20+
toolchain: 1.81
2121
components: rustfmt, clippy
2222
default: true
2323
- uses: actions-rs/cargo@v1
@@ -36,4 +36,4 @@ jobs:
3636
name: clippy
3737
with:
3838
token: ${{ secrets.GITHUB_TOKEN }}
39-
args: --all-targets -- -D warnings
39+
args: --all-targets -- -D warnings --allow clippy::mutable_key_type --allow clippy::result_unit_err

Cargo.lock

Lines changed: 4 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

mina-p2p-messages/benches/gossip-binprot.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
#![allow(unexpected_cfgs)]
12
#![cfg(benchmarks)]
23
#![feature(test)]
34

mina-p2p-messages/tests/rpc-read.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,7 @@ fn debugger_to_wire() {
158158
"v1/rpc/get-transition-knowledge",
159159
"v1/rpc/get-ancestry",
160160
] {
161-
for_all_with_path(&PathBuf::from(d).join("response"), |encoded, path| {
161+
for_all_with_path(PathBuf::from(d).join("response"), |encoded, path| {
162162
let mut p = &encoded[1..];
163163
let tag = BinprotTag::binprot_read(&mut p).unwrap().to_string_lossy();
164164
let ver = Ver::binprot_read(&mut p).unwrap();

node/common/src/service/p2p.rs

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,11 @@ use std::collections::BTreeMap;
33
use node::{
44
core::channels::mpsc,
55
event_source::Event,
6-
p2p::{connection::outgoing::P2pConnectionOutgoingInitOpts, PeerId},
6+
p2p::{
7+
connection::outgoing::P2pConnectionOutgoingInitOpts,
8+
identity::{EncryptableType, PublicKey},
9+
PeerId,
10+
},
711
};
812
use rand::prelude::*;
913
#[cfg(feature = "p2p-libp2p")]
@@ -34,6 +38,23 @@ impl webrtc::P2pServiceWebrtc for NodeService {
3438
fn peers(&mut self) -> &mut BTreeMap<PeerId, webrtc::PeerState> {
3539
&mut self.p2p.webrtc.peers
3640
}
41+
42+
fn encrypt<T: EncryptableType>(
43+
&mut self,
44+
other_pk: &PublicKey,
45+
message: &T,
46+
) -> Result<T::Encrypted, ()> {
47+
let rng = &mut self.rng;
48+
self.p2p.sec_key.encrypt(other_pk, rng, message)
49+
}
50+
51+
fn decrypt<T: EncryptableType>(
52+
&mut self,
53+
other_pk: &PublicKey,
54+
encrypted: &T::Encrypted,
55+
) -> Result<T, ()> {
56+
self.p2p.sec_key.decrypt(other_pk, encrypted)
57+
}
3758
}
3859

3960
impl webrtc_with_libp2p::P2pServiceWebrtcWithLibp2p for NodeService {

node/common/src/service/rpc/state.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,16 @@ impl State {
2323
#[cfg(target_family = "wasm")]
2424
#[cfg_attr(target_family = "wasm", wasm_bindgen)]
2525
impl State {
26+
pub async fn get(&self, filter: String) -> JsValue {
27+
let res = self
28+
.sender
29+
.oneshot_request::<RpcStateGetResponse>(RpcRequest::StateGet(Some(filter)))
30+
.await
31+
.and_then(|v| v.ok());
32+
res.map(|res| JsValue::from_serde(&res).unwrap_or_default())
33+
.unwrap_or_default()
34+
}
35+
2636
pub async fn peers(&self) -> JsValue {
2737
let res = self
2838
.sender

node/native/src/http_server.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,9 @@ pub async fn run(port: u16, rpc_sender: RpcSender) {
6565
false => StatusCode::OK,
6666
true => StatusCode::BAD_REQUEST,
6767
},
68+
P2pConnectionResponse::SignalDecryptionFailed => {
69+
StatusCode::BAD_REQUEST
70+
}
6871
P2pConnectionResponse::InternalError => {
6972
StatusCode::INTERNAL_SERVER_ERROR
7073
}

node/src/action_kind.rs

Lines changed: 141 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,10 @@ use crate::p2p::channels::best_tip::P2pChannelsBestTipAction;
2828
use crate::p2p::channels::best_tip_effectful::P2pChannelsBestTipEffectfulAction;
2929
use crate::p2p::channels::rpc::P2pChannelsRpcAction;
3030
use crate::p2p::channels::rpc_effectful::P2pChannelsRpcEffectfulAction;
31+
use crate::p2p::channels::signaling::discovery::P2pChannelsSignalingDiscoveryAction;
32+
use crate::p2p::channels::signaling::discovery_effectful::P2pChannelsSignalingDiscoveryEffectfulAction;
33+
use crate::p2p::channels::signaling::exchange::P2pChannelsSignalingExchangeAction;
34+
use crate::p2p::channels::signaling::exchange_effectful::P2pChannelsSignalingExchangeEffectfulAction;
3135
use crate::p2p::channels::snark::P2pChannelsSnarkAction;
3236
use crate::p2p::channels::snark_effectful::P2pChannelsSnarkEffectfulAction;
3337
use crate::p2p::channels::snark_job_commitment::P2pChannelsSnarkJobCommitmentAction;
@@ -209,6 +213,41 @@ pub enum ActionKind {
209213
P2pChannelsRpcEffectfulInit,
210214
P2pChannelsRpcEffectfulRequestSend,
211215
P2pChannelsRpcEffectfulResponseSend,
216+
P2pChannelsSignalingDiscoveryAnswerDecrypted,
217+
P2pChannelsSignalingDiscoveryAnswerReceived,
218+
P2pChannelsSignalingDiscoveryAnswerSend,
219+
P2pChannelsSignalingDiscoveryDiscoveredAccept,
220+
P2pChannelsSignalingDiscoveryDiscoveredAcceptReceived,
221+
P2pChannelsSignalingDiscoveryDiscoveredReceived,
222+
P2pChannelsSignalingDiscoveryDiscoveredReject,
223+
P2pChannelsSignalingDiscoveryDiscoveredRejectReceived,
224+
P2pChannelsSignalingDiscoveryDiscoveredSend,
225+
P2pChannelsSignalingDiscoveryDiscoveryRequestReceived,
226+
P2pChannelsSignalingDiscoveryDiscoveryRequestSend,
227+
P2pChannelsSignalingDiscoveryInit,
228+
P2pChannelsSignalingDiscoveryPending,
229+
P2pChannelsSignalingDiscoveryReady,
230+
P2pChannelsSignalingDiscoveryRequestReceived,
231+
P2pChannelsSignalingDiscoveryRequestSend,
232+
P2pChannelsSignalingDiscoveryEffectfulAnswerDecrypt,
233+
P2pChannelsSignalingDiscoveryEffectfulInit,
234+
P2pChannelsSignalingDiscoveryEffectfulMessageSend,
235+
P2pChannelsSignalingDiscoveryEffectfulOfferEncryptAndSend,
236+
P2pChannelsSignalingExchangeAnswerReceived,
237+
P2pChannelsSignalingExchangeAnswerSend,
238+
P2pChannelsSignalingExchangeInit,
239+
P2pChannelsSignalingExchangeOfferDecryptError,
240+
P2pChannelsSignalingExchangeOfferDecryptSuccess,
241+
P2pChannelsSignalingExchangeOfferReceived,
242+
P2pChannelsSignalingExchangeOfferSend,
243+
P2pChannelsSignalingExchangePending,
244+
P2pChannelsSignalingExchangeReady,
245+
P2pChannelsSignalingExchangeRequestReceived,
246+
P2pChannelsSignalingExchangeRequestSend,
247+
P2pChannelsSignalingExchangeEffectfulAnswerEncryptAndSend,
248+
P2pChannelsSignalingExchangeEffectfulInit,
249+
P2pChannelsSignalingExchangeEffectfulMessageSend,
250+
P2pChannelsSignalingExchangeEffectfulOfferDecrypt,
212251
P2pChannelsSnarkInit,
213252
P2pChannelsSnarkLibp2pBroadcast,
214253
P2pChannelsSnarkLibp2pReceived,
@@ -618,7 +657,7 @@ pub enum ActionKind {
618657
}
619658

620659
impl ActionKind {
621-
pub const COUNT: u16 = 510;
660+
pub const COUNT: u16 = 545;
622661
}
623662

624663
impl std::fmt::Display for ActionKind {
@@ -1029,6 +1068,8 @@ impl ActionKindGet for P2pChannelsAction {
10291068
fn kind(&self) -> ActionKind {
10301069
match self {
10311070
Self::MessageReceived(a) => a.kind(),
1071+
Self::SignalingDiscovery(a) => a.kind(),
1072+
Self::SignalingExchange(a) => a.kind(),
10321073
Self::BestTip(a) => a.kind(),
10331074
Self::Transaction(a) => a.kind(),
10341075
Self::Snark(a) => a.kind(),
@@ -1069,6 +1110,8 @@ impl ActionKindGet for P2pNetworkAction {
10691110
impl ActionKindGet for P2pChannelsEffectfulAction {
10701111
fn kind(&self) -> ActionKind {
10711112
match self {
1113+
Self::SignalingDiscovery(a) => a.kind(),
1114+
Self::SignalingExchange(a) => a.kind(),
10721115
Self::BestTip(a) => a.kind(),
10731116
Self::Rpc(a) => a.kind(),
10741117
Self::Snark(a) => a.kind(),
@@ -1400,6 +1443,69 @@ impl ActionKindGet for P2pChannelsMessageReceivedAction {
14001443
}
14011444
}
14021445

1446+
impl ActionKindGet for P2pChannelsSignalingDiscoveryAction {
1447+
fn kind(&self) -> ActionKind {
1448+
match self {
1449+
Self::Init { .. } => ActionKind::P2pChannelsSignalingDiscoveryInit,
1450+
Self::Pending { .. } => ActionKind::P2pChannelsSignalingDiscoveryPending,
1451+
Self::Ready { .. } => ActionKind::P2pChannelsSignalingDiscoveryReady,
1452+
Self::RequestSend { .. } => ActionKind::P2pChannelsSignalingDiscoveryRequestSend,
1453+
Self::DiscoveryRequestReceived { .. } => {
1454+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveryRequestReceived
1455+
}
1456+
Self::DiscoveredSend { .. } => ActionKind::P2pChannelsSignalingDiscoveryDiscoveredSend,
1457+
Self::DiscoveredRejectReceived { .. } => {
1458+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveredRejectReceived
1459+
}
1460+
Self::DiscoveredAcceptReceived { .. } => {
1461+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveredAcceptReceived
1462+
}
1463+
Self::AnswerSend { .. } => ActionKind::P2pChannelsSignalingDiscoveryAnswerSend,
1464+
Self::RequestReceived { .. } => {
1465+
ActionKind::P2pChannelsSignalingDiscoveryRequestReceived
1466+
}
1467+
Self::DiscoveryRequestSend { .. } => {
1468+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveryRequestSend
1469+
}
1470+
Self::DiscoveredReceived { .. } => {
1471+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveredReceived
1472+
}
1473+
Self::DiscoveredReject { .. } => {
1474+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveredReject
1475+
}
1476+
Self::DiscoveredAccept { .. } => {
1477+
ActionKind::P2pChannelsSignalingDiscoveryDiscoveredAccept
1478+
}
1479+
Self::AnswerReceived { .. } => ActionKind::P2pChannelsSignalingDiscoveryAnswerReceived,
1480+
Self::AnswerDecrypted { .. } => {
1481+
ActionKind::P2pChannelsSignalingDiscoveryAnswerDecrypted
1482+
}
1483+
}
1484+
}
1485+
}
1486+
1487+
impl ActionKindGet for P2pChannelsSignalingExchangeAction {
1488+
fn kind(&self) -> ActionKind {
1489+
match self {
1490+
Self::Init { .. } => ActionKind::P2pChannelsSignalingExchangeInit,
1491+
Self::Pending { .. } => ActionKind::P2pChannelsSignalingExchangePending,
1492+
Self::Ready { .. } => ActionKind::P2pChannelsSignalingExchangeReady,
1493+
Self::RequestSend { .. } => ActionKind::P2pChannelsSignalingExchangeRequestSend,
1494+
Self::OfferReceived { .. } => ActionKind::P2pChannelsSignalingExchangeOfferReceived,
1495+
Self::OfferDecryptError { .. } => {
1496+
ActionKind::P2pChannelsSignalingExchangeOfferDecryptError
1497+
}
1498+
Self::OfferDecryptSuccess { .. } => {
1499+
ActionKind::P2pChannelsSignalingExchangeOfferDecryptSuccess
1500+
}
1501+
Self::AnswerSend { .. } => ActionKind::P2pChannelsSignalingExchangeAnswerSend,
1502+
Self::RequestReceived { .. } => ActionKind::P2pChannelsSignalingExchangeRequestReceived,
1503+
Self::OfferSend { .. } => ActionKind::P2pChannelsSignalingExchangeOfferSend,
1504+
Self::AnswerReceived { .. } => ActionKind::P2pChannelsSignalingExchangeAnswerReceived,
1505+
}
1506+
}
1507+
}
1508+
14031509
impl ActionKindGet for P2pChannelsBestTipAction {
14041510
fn kind(&self) -> ActionKind {
14051511
match self {
@@ -1652,6 +1758,40 @@ impl ActionKindGet for P2pNetworkRpcAction {
16521758
}
16531759
}
16541760

1761+
impl ActionKindGet for P2pChannelsSignalingDiscoveryEffectfulAction {
1762+
fn kind(&self) -> ActionKind {
1763+
match self {
1764+
Self::Init { .. } => ActionKind::P2pChannelsSignalingDiscoveryEffectfulInit,
1765+
Self::MessageSend { .. } => {
1766+
ActionKind::P2pChannelsSignalingDiscoveryEffectfulMessageSend
1767+
}
1768+
Self::OfferEncryptAndSend { .. } => {
1769+
ActionKind::P2pChannelsSignalingDiscoveryEffectfulOfferEncryptAndSend
1770+
}
1771+
Self::AnswerDecrypt { .. } => {
1772+
ActionKind::P2pChannelsSignalingDiscoveryEffectfulAnswerDecrypt
1773+
}
1774+
}
1775+
}
1776+
}
1777+
1778+
impl ActionKindGet for P2pChannelsSignalingExchangeEffectfulAction {
1779+
fn kind(&self) -> ActionKind {
1780+
match self {
1781+
Self::Init { .. } => ActionKind::P2pChannelsSignalingExchangeEffectfulInit,
1782+
Self::MessageSend { .. } => {
1783+
ActionKind::P2pChannelsSignalingExchangeEffectfulMessageSend
1784+
}
1785+
Self::OfferDecrypt { .. } => {
1786+
ActionKind::P2pChannelsSignalingExchangeEffectfulOfferDecrypt
1787+
}
1788+
Self::AnswerEncryptAndSend { .. } => {
1789+
ActionKind::P2pChannelsSignalingExchangeEffectfulAnswerEncryptAndSend
1790+
}
1791+
}
1792+
}
1793+
}
1794+
16551795
impl ActionKindGet for P2pChannelsBestTipEffectfulAction {
16561796
fn kind(&self) -> ActionKind {
16571797
match self {

node/src/event_source/event_source_effects.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
use p2p::channels::signaling::discovery::P2pChannelsSignalingDiscoveryAction;
2+
use p2p::channels::signaling::exchange::P2pChannelsSignalingExchangeAction;
13
use p2p::channels::snark::P2pChannelsSnarkAction;
24
use p2p::channels::streaming_rpc::P2pChannelsStreamingRpcAction;
35
use p2p::channels::transaction::P2pChannelsTransactionAction;
@@ -158,6 +160,12 @@ pub fn event_source_effects<S: Service>(store: &mut Store<S>, action: EventSourc
158160
error: P2pConnectionErrorResponse::Rejected(reason),
159161
});
160162
}
163+
P2pConnectionResponse::SignalDecryptionFailed => {
164+
store.dispatch(P2pConnectionOutgoingAction::AnswerRecvError {
165+
peer_id,
166+
error: P2pConnectionErrorResponse::SignalDecryptionFailed,
167+
});
168+
}
161169
P2pConnectionResponse::InternalError => {
162170
store.dispatch(P2pConnectionOutgoingAction::AnswerRecvError {
163171
peer_id,
@@ -194,8 +202,17 @@ pub fn event_source_effects<S: Service>(store: &mut Store<S>, action: EventSourc
194202
openmina_core::log::warn!(meta.time(); kind = "P2pChannelEvent::Opened", peer_id = peer_id.to_string(), error = err);
195203
// TODO(binier): dispatch error action.
196204
}
197-
// TODO(binier): maybe dispatch success and then ready.
198205
Ok(_) => match chan_id {
206+
ChannelId::SignalingDiscovery => {
207+
store.dispatch(P2pChannelsSignalingDiscoveryAction::Ready {
208+
peer_id,
209+
});
210+
}
211+
ChannelId::SignalingExchange => {
212+
store.dispatch(P2pChannelsSignalingExchangeAction::Ready {
213+
peer_id,
214+
});
215+
}
199216
ChannelId::BestTipPropagation => {
200217
store.dispatch(P2pChannelsBestTipAction::Ready { peer_id });
201218
}

0 commit comments

Comments
 (0)