用工小程序前端代码
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

85 lines
2.1 KiB

6 months ago
2 months ago
6 months ago
  1. import {
  2. VOID, PRIMITIVE,
  3. ARRAY, OBJECT,
  4. DATE, REGEXP, MAP, SET,
  5. ERROR, BIGINT
  6. } from './types.js';
  7. const env = typeof self === 'object' ? self : globalThis;
  8. const deserializer = ($, _) => {
  9. const as = (out, index) => {
  10. $.set(index, out);
  11. return out;
  12. };
  13. const unpair = index => {
  14. if ($.has(index))
  15. return $.get(index);
  16. const [type, value] = _[index];
  17. switch (type) {
  18. case PRIMITIVE:
  19. case VOID:
  20. return as(value, index);
  21. case ARRAY: {
  22. const arr = as([], index);
  23. for (const index of value)
  24. arr.push(unpair(index));
  25. return arr;
  26. }
  27. case OBJECT: {
  28. const object = as({}, index);
  29. for (const [key, index] of value)
  30. object[unpair(key)] = unpair(index);
  31. return object;
  32. }
  33. case DATE:
  34. return as(new Date(value), index);
  35. case REGEXP: {
  36. const {source, flags} = value;
  37. return as(new RegExp(source, flags), index);
  38. }
  39. case MAP: {
  40. const map = as(new Map, index);
  41. for (const [key, index] of value)
  42. map.set(unpair(key), unpair(index));
  43. return map;
  44. }
  45. case SET: {
  46. const set = as(new Set, index);
  47. for (const index of value)
  48. set.add(unpair(index));
  49. return set;
  50. }
  51. case ERROR: {
  52. const {name, message} = value;
  53. return as(new env[name](message), index);
  54. }
  55. case BIGINT:
  56. return as(BigInt(value), index);
  57. case 'BigInt':
  58. return as(Object(BigInt(value)), index);
  59. case 'ArrayBuffer':
  60. return as(new Uint8Array(value).buffer, value);
  61. case 'DataView': {
  62. const { buffer } = new Uint8Array(value);
  63. return as(new DataView(buffer), value);
  64. }
  65. }
  66. return as(new env[type](value), index);
  67. };
  68. return unpair;
  69. };
  70. /**
  71. * @typedef {Array<string,any>} Record a type representation
  72. */
  73. /**
  74. * Returns a deserialized value from a serialized array of Records.
  75. * @param {Record[]} serialized a previously serialized value.
  76. * @returns {any}
  77. */
  78. export const deserialize = serialized => deserializer(new Map, serialized)(0);