mirror of
https://github.com/waku-org/nwaku.git
synced 2025-02-05 11:34:45 +00:00
feat: connection change event (#3225)
This commit is contained in:
parent
d932dd10cc
commit
e81a5517be
20
library/events/json_connection_change_event.nim
Normal file
20
library/events/json_connection_change_event.nim
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
import system, std/json, libp2p/[connmanager, peerid]
|
||||||
|
|
||||||
|
import ../../waku/common/base64, ./json_base_event
|
||||||
|
|
||||||
|
type JsonConnectionChangeEvent* = ref object of JsonEvent
|
||||||
|
peerId*: string
|
||||||
|
peerEvent*: PeerEventKind
|
||||||
|
|
||||||
|
proc new*(
|
||||||
|
T: type JsonConnectionChangeEvent, peerId: string, peerEvent: PeerEventKind
|
||||||
|
): T =
|
||||||
|
# Returns a JsonConnectionChangeEvent event as indicated in
|
||||||
|
# https://rfc.vac.dev/spec/36/#jsonmessageevent-type
|
||||||
|
|
||||||
|
return JsonConnectionChangeEvent(
|
||||||
|
eventType: "connection_change", peerId: peerId, peerEvent: peerEvent
|
||||||
|
)
|
||||||
|
|
||||||
|
method `$`*(jsonConnectionChangeEvent: JsonConnectionChangeEvent): string =
|
||||||
|
$(%*jsonConnectionChangeEvent)
|
@ -11,10 +11,12 @@ import
|
|||||||
waku/common/base64,
|
waku/common/base64,
|
||||||
waku/waku_core/message/message,
|
waku/waku_core/message/message,
|
||||||
waku/node/waku_node,
|
waku/node/waku_node,
|
||||||
|
waku/node/peer_manager,
|
||||||
waku/waku_core/topics/pubsub_topic,
|
waku/waku_core/topics/pubsub_topic,
|
||||||
waku/waku_core/subscription/push_handler,
|
waku/waku_core/subscription/push_handler,
|
||||||
waku/waku_relay,
|
waku/waku_relay,
|
||||||
./events/[json_message_event, json_topic_health_change_event],
|
./events/
|
||||||
|
[json_message_event, json_topic_health_change_event, json_connection_change_event],
|
||||||
./waku_thread/waku_thread,
|
./waku_thread/waku_thread,
|
||||||
./waku_thread/inter_thread_communication/requests/node_lifecycle_request,
|
./waku_thread/inter_thread_communication/requests/node_lifecycle_request,
|
||||||
./waku_thread/inter_thread_communication/requests/peer_manager_request,
|
./waku_thread/inter_thread_communication/requests/peer_manager_request,
|
||||||
@ -45,6 +47,29 @@ template checkLibwakuParams*(
|
|||||||
if isNil(callback):
|
if isNil(callback):
|
||||||
return RET_MISSING_CALLBACK
|
return RET_MISSING_CALLBACK
|
||||||
|
|
||||||
|
template callEventCallback(ctx: ptr WakuContext, eventName: string, body: untyped) =
|
||||||
|
if isNil(ctx[].eventCallback):
|
||||||
|
error eventName & " - eventCallback is nil"
|
||||||
|
return
|
||||||
|
|
||||||
|
if isNil(ctx[].eventUserData):
|
||||||
|
error eventName & " - eventUserData is nil"
|
||||||
|
return
|
||||||
|
|
||||||
|
foreignThreadGc:
|
||||||
|
try:
|
||||||
|
let event = body
|
||||||
|
cast[WakuCallBack](ctx[].eventCallback)(
|
||||||
|
RET_OK, unsafeAddr event[0], cast[csize_t](len(event)), ctx[].eventUserData
|
||||||
|
)
|
||||||
|
except Exception, CatchableError:
|
||||||
|
let msg =
|
||||||
|
"Exception " & eventName & " when calling 'eventCallBack': " &
|
||||||
|
getCurrentExceptionMsg()
|
||||||
|
cast[WakuCallBack](ctx[].eventCallback)(
|
||||||
|
RET_ERR, unsafeAddr msg[0], cast[csize_t](len(msg)), ctx[].eventUserData
|
||||||
|
)
|
||||||
|
|
||||||
proc handleRequest(
|
proc handleRequest(
|
||||||
ctx: ptr WakuContext,
|
ctx: ptr WakuContext,
|
||||||
requestType: RequestType,
|
requestType: RequestType,
|
||||||
@ -59,55 +84,20 @@ proc handleRequest(
|
|||||||
|
|
||||||
return RET_OK
|
return RET_OK
|
||||||
|
|
||||||
|
proc onConnectionChange(ctx: ptr WakuContext): ConnectionChangeHandler =
|
||||||
|
return proc(peerId: PeerId, peerEvent: PeerEventKind) {.async.} =
|
||||||
|
callEventCallback(ctx, "onConnectionChange"):
|
||||||
|
$JsonConnectionChangeEvent.new($peerId, peerEvent)
|
||||||
|
|
||||||
proc onReceivedMessage(ctx: ptr WakuContext): WakuRelayHandler =
|
proc onReceivedMessage(ctx: ptr WakuContext): WakuRelayHandler =
|
||||||
return proc(
|
return proc(pubsubTopic: PubsubTopic, msg: WakuMessage) {.async.} =
|
||||||
pubsubTopic: PubsubTopic, msg: WakuMessage
|
callEventCallback(ctx, "onReceivedMessage"):
|
||||||
): Future[system.void] {.async.} =
|
$JsonMessageEvent.new(pubsubTopic, msg)
|
||||||
# Callback that hadles the Waku Relay events. i.e. messages or errors.
|
|
||||||
if isNil(ctx[].eventCallback):
|
|
||||||
error "eventCallback is nil"
|
|
||||||
return
|
|
||||||
|
|
||||||
if isNil(ctx[].eventUserData):
|
|
||||||
error "eventUserData is nil"
|
|
||||||
return
|
|
||||||
|
|
||||||
foreignThreadGc:
|
|
||||||
try:
|
|
||||||
let event = $JsonMessageEvent.new(pubsubTopic, msg)
|
|
||||||
cast[WakuCallBack](ctx[].eventCallback)(
|
|
||||||
RET_OK, unsafeAddr event[0], cast[csize_t](len(event)), ctx[].eventUserData
|
|
||||||
)
|
|
||||||
except Exception, CatchableError:
|
|
||||||
let msg = "Exception when calling 'eventCallBack': " & getCurrentExceptionMsg()
|
|
||||||
cast[WakuCallBack](ctx[].eventCallback)(
|
|
||||||
RET_ERR, unsafeAddr msg[0], cast[csize_t](len(msg)), ctx[].eventUserData
|
|
||||||
)
|
|
||||||
|
|
||||||
proc onTopicHealthChange(ctx: ptr WakuContext): TopicHealthChangeHandler =
|
proc onTopicHealthChange(ctx: ptr WakuContext): TopicHealthChangeHandler =
|
||||||
return proc(pubsubTopic: PubsubTopic, topicHealth: TopicHealth) {.async.} =
|
return proc(pubsubTopic: PubsubTopic, topicHealth: TopicHealth) {.async.} =
|
||||||
# Callback that hadles the Waku Relay events. i.e. messages or errors.
|
callEventCallback(ctx, "onTopicHealthChange"):
|
||||||
if isNil(ctx[].eventCallback):
|
$JsonTopicHealthChangeEvent.new(pubsubTopic, topicHealth)
|
||||||
error "onTopicHealthChange - eventCallback is nil"
|
|
||||||
return
|
|
||||||
|
|
||||||
if isNil(ctx[].eventUserData):
|
|
||||||
error "onTopicHealthChange - eventUserData is nil"
|
|
||||||
return
|
|
||||||
|
|
||||||
foreignThreadGc:
|
|
||||||
try:
|
|
||||||
let event = $JsonTopicHealthChangeEvent.new(pubsubTopic, topicHealth)
|
|
||||||
cast[WakuCallBack](ctx[].eventCallback)(
|
|
||||||
RET_OK, unsafeAddr event[0], cast[csize_t](len(event)), ctx[].eventUserData
|
|
||||||
)
|
|
||||||
except Exception, CatchableError:
|
|
||||||
let msg =
|
|
||||||
"Exception onTopicHealthChange when calling 'eventCallBack': " &
|
|
||||||
getCurrentExceptionMsg()
|
|
||||||
cast[WakuCallBack](ctx[].eventCallback)(
|
|
||||||
RET_ERR, unsafeAddr msg[0], cast[csize_t](len(msg)), ctx[].eventUserData
|
|
||||||
)
|
|
||||||
|
|
||||||
### End of not-exported components
|
### End of not-exported components
|
||||||
################################################################################
|
################################################################################
|
||||||
@ -167,6 +157,7 @@ proc waku_new(
|
|||||||
let appCallbacks = AppCallbacks(
|
let appCallbacks = AppCallbacks(
|
||||||
relayHandler: onReceivedMessage(ctx),
|
relayHandler: onReceivedMessage(ctx),
|
||||||
topicHealthChangeHandler: onTopicHealthChange(ctx),
|
topicHealthChangeHandler: onTopicHealthChange(ctx),
|
||||||
|
connectionChangeHandler: onConnectionChange(ctx),
|
||||||
)
|
)
|
||||||
|
|
||||||
let retCode = handleRequest(
|
let retCode = handleRequest(
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import ../waku_relay
|
import ../waku_relay, ../node/peer_manager
|
||||||
|
|
||||||
type AppCallbacks* = ref object
|
type AppCallbacks* = ref object
|
||||||
relayHandler*: WakuRelayHandler
|
relayHandler*: WakuRelayHandler
|
||||||
topicHealthChangeHandler*: TopicHealthChangeHandler
|
topicHealthChangeHandler*: TopicHealthChangeHandler
|
||||||
|
connectionChangeHandler*: ConnectionChangeHandler
|
||||||
|
@ -175,6 +175,12 @@ proc setupAppCallbacks(
|
|||||||
err("Cannot configure topicHealthChangeHandler callback without Relay mounted")
|
err("Cannot configure topicHealthChangeHandler callback without Relay mounted")
|
||||||
node.wakuRelay.onTopicHealthChange = appCallbacks.topicHealthChangeHandler
|
node.wakuRelay.onTopicHealthChange = appCallbacks.topicHealthChangeHandler
|
||||||
|
|
||||||
|
if not appCallbacks.connectionChangeHandler.isNil():
|
||||||
|
if node.peerManager.isNil():
|
||||||
|
return
|
||||||
|
err("Cannot configure connectionChangeHandler callback with empty peer manager")
|
||||||
|
node.peerManager.onConnectionChange = appCallbacks.connectionChangeHandler
|
||||||
|
|
||||||
return ok()
|
return ok()
|
||||||
|
|
||||||
proc new*(
|
proc new*(
|
||||||
|
@ -71,6 +71,10 @@ const
|
|||||||
# Max peers that we allow from the same IP
|
# Max peers that we allow from the same IP
|
||||||
DefaultColocationLimit* = 5
|
DefaultColocationLimit* = 5
|
||||||
|
|
||||||
|
type ConnectionChangeHandler* = proc(
|
||||||
|
peerId: PeerId, peerEvent: PeerEventKind
|
||||||
|
): Future[void] {.gcsafe, raises: [Defect].}
|
||||||
|
|
||||||
type PeerManager* = ref object of RootObj
|
type PeerManager* = ref object of RootObj
|
||||||
switch*: Switch
|
switch*: Switch
|
||||||
wakuPeerStore*: WakuPeerStore
|
wakuPeerStore*: WakuPeerStore
|
||||||
@ -87,6 +91,7 @@ type PeerManager* = ref object of RootObj
|
|||||||
colocationLimit*: int
|
colocationLimit*: int
|
||||||
started: bool
|
started: bool
|
||||||
shardedPeerManagement: bool # temp feature flag
|
shardedPeerManagement: bool # temp feature flag
|
||||||
|
onConnectionChange*: ConnectionChangeHandler
|
||||||
|
|
||||||
#~~~~~~~~~~~~~~~~~~~#
|
#~~~~~~~~~~~~~~~~~~~#
|
||||||
# Helper Functions #
|
# Helper Functions #
|
||||||
@ -676,6 +681,9 @@ proc onPeerEvent(pm: PeerManager, peerId: PeerId, event: PeerEvent) {.async.} =
|
|||||||
debug "Pruning connection due to ip colocation", peerId = peerId, ip = ip
|
debug "Pruning connection due to ip colocation", peerId = peerId, ip = ip
|
||||||
asyncSpawn(pm.switch.disconnect(peerId))
|
asyncSpawn(pm.switch.disconnect(peerId))
|
||||||
pm.wakuPeerStore.delete(peerId)
|
pm.wakuPeerStore.delete(peerId)
|
||||||
|
if not pm.onConnectionChange.isNil():
|
||||||
|
# we don't want to await for the callback to finish
|
||||||
|
asyncSpawn pm.onConnectionChange(peerId, Joined)
|
||||||
of Left:
|
of Left:
|
||||||
direction = UnknownDirection
|
direction = UnknownDirection
|
||||||
connectedness = CanConnect
|
connectedness = CanConnect
|
||||||
@ -687,6 +695,9 @@ proc onPeerEvent(pm: PeerManager, peerId: PeerId, event: PeerEvent) {.async.} =
|
|||||||
if pm.ipTable[ip].len == 0:
|
if pm.ipTable[ip].len == 0:
|
||||||
pm.ipTable.del(ip)
|
pm.ipTable.del(ip)
|
||||||
break
|
break
|
||||||
|
if not pm.onConnectionChange.isNil():
|
||||||
|
# we don't want to await for the callback to finish
|
||||||
|
asyncSpawn pm.onConnectionChange(peerId, Left)
|
||||||
of Identified:
|
of Identified:
|
||||||
debug "event identified", peerId = peerId
|
debug "event identified", peerId = peerId
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user