mirror of https://github.com/waku-org/nwaku.git
refactor(wakunode2): extract setup proc definitions from main section
This commit is contained in:
parent
bdb120d842
commit
c19081b6ce
|
@ -49,23 +49,9 @@ logScope:
|
|||
topics = "wakunode.setup"
|
||||
|
||||
|
||||
{.pop.} # @TODO confutils.nim(775, 17) Error: can raise an unlisted exception: ref IOError
|
||||
when isMainModule:
|
||||
## Node setup happens in 6 phases:
|
||||
## 1. Set up storage
|
||||
## 2. Initialize node
|
||||
## 3. Mount and initialize configured protocols
|
||||
## 4. Start node and mounted protocols
|
||||
## 5. Start monitoring tools and external interfaces
|
||||
## 6. Setup graceful shutdown hooks
|
||||
|
||||
###################
|
||||
# Setup functions #
|
||||
###################
|
||||
|
||||
type SetupResult[T] = Result[T, string]
|
||||
|
||||
# 1/7 Setup storage
|
||||
|
||||
proc setupStorage(conf: WakuNodeConf):
|
||||
SetupResult[tuple[pStorage: WakuPeerStorage, mStorage: MessageStore]] =
|
||||
|
||||
|
@ -144,7 +130,6 @@ when isMainModule:
|
|||
|
||||
ok(storeTuple)
|
||||
|
||||
# 2/7 Retrieve dynamic bootstrap nodes
|
||||
proc retrieveDynamicBootstrapNodes(conf: WakuNodeConf): SetupResult[seq[RemotePeerInfo]] =
|
||||
|
||||
if conf.dnsDiscovery and conf.dnsDiscoveryUrl != "":
|
||||
|
@ -173,7 +158,6 @@ when isMainModule:
|
|||
debug "No method for retrieving dynamic bootstrap nodes specified."
|
||||
ok(newSeq[RemotePeerInfo]()) # Return an empty seq by default
|
||||
|
||||
# 3/7 Initialize node
|
||||
proc initNode(conf: WakuNodeConf,
|
||||
pStorage: WakuPeerStorage = nil,
|
||||
dynamicBootstrapNodes: openArray[RemotePeerInfo] = @[]): SetupResult[WakuNode] =
|
||||
|
@ -219,6 +203,8 @@ when isMainModule:
|
|||
conf.store,
|
||||
conf.relay)
|
||||
|
||||
var node: WakuNode
|
||||
try:
|
||||
node = WakuNode.new(conf.nodekey,
|
||||
conf.listenAddress, Port(uint16(conf.tcpPort) + conf.portsShift),
|
||||
extIp, extPort,
|
||||
|
@ -235,6 +221,8 @@ when isMainModule:
|
|||
dns4DomainName,
|
||||
discv5UdpPort
|
||||
)
|
||||
except:
|
||||
return err("failed to create waku node instance: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.discv5Discovery:
|
||||
let
|
||||
|
@ -271,8 +259,7 @@ when isMainModule:
|
|||
|
||||
ok(node)
|
||||
|
||||
# 4/7 Mount and initialize configured protocols
|
||||
proc setupProtocols(node: WakuNode, conf: WakuNodeConf, mStorage: MessageStore): SetupResult[bool] =
|
||||
proc setupProtocols(node: WakuNode, conf: WakuNodeConf, mStorage: MessageStore): Future[SetupResult[void]] {.async.} =
|
||||
## Setup configured protocols on an existing Waku v2 node.
|
||||
## Optionally include persistent message storage.
|
||||
## No protocols are started yet.
|
||||
|
@ -295,105 +282,163 @@ when isMainModule:
|
|||
peerExchangeHandler = some(handlePeerExchange)
|
||||
|
||||
if conf.relay:
|
||||
waitFor mountRelay(node,
|
||||
conf.topics.split(" "),
|
||||
peerExchangeHandler = peerExchangeHandler)
|
||||
try:
|
||||
let pubsubTopics = conf.topics.split(" ")
|
||||
await mountRelay(node, pubsubTopics, peerExchangeHandler = peerExchangeHandler)
|
||||
except:
|
||||
return err("failed to mount waku relay protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
|
||||
# Keepalive mounted on all nodes
|
||||
waitFor mountLibp2pPing(node)
|
||||
try:
|
||||
await mountLibp2pPing(node)
|
||||
except:
|
||||
return err("failed to mount libp2p ping protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
when defined(rln) or defined(rlnzerokit):
|
||||
if conf.rlnRelay:
|
||||
try:
|
||||
let res = node.mountRlnRelay(conf)
|
||||
if res.isErr():
|
||||
debug "could not mount WakuRlnRelay"
|
||||
return err("failed to mount waku RLN relay protocol: " & res.error)
|
||||
except:
|
||||
return err("failed to mount waku RLN relay protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.swap:
|
||||
waitFor mountSwap(node)
|
||||
# TODO Set swap peer, for now should be same as store peer
|
||||
try:
|
||||
await mountSwap(node)
|
||||
# TODO: Set swap peer, for now should be same as store peer
|
||||
except:
|
||||
return err("failed to mount waku swap protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
# Store setup
|
||||
if (conf.storenode != "") or (conf.store):
|
||||
let retentionPolicy = if conf.sqliteStore: TimeRetentionPolicy.init(conf.sqliteRetentionTime)
|
||||
else: CapacityRetentionPolicy.init(conf.storeCapacity)
|
||||
waitFor mountStore(node, mStorage, retentionPolicy=some(retentionPolicy))
|
||||
|
||||
try:
|
||||
await mountStore(node, mStorage, retentionPolicy=some(retentionPolicy))
|
||||
except:
|
||||
return err("failed to mount waku store protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
executeMessageRetentionPolicy(node)
|
||||
startMessageRetentionPolicyPeriodicTask(node, interval=MessageStoreDefaultRetentionPolicyInterval)
|
||||
|
||||
if conf.storenode != "":
|
||||
try:
|
||||
setStorePeer(node, conf.storenode)
|
||||
except:
|
||||
return err("failed to set node waku store peer: " & getCurrentExceptionMsg())
|
||||
|
||||
# NOTE Must be mounted after relay
|
||||
if (conf.lightpushnode != "") or (conf.lightpush):
|
||||
waitFor mountLightPush(node)
|
||||
try:
|
||||
await mountLightPush(node)
|
||||
except:
|
||||
return err("failed to mount waku lightpush protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.lightpushnode != "":
|
||||
try:
|
||||
setLightPushPeer(node, conf.lightpushnode)
|
||||
except:
|
||||
return err("failed to set node waku lightpush peer: " & getCurrentExceptionMsg())
|
||||
|
||||
# Filter setup. NOTE Must be mounted after relay
|
||||
if (conf.filternode != "") or (conf.filter):
|
||||
waitFor mountFilter(node, filterTimeout = chronos.seconds(conf.filterTimeout))
|
||||
try:
|
||||
await mountFilter(node, filterTimeout = chronos.seconds(conf.filterTimeout))
|
||||
except:
|
||||
return err("failed to mount waku filter protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.filternode != "":
|
||||
try:
|
||||
setFilterPeer(node, conf.filternode)
|
||||
except:
|
||||
return err("failed to set node waku filter peer: " & getCurrentExceptionMsg())
|
||||
|
||||
# waku peer exchange setup
|
||||
if (conf.peerExchangeNode != "") or (conf.peerExchange):
|
||||
waitFor mountWakuPeerExchange(node)
|
||||
try:
|
||||
await mountWakuPeerExchange(node)
|
||||
except:
|
||||
return err("failed to mount waku peer-exchange protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.peerExchangeNode != "":
|
||||
try:
|
||||
setPeerExchangePeer(node, conf.peerExchangeNode)
|
||||
except:
|
||||
return err("failed to set node waku lightpush peer: " & getCurrentExceptionMsg())
|
||||
|
||||
ok(true) # Success
|
||||
return ok()
|
||||
|
||||
# 5/7 Start node and mounted protocols
|
||||
proc startNode(node: WakuNode, conf: WakuNodeConf,
|
||||
dynamicBootstrapNodes: seq[RemotePeerInfo] = @[]): SetupResult[bool] =
|
||||
dynamicBootstrapNodes: seq[RemotePeerInfo] = @[]): Future[SetupResult[void]] {.async.} =
|
||||
## Start a configured node and all mounted protocols.
|
||||
## Resume history, connect to static nodes and start
|
||||
## keep-alive, if configured.
|
||||
|
||||
# Start Waku v2 node
|
||||
waitFor node.start()
|
||||
try:
|
||||
await node.start()
|
||||
except:
|
||||
return err("failed to start waku node: " & getCurrentExceptionMsg())
|
||||
|
||||
# Start discv5 and connect to discovered nodes
|
||||
if conf.discv5Discovery:
|
||||
if not waitFor node.startDiscv5():
|
||||
try:
|
||||
if not await node.startDiscv5():
|
||||
error "could not start Discovery v5"
|
||||
except:
|
||||
return err("failed to start waku discovery v5: " & getCurrentExceptionMsg())
|
||||
|
||||
|
||||
# Resume historical messages, this has to be called after the node has been started
|
||||
if conf.store and conf.persistMessages:
|
||||
waitFor node.resume()
|
||||
try:
|
||||
await node.resume()
|
||||
except:
|
||||
return err("failed to resume messages history: " & getCurrentExceptionMsg())
|
||||
|
||||
# Connect to configured static nodes
|
||||
if conf.staticnodes.len > 0:
|
||||
waitFor connectToNodes(node, conf.staticnodes, "static")
|
||||
try:
|
||||
await connectToNodes(node, conf.staticnodes, "static")
|
||||
except:
|
||||
return err("failed to connect to static nodes: " & getCurrentExceptionMsg())
|
||||
|
||||
if dynamicBootstrapNodes.len > 0:
|
||||
info "Connecting to dynamic bootstrap peers"
|
||||
waitFor connectToNodes(node, dynamicBootstrapNodes, "dynamic bootstrap")
|
||||
try:
|
||||
await connectToNodes(node, dynamicBootstrapNodes, "dynamic bootstrap")
|
||||
except:
|
||||
return err("failed to connect to dynamic bootstrap nodes: " & getCurrentExceptionMsg())
|
||||
|
||||
|
||||
# retrieve and connect to peer exchange peers
|
||||
if conf.peerExchangeNode != "":
|
||||
info "Retrieving peer info via peer exchange protocol"
|
||||
let desiredOutDegree = node.wakuRelay.parameters.d.uint64()
|
||||
discard waitFor node.wakuPeerExchange.request(desiredOutDegree)
|
||||
try:
|
||||
discard await node.wakuPeerExchange.request(desiredOutDegree)
|
||||
except:
|
||||
return err("failed to retrieve peer info via peer exchange protocol: " & getCurrentExceptionMsg())
|
||||
|
||||
# Start keepalive, if enabled
|
||||
if conf.keepAlive:
|
||||
node.startKeepalive()
|
||||
|
||||
ok(true) # Success
|
||||
return ok()
|
||||
|
||||
# 6/7 Start monitoring tools and external interfaces
|
||||
proc startExternal(node: WakuNode, conf: WakuNodeConf): SetupResult[bool] =
|
||||
proc startExternal(node: WakuNode, conf: WakuNodeConf): SetupResult[void] =
|
||||
## Start configured external interfaces and monitoring tools
|
||||
## on a Waku v2 node, including the RPC API, REST API and metrics
|
||||
## monitoring ports.
|
||||
|
||||
if conf.rpc:
|
||||
try:
|
||||
startRpcServer(node, conf.rpcAddress, Port(conf.rpcPort + conf.portsShift), conf)
|
||||
except:
|
||||
return err("failed to start the json-rpc server: " & getCurrentExceptionMsg())
|
||||
|
||||
if conf.rest:
|
||||
startRestServer(node, conf.restAddress, Port(conf.restPort + conf.portsShift), conf)
|
||||
|
@ -405,7 +450,18 @@ when isMainModule:
|
|||
startMetricsServer(conf.metricsServerAddress,
|
||||
Port(conf.metricsServerPort + conf.portsShift))
|
||||
|
||||
ok(true) # Success
|
||||
ok()
|
||||
|
||||
|
||||
{.pop.} # @TODO confutils.nim(775, 17) Error: can raise an unlisted exception: ref IOError
|
||||
when isMainModule:
|
||||
## Node setup happens in 6 phases:
|
||||
## 1. Set up storage
|
||||
## 2. Initialize node
|
||||
## 3. Mount and initialize configured protocols
|
||||
## 4. Start node and mounted protocols
|
||||
## 5. Start monitoring tools and external interfaces
|
||||
## 6. Setup graceful shutdown hooks
|
||||
|
||||
{.push warning[ProveInit]: off.}
|
||||
let conf = try:
|
||||
|
@ -414,8 +470,8 @@ when isMainModule:
|
|||
if conf.configFile.isSome:
|
||||
sources.addConfigFile(Toml, conf.configFile.get)
|
||||
)
|
||||
except CatchableError as err:
|
||||
error "Failure while loading the configuration: \n", err_msg=err.msg
|
||||
except CatchableError:
|
||||
error "Failure while loading the configuration: \n", error=getCurrentExceptionMsg()
|
||||
quit 1 # if we don't leave here, the initialization of conf does not work in the success case
|
||||
{.pop.}
|
||||
|
||||
|
@ -442,9 +498,8 @@ when isMainModule:
|
|||
mStorage: MessageStore
|
||||
|
||||
let setupStorageRes = setupStorage(conf)
|
||||
|
||||
if setupStorageRes.isErr:
|
||||
error "1/7 Setting up storage failed. Continuing without storage."
|
||||
if setupStorageRes.isErr():
|
||||
error "1/7 Setting up storage failed. Continuing without storage.", error=setupStorageRes.error
|
||||
else:
|
||||
(pStorage, mStorage) = setupStorageRes.get()
|
||||
|
||||
|
@ -452,41 +507,37 @@ when isMainModule:
|
|||
|
||||
var dynamicBootstrapNodes: seq[RemotePeerInfo]
|
||||
let dynamicBootstrapNodesRes = retrieveDynamicBootstrapNodes(conf)
|
||||
if dynamicBootstrapNodesRes.isErr:
|
||||
warn "2/7 Retrieving dynamic bootstrap nodes failed. Continuing without dynamic bootstrap nodes."
|
||||
if dynamicBootstrapNodesRes.isErr():
|
||||
warn "2/7 Retrieving dynamic bootstrap nodes failed. Continuing without dynamic bootstrap nodes.", error=dynamicBootstrapNodesRes.error
|
||||
else:
|
||||
dynamicBootstrapNodes = dynamicBootstrapNodesRes.get()
|
||||
|
||||
debug "3/7 Initializing node"
|
||||
|
||||
let initNodeRes = initNode(conf, pStorage, dynamicBootstrapNodes)
|
||||
|
||||
if initNodeRes.isErr:
|
||||
error "3/7 Initializing node failed. Quitting."
|
||||
if initNodeRes.isErr():
|
||||
error "3/7 Initializing node failed. Quitting.", error=initNodeRes.error
|
||||
quit(QuitFailure)
|
||||
else:
|
||||
node = initNodeRes.get()
|
||||
|
||||
debug "4/7 Mounting protocols"
|
||||
|
||||
let setupProtocolsRes = setupProtocols(node, conf, mStorage)
|
||||
|
||||
if setupProtocolsRes.isErr:
|
||||
error "4/7 Mounting protocols failed. Continuing in current state."
|
||||
let setupProtocolsRes = waitFor setupProtocols(node, conf, mStorage)
|
||||
if setupProtocolsRes.isErr():
|
||||
error "4/7 Mounting protocols failed. Continuing in current state.", error=setupProtocolsRes.error
|
||||
|
||||
debug "5/7 Starting node and mounted protocols"
|
||||
|
||||
let startNodeRes = startNode(node, conf, dynamicBootstrapNodes)
|
||||
|
||||
if startNodeRes.isErr:
|
||||
error "5/7 Starting node and mounted protocols failed. Continuing in current state."
|
||||
let startNodeRes = waitFor startNode(node, conf, dynamicBootstrapNodes)
|
||||
if startNodeRes.isErr():
|
||||
error "5/7 Starting node and mounted protocols failed. Continuing in current state.", error=startNodeRes.error
|
||||
|
||||
debug "6/7 Starting monitoring and external interfaces"
|
||||
|
||||
let startExternalRes = startExternal(node, conf)
|
||||
|
||||
if startExternalRes.isErr:
|
||||
error "6/7 Starting monitoring and external interfaces failed. Continuing in current state."
|
||||
if startExternalRes.isErr():
|
||||
error "6/7 Starting monitoring and external interfaces failed. Continuing in current state.", error=startExternalRes.error
|
||||
|
||||
debug "7/7 Setting up shutdown hooks"
|
||||
|
||||
|
@ -514,6 +565,6 @@ when isMainModule:
|
|||
|
||||
c_signal(ansi_c.SIGTERM, handleSigterm)
|
||||
|
||||
debug "Node setup complete"
|
||||
info "Node setup complete"
|
||||
|
||||
runForever()
|
||||
|
|
Loading…
Reference in New Issue