cst-stringify.js 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
  1. 'use strict';
  2. /**
  3. * Stringify a CST document, token, or collection item
  4. *
  5. * Fair warning: This applies no validation whatsoever, and
  6. * simply concatenates the sources in their logical order.
  7. */
  8. const stringify = (cst) => 'type' in cst ? stringifyToken(cst) : stringifyItem(cst);
  9. function stringifyToken(token) {
  10. switch (token.type) {
  11. case 'block-scalar': {
  12. let res = '';
  13. for (const tok of token.props)
  14. res += stringifyToken(tok);
  15. return res + token.source;
  16. }
  17. case 'block-map':
  18. case 'block-seq': {
  19. let res = '';
  20. for (const item of token.items)
  21. res += stringifyItem(item);
  22. return res;
  23. }
  24. case 'flow-collection': {
  25. let res = token.start.source;
  26. for (const item of token.items)
  27. res += stringifyItem(item);
  28. for (const st of token.end)
  29. res += st.source;
  30. return res;
  31. }
  32. case 'document': {
  33. let res = stringifyItem(token);
  34. if (token.end)
  35. for (const st of token.end)
  36. res += st.source;
  37. return res;
  38. }
  39. default: {
  40. let res = token.source;
  41. if ('end' in token && token.end)
  42. for (const st of token.end)
  43. res += st.source;
  44. return res;
  45. }
  46. }
  47. }
  48. function stringifyItem({ start, key, sep, value }) {
  49. let res = '';
  50. for (const st of start)
  51. res += st.source;
  52. if (key)
  53. res += stringifyToken(key);
  54. if (sep)
  55. for (const st of sep)
  56. res += st.source;
  57. if (value)
  58. res += stringifyToken(value);
  59. return res;
  60. }
  61. exports.stringify = stringify;