mirror of
https://github.com/varun-r-mallya/py-libp2p.git
synced 2025-12-31 20:36:24 +00:00
109 lines
2.6 KiB
Nim
109 lines
2.6 KiB
Nim
{.used.}
|
|
|
|
import chronos
|
|
import stew/byteutils
|
|
import libp2p
|
|
|
|
##
|
|
# Simple Echo Protocol Implementation for py-libp2p Interop Testing
|
|
##
|
|
const EchoCodec = "/echo/1.0.0"
|
|
|
|
type EchoProto = ref object of LPProtocol
|
|
|
|
proc new(T: typedesc[EchoProto]): T =
|
|
proc handle(conn: Connection, proto: string) {.async: (raises: [CancelledError]).} =
|
|
try:
|
|
echo "Echo server: Received connection from ", conn.peerId
|
|
|
|
# Read and echo messages in a loop
|
|
while not conn.atEof:
|
|
try:
|
|
# Read length-prefixed message using nim-libp2p's readLp
|
|
let message = await conn.readLp(1024 * 1024) # Max 1MB
|
|
if message.len == 0:
|
|
echo "Echo server: Empty message, closing connection"
|
|
break
|
|
|
|
let messageStr = string.fromBytes(message)
|
|
echo "Echo server: Received (", message.len, " bytes): ", messageStr
|
|
|
|
# Echo back using writeLp
|
|
await conn.writeLp(message)
|
|
echo "Echo server: Echoed message back"
|
|
|
|
except CatchableError as e:
|
|
echo "Echo server: Error processing message: ", e.msg
|
|
break
|
|
|
|
except CancelledError as e:
|
|
echo "Echo server: Connection cancelled"
|
|
raise e
|
|
except CatchableError as e:
|
|
echo "Echo server: Exception in handler: ", e.msg
|
|
finally:
|
|
echo "Echo server: Connection closed"
|
|
await conn.close()
|
|
|
|
return T.new(codecs = @[EchoCodec], handler = handle)
|
|
|
|
##
|
|
# Create QUIC-enabled switch
|
|
##
|
|
proc createSwitch(ma: MultiAddress, rng: ref HmacDrbgContext): Switch =
|
|
var switch = SwitchBuilder
|
|
.new()
|
|
.withRng(rng)
|
|
.withAddress(ma)
|
|
.withQuicTransport()
|
|
.build()
|
|
result = switch
|
|
|
|
##
|
|
# Main server
|
|
##
|
|
proc main() {.async.} =
|
|
let
|
|
rng = newRng()
|
|
localAddr = MultiAddress.init("/ip4/0.0.0.0/udp/0/quic-v1").tryGet()
|
|
echoProto = EchoProto.new()
|
|
|
|
echo "=== Nim Echo Server for py-libp2p Interop ==="
|
|
|
|
# Create switch
|
|
let switch = createSwitch(localAddr, rng)
|
|
switch.mount(echoProto)
|
|
|
|
# Start server
|
|
await switch.start()
|
|
|
|
# Print connection info
|
|
echo "Peer ID: ", $switch.peerInfo.peerId
|
|
echo "Listening on:"
|
|
for addr in switch.peerInfo.addrs:
|
|
echo " ", $addr, "/p2p/", $switch.peerInfo.peerId
|
|
echo "Protocol: ", EchoCodec
|
|
echo "Ready for py-libp2p connections!"
|
|
echo ""
|
|
|
|
# Keep running
|
|
try:
|
|
await sleepAsync(100.hours)
|
|
except CancelledError:
|
|
echo "Shutting down..."
|
|
finally:
|
|
await switch.stop()
|
|
|
|
# Graceful shutdown handler
|
|
proc signalHandler() {.noconv.} =
|
|
echo "\nShutdown signal received"
|
|
quit(0)
|
|
|
|
when isMainModule:
|
|
setControlCHook(signalHandler)
|
|
try:
|
|
waitFor(main())
|
|
except CatchableError as e:
|
|
echo "Error: ", e.msg
|
|
quit(1)
|