Does extension messaging like chrome.runtime.sendMessage internally use JSON.stringify?

In Chrome the messages are automatically JSON-serialized (literally using JSON.stringify) in Chrome’s JavaScript shim layer that interacts with an extension as can be seen in the source code of messaging.js.

The same applies to chrome.runtime.sendMessage and chrome.tabs.sendMessage which use Port-based messaging internally.

It means that only JSON-compatible portion of the object is passed: strings, numbers, booleans, null, and objects/arrays that consist of the listed types. Complex types are not supported and will be sent as an empty object {} e.g. DOM elements, Set, Map, class instances, functions, and so on.

To send an unsupported type, serialize/stringify it manually, for example if map = new Map():

  • {data: [...map]} when sending
  • new Map(request.data) when receiving

Hopefully, Chrome will be able to send more types directly one day, see https://crbug.com/248548.

In Firefox, the structured clone algorithm is used, which preserves many popular complex types like Date, RegExp, Blob, File, ArrayBuffer, Map, Set, and several others.

Leave a Comment