code: function metaToValue (meta) {
    const types = {
      value: () => meta.value,
      array: () => meta.members.map((member) => metaToValue(member)),
      buffer: () => bufferUtils.metaToBuffer(meta.value),
      promise: () => resolvePromise({ then: metaToValue(meta.then) }),
      error: () => metaToPlainObject(meta),
      date: () => new Date(meta.value),
      exception: () => { throw errorUtils.deserialize(meta.value) }
    }
  
    if (meta.type in types) {
      return types[meta.type]()
    } else {
      let ret
      if (remoteObjectCache.has(meta.id)) {
        v8Util.addRemoteObjectRef(contextId, meta.id)
        return remoteObjectCache.get(meta.id)
      }
  
      // A shadow class to represent the remote function object.
      if (meta.type === 'function') {
        const remoteFunction = function (...args) {
          let command
          if (this && this.constructor === remoteFunction) {
            command = 'ELECTRON_BROWSER_CONSTRUCTOR'
          } else {
            command = 'ELECTRON_BROWSER_FUNCTION_CALL'
          }
          const obj = ipcRendererInternal.sendSync(command, contextId, meta.id, wrapArgs(args))
          return metaToValue(obj)
        }
        ret = remoteFunction
      } else {
        ret = {}
      }
  
      setObjectMembers(ret, ret, meta.id, meta.members)
      setObjectPrototype(ret, ret, meta.id, meta.proto)
      Object.defineProperty(ret.constructor, 'name', { value: meta.name })
  
      // Track delegate obj's lifetime & tell browser to clean up when object is GCed.
      v8Util.setRemoteObjectFreer(ret, contextId, meta.id)
      v8Util.setHiddenValue(ret, 'atomId', meta.id)
      v8Util.addRemoteObjectRef(contextId, meta.id)
      remoteObjectCache.set(meta.id, ret)
      return ret
    }
  }
docs: Convert meta data from browser into real value.