superjson icon indicating copy to clipboard operation
superjson copied to clipboard

Annotate containers with their common types

Open Skn0tt opened this issue 5 years ago • 2 comments

When serialising a list of Dates, our meta will grow very large:

SuperJSON.serialize({
  timestamps: [ new Date(), new Date(), new RegExp(), new Date() ]
})

// yields

{
  json: ...
  meta: {
    values: { "timestamps.0": "Date", "timestamps.1": "Date", "timestamps.2": "RegExp", "timestamps.3": "Date" }
  }
}

We could save some space by serialising to the following instead:

{
  json: ...
  meta: {
    values: { "timestamps": ["array", "Date"], "timestamps.2": "RegExp" }
  }
}

(Date is chosen because it occurs most in timestamps)

Skn0tt avatar Aug 02 '20 13:08 Skn0tt

Could we use predefined numeric constants + bit comparisons to represent the types? It'll make the meta a little less human readable, but we'll save bytes in both the library and the transported JSON. We could even compile away the constants during our build which would compress the bundled code size further.

const StringType = 1;
const DateType = 2;
const ArrayType = 3;

// in untransform
switch(0) {
  case fieldType ^ StringType:
    return String(fieldValue);
  case fieldType ^ DateType:
    return Date(fieldValue);
  case filedType ^ ArrayType:
    return toArray(fieldValue);
  // ...
}

The compiled code will look something like this (whitespace notwithstanding):

switch(0) {
  case f^0: return String(v);
  case f^1: return Date(v);
  case f^2: return toArray(v);
  // ...

And the resulting meta:

{
  meta: {
    values: { "timestamps.0": 2, "timestamps.1": 2, "timestamps.2": 5, "timestamps.3": 2 }
  }
}

Still replicated field names, but solves the duplication of field types.

aem avatar Aug 02 '20 15:08 aem

Good idea! This is one of the ideas proposed in https://github.com/blitz-js/superjson/issues/11. Out of curiosity, what's the advantage of switch (0) { case fieldType ^ StringType: ... } over switch (fieldType) { case StringType: ... } in your code snippet?

Skn0tt avatar Aug 03 '20 07:08 Skn0tt