_asyncOptionalChain.js 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859
  1. /**
  2. * Polyfill for the optional chain operator, `?.`, given previous conversion of the expression into an array of values,
  3. * descriptors, and functions, for situations in which at least one part of the expression is async.
  4. *
  5. * Adapted from Sucrase (https://github.com/alangpierce/sucrase) See
  6. * https://github.com/alangpierce/sucrase/blob/265887868966917f3b924ce38dfad01fbab1329f/src/transformers/OptionalChainingNullishTransformer.ts#L15
  7. *
  8. * @param ops Array result of expression conversion
  9. * @returns The value of the expression
  10. */
  11. async function _asyncOptionalChain(ops) {
  12. let lastAccessLHS = undefined;
  13. let value = ops[0];
  14. let i = 1;
  15. while (i < ops.length) {
  16. const op = ops[i] ;
  17. const fn = ops[i + 1] ;
  18. i += 2;
  19. // by checking for loose equality to `null`, we catch both `null` and `undefined`
  20. if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) {
  21. // really we're meaning to return `undefined` as an actual value here, but it saves bytes not to write it
  22. return;
  23. }
  24. if (op === 'access' || op === 'optionalAccess') {
  25. lastAccessLHS = value;
  26. value = await fn(value);
  27. } else if (op === 'call' || op === 'optionalCall') {
  28. value = await fn((...args) => (value ).call(lastAccessLHS, ...args));
  29. lastAccessLHS = undefined;
  30. }
  31. }
  32. return value;
  33. }
  34. // Sucrase version:
  35. // async function _asyncOptionalChain(ops) {
  36. // let lastAccessLHS = undefined;
  37. // let value = ops[0];
  38. // let i = 1;
  39. // while (i < ops.length) {
  40. // const op = ops[i];
  41. // const fn = ops[i + 1];
  42. // i += 2;
  43. // if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) {
  44. // return undefined;
  45. // }
  46. // if (op === 'access' || op === 'optionalAccess') {
  47. // lastAccessLHS = value;
  48. // value = await fn(value);
  49. // } else if (op === 'call' || op === 'optionalCall') {
  50. // value = await fn((...args) => value.call(lastAccessLHS, ...args));
  51. // lastAccessLHS = undefined;
  52. // }
  53. // }
  54. // return value;
  55. // }
  56. export { _asyncOptionalChain };
  57. //# sourceMappingURL=_asyncOptionalChain.js.map