RangerMauve / hyper-sdk-rpc

JSON-RPC wrapper for hyper-sdk to enable embedding into other applications.
GNU Affero General Public License v3.0
1 stars 1 forks source link

` TypeError: Converting circular structure to JSON` #5

Closed josephmturner closed 11 months ago

josephmturner commented 11 months ago

Given the following request:

{
  jsonrpc: '2.0',
  id: 1,
  method: 'sdk.getDrive(url)',
  params: { url: 'what' }
}

I get the following error:

SYNCHRONOUS TERMINATION NOTICE: When explicitly exiting the process via process.exit or via a parent process, asynchronous tasks in your exitHooks will not run. Either remove these tasks, use gracefulExit() instead of process.exit(), or ensure your parent process sends a SIGINT to the process running this code.
file:///home/joseph/.local/src/hyper-sdk-rpc/index.js:152
    const encoded = JSON.stringify(data)
                         ^

TypeError: Converting circular structure to JSON
    --> starting at object with constructor 'Corestore'
    --- property '_root' closes the circle
    at JSON.stringify (<anonymous>)
    at ServerConnection.write (file:///home/joseph/.local/src/hyper-sdk-rpc/index.js:152:26)
    at ServerConnection.process (file:///home/joseph/.local/src/hyper-sdk-rpc/index.js:142:12)
    at process.processTicksAndRejections (node:internal/process/task_queues:95:5)
    at async Server.<anonymous> (file:///home/joseph/.local/src/hyper-sdk-rpc/bin.js:20:5)

When I add console.log inside of ServerConnection.write(), I get

{
  jsonrpc: '2.0',
  id: 1,
  result: Hyperdrive {
    _events: [Object: null prototype] {},
    _eventsCount: 0,
    _maxListeners: undefined,
    opening: Promise { undefined },
    closing: null,
    opened: true,
    closed: false,
    corestore: Corestore {
      _events: [Object: null prototype] {},
      _eventsCount: 0,
      _maxListeners: undefined,
      opening: [Promise],
      closing: null,
      opened: true,
      closed: false,
      storage: [Function (anonymous)],
      cores: [Map],
      cache: false,
      primaryKey: <Buffer 47 73 0c 06 4e 6d 3b 79 49 f8 51 0d 52 3b 93 8f 54 e5 72 9a 06 b2 73 0f c8 7b 6e 7c 96 6d 52 c6>,
      passive: false,
      _keyStorage: null,
      _bootstrap: null,
      _namespace: <Buffer c4 b3 20 12 c1 12 76 24 f5 01 99 6c ae c3 bc 1e 55 ac 60 6b d0 bb 5a 42 0a b4 f2 bb 46 24 c3 f9>,
      _root: [Corestore],
      _replicationStreams: [],
      _overwrite: false,
      _readonly: false,
      _attached: null,
      _sessions: [Set],
      _rootStoreSessions: Set(0) {},
      _locks: [Map],
      _findingPeersCount: 0,
      _findingPeers: [],
      _isCorestore: true,
      [Symbol(kCapture)]: false
    },
    db: Hyperbee {
      _events: [Object: null prototype] {},
      _eventsCount: 0,
      _maxListeners: undefined,
      opening: [Promise],
      closing: null,
      opened: true,
      closed: false,
      feed: Hypercore(
        id: eyot9cbfuj94wf71ed4pt8c8mddaf88tnx1ehoqi6u63fdcrarmo
        key: 40211fb0259a7faa17b240f4d89d8758c7829cf113e48e41d5f4fd928d84c117
        discoveryKey: df4986b5c6d2809700266dc69d2c0684be62bbc39cff5ff3b131203663988938
        opened: true
        closed: false
        snapshotted: false
        sparse: true
        writable: true
        length: 0
        fork: 0
        sessions: [ 2 ]
        activeRequests: [ 0 ]
        peers: [ 0 ]
      ),
      core: Hypercore(
        id: eyot9cbfuj94wf71ed4pt8c8mddaf88tnx1ehoqi6u63fdcrarmo
        key: 40211fb0259a7faa17b240f4d89d8758c7829cf113e48e41d5f4fd928d84c117
        discoveryKey: df4986b5c6d2809700266dc69d2c0684be62bbc39cff5ff3b131203663988938
        opened: true
        closed: false
        snapshotted: false
        sparse: true
        writable: true
        length: 0
        fork: 0
        sessions: [ 2 ]
        activeRequests: [ 0 ]
        peers: [ 0 ]
      ),
      keyEncoding: [Object],
      valueEncoding: [Object],
      extension: [HyperbeeExtension],
      metadata: [Object],
      lock: [Function],
      sep: <Buffer 00>,
      readonly: false,
      prefix: null,
      _unprefixedKeyEncoding: [Object],
      _sub: false,
      _checkout: 0,
      _view: false,
      _onappendBound: [Function: bound _onappend],
      _ontruncateBound: [Function: bound _ontruncate],
      _watchers: [],
      _entryWatchers: [],
      _batches: [],
      [Symbol(kCapture)]: false
    },
    core: Hypercore(
      id: eyot9cbfuj94wf71ed4pt8c8mddaf88tnx1ehoqi6u63fdcrarmo
      key: 40211fb0259a7faa17b240f4d89d8758c7829cf113e48e41d5f4fd928d84c117
      discoveryKey: df4986b5c6d2809700266dc69d2c0684be62bbc39cff5ff3b131203663988938
      opened: true
      closed: false
      snapshotted: false
      sparse: true
      writable: true
      length: 0
      fork: 0
      sessions: [ 2 ]
      activeRequests: [ 0 ]
      peers: [ 0 ]
    ),
    blobs: Hyperblobs {
      core: Hypercore(
        id: cwukgmjwg6s6t5jin6kssu46jp6bu1ptnbh3z8ryppbb7uypsx1o
        key: 6526a32d3437ade8ed3517956b4f5e4b7c19c9b110799b9c806b421ecc0db3e5
        discoveryKey: dba963f67e4b2d654aeeead46f2cc0a105267c5df669c9c144555e04cfab85ba
        opened: true
        closed: false
        snapshotted: false
        sparse: true
        writable: true
        length: 0
        fork: 0
        sessions: [ 2 ]
        activeRequests: [ 0 ]
        peers: [ 0 ]
      ),
      blockSize: 65536,
      _lock: [Function],
      _core: Hypercore(
        id: cwukgmjwg6s6t5jin6kssu46jp6bu1ptnbh3z8ryppbb7uypsx1o
        key: 6526a32d3437ade8ed3517956b4f5e4b7c19c9b110799b9c806b421ecc0db3e5
        discoveryKey: dba963f67e4b2d654aeeead46f2cc0a105267c5df669c9c144555e04cfab85ba
        opened: true
        closed: false
        snapshotted: false
        sparse: true
        writable: true
        length: 0
        fork: 0
        sessions: [ 2 ]
        activeRequests: [ 0 ]
        peers: [ 0 ]
      )
    },
    supportsMetadata: true,
    encryptionKey: null,
    _openingBlobs: null,
    _onwait: null,
    _batching: false,
    _checkout: null,
    [Symbol(kCapture)]: false
  }
}

It looks like the Hypercore logic works fine, but that its output isn't serialized correctly.

josephmturner commented 11 months ago

IIUC, this is a case where methods.json would come in handy, since we probably only want to allow clients to call methods and properties like sdk.getDrive(url).version, but not return the drive object itself.

RangerMauve commented 11 months ago

Yeah I think this is a wontfix since you should be acessing individual properties. :P