Files
BridgeSwarm/spec/hrpc/index.js
T
Raven Scott bb47954b9f Implement hrpc with streaming and wire into setup
- Add spec/hyperschema and spec/hrpc codegen (scripts/build-hrpc.js)
  with unary, request/response-stream, duplex, and send-only commands
- Run build:hrpc and build:protomux from install.sh so setup is one-step
- Native host: add attachHrpc (Protomux channel + generated HRPC),
  handlers for ping, streamSum, fetchStream, duplex, notify
- Load HRPC lazily so missing spec does not crash host; use bare-stream
  for Duplex under Bare; add bare-stream, compact-encoding deps
2026-02-12 04:51:03 -05:00

198 lines
6.0 KiB
JavaScript

// This file is autogenerated by the hrpc compiler
/* eslint-disable camelcase */
/* eslint-disable space-before-function-paren */
const { c, RPC, RPCStream, RPCRequestStream } = require('hrpc/runtime')
const { getEncoding } = require('./messages.js')
const methods = new Map([
['@bridgeswarm/ping', 0],
[0, '@bridgeswarm/ping'],
['@bridgeswarm/streamSum', 1],
[1, '@bridgeswarm/streamSum'],
['@bridgeswarm/fetchStream', 2],
[2, '@bridgeswarm/fetchStream'],
['@bridgeswarm/duplex', 3],
[3, '@bridgeswarm/duplex'],
['@bridgeswarm/notify', 4],
[4, '@bridgeswarm/notify']
])
class HRPC {
constructor(stream) {
this._stream = stream
this._handlers = []
this._requestEncodings = new Map([
['@bridgeswarm/ping', getEncoding('@bridgeswarm/ping-request')],
['@bridgeswarm/streamSum', getEncoding('@bridgeswarm/stream-request-chunk')],
['@bridgeswarm/fetchStream', getEncoding('@bridgeswarm/fetch-request')],
['@bridgeswarm/duplex', getEncoding('@bridgeswarm/duplex-in')],
['@bridgeswarm/notify', getEncoding('@bridgeswarm/notify-request')]
])
this._responseEncodings = new Map([
['@bridgeswarm/ping', getEncoding('@bridgeswarm/ping-response')],
['@bridgeswarm/streamSum', getEncoding('@bridgeswarm/stream-sum-response')],
['@bridgeswarm/fetchStream', getEncoding('@bridgeswarm/fetch-chunk')],
['@bridgeswarm/duplex', getEncoding('@bridgeswarm/duplex-out')]
])
this._rpc = new RPC(stream, async (req) => {
const command = methods.get(req.command)
const responseEncoding = this._responseEncodings.get(command)
const requestEncoding = this._requestEncodings.get(command)
if (this._requestIsSend(command)) {
const request = req.data ? c.decode(requestEncoding, req.data) : null
await this._handlers[command](request)
return
}
if (!this._requestIsStream(command) && !this._responseIsStream(command)) {
const request = req.data ? c.decode(requestEncoding, req.data) : null
const response = await this._handlers[command](request)
req.reply(c.encode(responseEncoding, response))
}
if (!this._requestIsStream(command) && this._responseIsStream(command)) {
const request = req.data ? c.decode(requestEncoding, req.data) : null
const responseStream = new RPCStream(
null,
null,
req.createResponseStream(),
responseEncoding
)
responseStream.data = request
await this._handlers[command](responseStream)
}
if (this._requestIsStream(command) && !this._responseIsStream(command)) {
const requestStream = new RPCRequestStream(
req,
responseEncoding,
req.createRequestStream(),
requestEncoding
)
const response = await this._handlers[command](requestStream)
req.reply(c.encode(responseEncoding, response))
}
if (this._requestIsStream(command) && this._responseIsStream(command)) {
const requestStream = new RPCRequestStream(
req,
responseEncoding,
req.createRequestStream(),
requestEncoding,
req.createResponseStream(),
responseEncoding
)
await this._handlers[command](requestStream)
}
})
}
async _call(name, args) {
const requestEncoding = this._requestEncodings.get(name)
const responseEncoding = this._responseEncodings.get(name)
const request = this._rpc.request(methods.get(name))
const encoded = c.encode(requestEncoding, args)
request.send(encoded)
return c.decode(responseEncoding, await request.reply())
}
_callSync(name, args) {
const requestEncoding = this._requestEncodings.get(name)
const responseEncoding = this._responseEncodings.get(name)
if (this._requestIsSend(name)) {
const encoded = c.encode(requestEncoding, args)
const request = this._rpc.event(methods.get(name))
request.send(encoded)
}
const request = this._rpc.request(methods.get(name))
if (!this._requestIsStream(name) && this._responseIsStream(name)) {
const encoded = c.encode(requestEncoding, args)
request.send(encoded)
return new RPCStream(request.createResponseStream(), responseEncoding)
}
if (this._requestIsStream(name) && !this._responseIsStream(name)) {
return new RPCRequestStream(
request,
responseEncoding,
null,
null,
request.createRequestStream(),
requestEncoding
)
}
if (this._requestIsStream(name) && this._responseIsStream(name)) {
return new RPCRequestStream(
request,
responseEncoding,
request.createResponseStream(),
responseEncoding,
request.createRequestStream(),
requestEncoding
)
}
}
async ping(args) {
return this._call('@bridgeswarm/ping', args)
}
streamSum(args) {
return this._callSync('@bridgeswarm/streamSum', args)
}
fetchStream(args) {
return this._callSync('@bridgeswarm/fetchStream', args)
}
duplex(args) {
return this._callSync('@bridgeswarm/duplex', args)
}
notify(args) {
return this._callSync('@bridgeswarm/notify', args)
}
onPing(responseFn) {
this._handlers['@bridgeswarm/ping'] = responseFn
}
onStreamSum(responseFn) {
this._handlers['@bridgeswarm/streamSum'] = responseFn
}
onFetchStream(responseFn) {
this._handlers['@bridgeswarm/fetchStream'] = responseFn
}
onDuplex(responseFn) {
this._handlers['@bridgeswarm/duplex'] = responseFn
}
onNotify(responseFn) {
this._handlers['@bridgeswarm/notify'] = responseFn
}
_requestIsStream(command) {
return [
'@bridgeswarm/streamSum',
'@bridgeswarm/duplex'
].includes(command)
}
_responseIsStream(command) {
return [
'@bridgeswarm/fetchStream',
'@bridgeswarm/duplex'
].includes(command)
}
// prettier-ignore-start
_requestIsSend(command) {
return [
// prettier-ignore
'@bridgeswarm/notify'
].includes(command)
}
}
module.exports = HRPC