Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Annotate containers with their common types #38

Open
Skn0tt opened this issue Aug 2, 2020 · 2 comments
Open

Annotate containers with their common types #38

Skn0tt opened this issue Aug 2, 2020 · 2 comments

Comments

@Skn0tt
Copy link
Collaborator

Skn0tt commented Aug 2, 2020

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)

@aem
Copy link

aem commented Aug 2, 2020

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.

@Skn0tt
Copy link
Collaborator Author

Skn0tt commented Aug 3, 2020

Good idea! This is one of the ideas proposed in #11.
Out of curiosity, what's the advantage of switch (0) { case fieldType ^ StringType: ... } over switch (fieldType) { case StringType: ... } in your code snippet?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants