@borgar/fx 4.13.0 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (141) hide show
  1. package/dist/index-BMr6cTgc.d.cts +1444 -0
  2. package/dist/index-BMr6cTgc.d.ts +1444 -0
  3. package/dist/index.cjs +3054 -0
  4. package/dist/index.cjs.map +1 -0
  5. package/dist/index.d.cts +1 -0
  6. package/dist/index.d.ts +1 -0
  7. package/dist/index.js +2984 -0
  8. package/dist/index.js.map +1 -0
  9. package/dist/xlsx/index.cjs +3120 -0
  10. package/dist/xlsx/index.cjs.map +1 -0
  11. package/dist/xlsx/index.d.cts +55 -0
  12. package/dist/xlsx/index.d.ts +55 -0
  13. package/dist/xlsx/index.js +3049 -0
  14. package/dist/xlsx/index.js.map +1 -0
  15. package/docs/API.md +2959 -718
  16. package/docs/AST_format.md +2 -2
  17. package/eslint.config.mjs +40 -0
  18. package/lib/a1.spec.ts +32 -0
  19. package/lib/a1.ts +26 -0
  20. package/lib/addA1RangeBounds.ts +50 -0
  21. package/lib/addTokenMeta.spec.ts +166 -0
  22. package/lib/{addTokenMeta.js → addTokenMeta.ts} +53 -33
  23. package/lib/astTypes.ts +211 -0
  24. package/lib/cloneToken.ts +29 -0
  25. package/lib/{constants.js → constants.ts} +6 -3
  26. package/lib/fixRanges.spec.ts +220 -0
  27. package/lib/fixRanges.ts +260 -0
  28. package/lib/fromCol.spec.ts +15 -0
  29. package/lib/{fromCol.js → fromCol.ts} +1 -1
  30. package/lib/index.spec.ts +119 -0
  31. package/lib/index.ts +76 -0
  32. package/lib/isNodeType.ts +151 -0
  33. package/lib/isType.spec.ts +208 -0
  34. package/lib/{isType.js → isType.ts} +26 -25
  35. package/lib/lexers/{advRangeOp.js → advRangeOp.ts} +1 -1
  36. package/lib/lexers/{canEndRange.js → canEndRange.ts} +2 -2
  37. package/lib/lexers/{lexBoolean.js → lexBoolean.ts} +25 -6
  38. package/lib/lexers/{lexContext.js → lexContext.ts} +14 -6
  39. package/lib/lexers/{lexError.js → lexError.ts} +3 -3
  40. package/lib/lexers/{lexFunction.js → lexFunction.ts} +3 -2
  41. package/lib/lexers/lexNameFuncCntx.ts +112 -0
  42. package/lib/lexers/{lexNamed.js → lexNamed.ts} +4 -4
  43. package/lib/lexers/{lexNewLine.js → lexNewLine.ts} +3 -2
  44. package/lib/lexers/{lexNumber.js → lexNumber.ts} +4 -3
  45. package/lib/lexers/{lexOperator.js → lexOperator.ts} +5 -4
  46. package/lib/lexers/lexRange.ts +15 -0
  47. package/lib/lexers/{lexRangeA1.js → lexRangeA1.ts} +11 -7
  48. package/lib/lexers/{lexRangeR1C1.js → lexRangeR1C1.ts} +10 -6
  49. package/lib/lexers/{lexRangeTrim.js → lexRangeTrim.ts} +3 -2
  50. package/lib/lexers/{lexRefOp.js → lexRefOp.ts} +4 -3
  51. package/lib/lexers/{lexString.js → lexString.ts} +3 -3
  52. package/lib/lexers/{lexStructured.js → lexStructured.ts} +5 -5
  53. package/lib/lexers/{lexWhitespace.js → lexWhitespace.ts} +3 -2
  54. package/lib/lexers/sets.ts +51 -0
  55. package/lib/mergeRefTokens.spec.ts +141 -0
  56. package/lib/{mergeRefTokens.js → mergeRefTokens.ts} +14 -9
  57. package/lib/nodeTypes.ts +54 -0
  58. package/lib/parse.spec.ts +1410 -0
  59. package/lib/{parser.js → parse.ts} +81 -63
  60. package/lib/parseA1Range.spec.ts +233 -0
  61. package/lib/parseA1Range.ts +206 -0
  62. package/lib/parseA1Ref.spec.ts +337 -0
  63. package/lib/parseA1Ref.ts +115 -0
  64. package/lib/parseR1C1Range.ts +191 -0
  65. package/lib/parseR1C1Ref.spec.ts +323 -0
  66. package/lib/parseR1C1Ref.ts +127 -0
  67. package/lib/parseRef.spec.ts +90 -0
  68. package/lib/parseRef.ts +240 -0
  69. package/lib/{parseSRange.js → parseSRange.ts} +15 -10
  70. package/lib/parseStructRef.spec.ts +168 -0
  71. package/lib/parseStructRef.ts +76 -0
  72. package/lib/stringifyA1Range.spec.ts +72 -0
  73. package/lib/stringifyA1Range.ts +72 -0
  74. package/lib/stringifyA1Ref.spec.ts +64 -0
  75. package/lib/stringifyA1Ref.ts +59 -0
  76. package/lib/{stringifyPrefix.js → stringifyPrefix.ts} +17 -2
  77. package/lib/stringifyR1C1Range.spec.ts +92 -0
  78. package/lib/stringifyR1C1Range.ts +73 -0
  79. package/lib/stringifyR1C1Ref.spec.ts +63 -0
  80. package/lib/stringifyR1C1Ref.ts +67 -0
  81. package/lib/stringifyStructRef.spec.ts +124 -0
  82. package/lib/stringifyStructRef.ts +113 -0
  83. package/lib/stringifyTokens.ts +15 -0
  84. package/lib/toCol.spec.ts +11 -0
  85. package/lib/{toCol.js → toCol.ts} +4 -4
  86. package/lib/tokenTypes.ts +76 -0
  87. package/lib/tokenize-srefs.spec.ts +429 -0
  88. package/lib/tokenize.spec.ts +2103 -0
  89. package/lib/tokenize.ts +346 -0
  90. package/lib/translate.spec.ts +35 -0
  91. package/lib/translateToA1.spec.ts +247 -0
  92. package/lib/translateToA1.ts +231 -0
  93. package/lib/translateToR1C1.spec.ts +227 -0
  94. package/lib/translateToR1C1.ts +145 -0
  95. package/lib/types.ts +179 -0
  96. package/lib/xlsx/index.spec.ts +27 -0
  97. package/lib/xlsx/index.ts +32 -0
  98. package/package.json +45 -31
  99. package/tsconfig.json +28 -0
  100. package/typedoc-ignore-links.ts +17 -0
  101. package/typedoc.json +41 -0
  102. package/.eslintrc +0 -22
  103. package/benchmark/benchmark.js +0 -48
  104. package/benchmark/formulas.json +0 -15677
  105. package/dist/fx.d.ts +0 -823
  106. package/dist/fx.js +0 -2
  107. package/dist/package.json +0 -1
  108. package/lib/a1.js +0 -348
  109. package/lib/a1.spec.js +0 -458
  110. package/lib/addTokenMeta.spec.js +0 -153
  111. package/lib/astTypes.js +0 -96
  112. package/lib/extraTypes.js +0 -74
  113. package/lib/fixRanges.js +0 -104
  114. package/lib/fixRanges.spec.js +0 -171
  115. package/lib/fromCol.spec.js +0 -11
  116. package/lib/index.js +0 -134
  117. package/lib/index.spec.js +0 -67
  118. package/lib/isType.spec.js +0 -168
  119. package/lib/lexer-srefs.spec.js +0 -324
  120. package/lib/lexer.js +0 -264
  121. package/lib/lexer.spec.js +0 -1953
  122. package/lib/lexers/lexRange.js +0 -8
  123. package/lib/lexers/sets.js +0 -38
  124. package/lib/mergeRefTokens.spec.js +0 -121
  125. package/lib/package.json +0 -1
  126. package/lib/parseRef.js +0 -157
  127. package/lib/parseRef.spec.js +0 -71
  128. package/lib/parseStructRef.js +0 -48
  129. package/lib/parseStructRef.spec.js +0 -164
  130. package/lib/parser.spec.js +0 -1208
  131. package/lib/rc.js +0 -341
  132. package/lib/rc.spec.js +0 -403
  133. package/lib/stringifyStructRef.js +0 -80
  134. package/lib/stringifyStructRef.spec.js +0 -182
  135. package/lib/toCol.spec.js +0 -11
  136. package/lib/translate-toA1.spec.js +0 -214
  137. package/lib/translate-toRC.spec.js +0 -197
  138. package/lib/translate.js +0 -239
  139. package/lib/translate.spec.js +0 -21
  140. package/rollup.config.mjs +0 -22
  141. package/tsd.json +0 -12
@@ -1,168 +0,0 @@
1
- import { test } from 'tape';
2
- import {
3
- REF_RANGE, REF_BEAM, REF_NAMED, REF_TERNARY, REF_STRUCT,
4
- FX_PREFIX, WHITESPACE, NEWLINE,
5
- FUNCTION, OPERATOR,
6
- ERROR, STRING, NUMBER, BOOLEAN
7
- } from './constants.js';
8
- import { isRange, isReference, isLiteral, isError, isWhitespace, isFunction, isFxPrefix, isOperator } from './isType.js';
9
-
10
- test('isRange', t => {
11
- t.is(isRange(null), false, 'null is not a range');
12
- t.is(isRange({}), false, 'plain object is not a range');
13
- t.is(isRange({ type: BOOLEAN }), false, 'BOOLEAN is not a range');
14
- t.is(isRange({ type: ERROR }), false, 'ERROR is not a range');
15
- t.is(isRange({ type: FUNCTION }), false, 'FUNCTION is not a range');
16
- t.is(isRange({ type: FX_PREFIX }), false, 'FX_PREFIX is not a range');
17
- t.is(isRange({ type: NEWLINE }), false, 'NEWLINE is not a range');
18
- t.is(isRange({ type: NUMBER }), false, 'NUMBER is not a range');
19
- t.is(isRange({ type: OPERATOR }), false, 'OPERATOR is not a range');
20
- t.is(isRange({ type: REF_BEAM }), true, 'REF_BEAM is a range');
21
- t.is(isRange({ type: REF_NAMED }), false, 'REF_NAMED is not a range');
22
- t.is(isRange({ type: REF_RANGE }), true, 'REF_RANGE is a range');
23
- t.is(isRange({ type: REF_STRUCT }), false, 'REF_STRUCT is not a range');
24
- t.is(isRange({ type: REF_TERNARY }), true, 'REF_TERNARY is a range');
25
- t.is(isRange({ type: STRING }), false, 'STRING is not a range');
26
- t.is(isRange({ type: WHITESPACE }), false, 'WHITESPACE is not a range');
27
- t.end();
28
- });
29
-
30
- test('isReference', t => {
31
- t.is(isReference(null), false, 'null is not a reference');
32
- t.is(isReference({}), false, 'plain object is not a reference');
33
- t.is(isReference({ type: BOOLEAN }), false, 'BOOLEAN is not a reference');
34
- t.is(isReference({ type: ERROR }), false, 'ERROR is not a reference');
35
- t.is(isReference({ type: FUNCTION }), false, 'FUNCTION is not a reference');
36
- t.is(isReference({ type: FX_PREFIX }), false, 'FX_PREFIX is not a reference');
37
- t.is(isReference({ type: NEWLINE }), false, 'NEWLINE is not a reference');
38
- t.is(isReference({ type: NUMBER }), false, 'NUMBER is not a reference');
39
- t.is(isReference({ type: OPERATOR }), false, 'OPERATOR is not a reference');
40
- t.is(isReference({ type: REF_BEAM }), true, 'REF_BEAM is a reference');
41
- t.is(isReference({ type: REF_NAMED }), true, 'REF_NAMED is not a reference');
42
- t.is(isReference({ type: REF_RANGE }), true, 'REF_RANGE is a reference');
43
- t.is(isReference({ type: REF_STRUCT }), true, 'REF_STRUCT is not a reference');
44
- t.is(isReference({ type: REF_TERNARY }), true, 'REF_TERNARY is a reference');
45
- t.is(isReference({ type: STRING }), false, 'STRING is not a reference');
46
- t.is(isReference({ type: WHITESPACE }), false, 'WHITESPACE is not a reference');
47
- t.end();
48
- });
49
-
50
- test('isLiteral', t => {
51
- t.is(isLiteral(null), false, 'null is not a literal');
52
- t.is(isLiteral({}), false, 'plain object is not a literal');
53
- t.is(isLiteral({ type: BOOLEAN }), true, 'BOOLEAN is not a literal');
54
- t.is(isLiteral({ type: ERROR }), true, 'ERROR is not a literal');
55
- t.is(isLiteral({ type: FUNCTION }), false, 'FUNCTION is not a literal');
56
- t.is(isLiteral({ type: FX_PREFIX }), false, 'FX_PREFIX is not a literal');
57
- t.is(isLiteral({ type: NEWLINE }), false, 'NEWLINE is not a literal');
58
- t.is(isLiteral({ type: NUMBER }), true, 'NUMBER is not a literal');
59
- t.is(isLiteral({ type: OPERATOR }), false, 'OPERATOR is not a literal');
60
- t.is(isLiteral({ type: REF_BEAM }), false, 'REF_BEAM is a literal');
61
- t.is(isLiteral({ type: REF_NAMED }), false, 'REF_NAMED is not a literal');
62
- t.is(isLiteral({ type: REF_RANGE }), false, 'REF_RANGE is a literal');
63
- t.is(isLiteral({ type: REF_STRUCT }), false, 'REF_STRUCT is not a literal');
64
- t.is(isLiteral({ type: REF_TERNARY }), false, 'REF_TERNARY is a literal');
65
- t.is(isLiteral({ type: STRING }), true, 'STRING is not a literal');
66
- t.is(isLiteral({ type: WHITESPACE }), false, 'WHITESPACE is not a literal');
67
- t.end();
68
- });
69
-
70
- test('isError', t => {
71
- t.is(isError(null), false, 'null is not an error');
72
- t.is(isError({}), false, 'plain object is not an error');
73
- t.is(isError({ type: BOOLEAN }), false, 'BOOLEAN is not an error');
74
- t.is(isError({ type: ERROR }), true, 'ERROR is not an error');
75
- t.is(isError({ type: FUNCTION }), false, 'FUNCTION is not an error');
76
- t.is(isError({ type: FX_PREFIX }), false, 'FX_PREFIX is not an error');
77
- t.is(isError({ type: NEWLINE }), false, 'NEWLINE is not an error');
78
- t.is(isError({ type: NUMBER }), false, 'NUMBER is not an error');
79
- t.is(isError({ type: OPERATOR }), false, 'OPERATOR is not an error');
80
- t.is(isError({ type: REF_BEAM }), false, 'REF_BEAM is an error');
81
- t.is(isError({ type: REF_NAMED }), false, 'REF_NAMED is not an error');
82
- t.is(isError({ type: REF_RANGE }), false, 'REF_RANGE is an error');
83
- t.is(isError({ type: REF_STRUCT }), false, 'REF_STRUCT is not an error');
84
- t.is(isError({ type: REF_TERNARY }), false, 'REF_TERNARY is an error');
85
- t.is(isError({ type: STRING }), false, 'STRING is not an error');
86
- t.is(isError({ type: WHITESPACE }), false, 'WHITESPACE is not an error');
87
- t.end();
88
- });
89
-
90
- test('isWhitespace', t => {
91
- t.is(isWhitespace(null), false, 'null is not a whitespace');
92
- t.is(isWhitespace({}), false, 'plain object is not a whitespace');
93
- t.is(isWhitespace({ type: BOOLEAN }), false, 'BOOLEAN is not a whitespace');
94
- t.is(isWhitespace({ type: ERROR }), false, 'ERROR is not a whitespace');
95
- t.is(isWhitespace({ type: FUNCTION }), false, 'FUNCTION is not a whitespace');
96
- t.is(isWhitespace({ type: FX_PREFIX }), false, 'FX_PREFIX is not a whitespace');
97
- t.is(isWhitespace({ type: NEWLINE }), true, 'NEWLINE is not a whitespace');
98
- t.is(isWhitespace({ type: NUMBER }), false, 'NUMBER is not a whitespace');
99
- t.is(isWhitespace({ type: OPERATOR }), false, 'OPERATOR is not a whitespace');
100
- t.is(isWhitespace({ type: REF_BEAM }), false, 'REF_BEAM is a whitespace');
101
- t.is(isWhitespace({ type: REF_NAMED }), false, 'REF_NAMED is not a whitespace');
102
- t.is(isWhitespace({ type: REF_RANGE }), false, 'REF_RANGE is a whitespace');
103
- t.is(isWhitespace({ type: REF_STRUCT }), false, 'REF_STRUCT is not a whitespace');
104
- t.is(isWhitespace({ type: REF_TERNARY }), false, 'REF_TERNARY is a whitespace');
105
- t.is(isWhitespace({ type: STRING }), false, 'STRING is not a whitespace');
106
- t.is(isWhitespace({ type: WHITESPACE }), true, 'WHITESPACE is not a whitespace');
107
- t.end();
108
- });
109
-
110
- test('isFunction', t => {
111
- t.is(isFunction(null), false, 'null is not a function');
112
- t.is(isFunction({}), false, 'plain object is not a function');
113
- t.is(isFunction({ type: BOOLEAN }), false, 'BOOLEAN is not a function');
114
- t.is(isFunction({ type: ERROR }), false, 'ERROR is not a function');
115
- t.is(isFunction({ type: FUNCTION }), true, 'FUNCTION is not a function');
116
- t.is(isFunction({ type: FX_PREFIX }), false, 'FX_PREFIX is not a function');
117
- t.is(isFunction({ type: NEWLINE }), false, 'NEWLINE is not a function');
118
- t.is(isFunction({ type: NUMBER }), false, 'NUMBER is not a function');
119
- t.is(isFunction({ type: OPERATOR }), false, 'OPERATOR is not a function');
120
- t.is(isFunction({ type: REF_BEAM }), false, 'REF_BEAM is a function');
121
- t.is(isFunction({ type: REF_NAMED }), false, 'REF_NAMED is not a function');
122
- t.is(isFunction({ type: REF_RANGE }), false, 'REF_RANGE is a function');
123
- t.is(isFunction({ type: REF_STRUCT }), false, 'REF_STRUCT is not a function');
124
- t.is(isFunction({ type: REF_TERNARY }), false, 'REF_TERNARY is a function');
125
- t.is(isFunction({ type: STRING }), false, 'STRING is not a function');
126
- t.is(isFunction({ type: WHITESPACE }), false, 'WHITESPACE is not a function');
127
- t.end();
128
- });
129
-
130
- test('isFxPrefix', t => {
131
- t.is(isFxPrefix(null), false, 'null is not a prefix');
132
- t.is(isFxPrefix({}), false, 'plain object is not a prefix');
133
- t.is(isFxPrefix({ type: BOOLEAN }), false, 'BOOLEAN is not a prefix');
134
- t.is(isFxPrefix({ type: ERROR }), false, 'ERROR is not a prefix');
135
- t.is(isFxPrefix({ type: FUNCTION }), false, 'FUNCTION is not a prefix');
136
- t.is(isFxPrefix({ type: FX_PREFIX }), true, 'FX_PREFIX is not a prefix');
137
- t.is(isFxPrefix({ type: NEWLINE }), false, 'NEWLINE is not a prefix');
138
- t.is(isFxPrefix({ type: NUMBER }), false, 'NUMBER is not a prefix');
139
- t.is(isFxPrefix({ type: OPERATOR }), false, 'OPERATOR is not a prefix');
140
- t.is(isFxPrefix({ type: REF_BEAM }), false, 'REF_BEAM is a prefix');
141
- t.is(isFxPrefix({ type: REF_NAMED }), false, 'REF_NAMED is not a prefix');
142
- t.is(isFxPrefix({ type: REF_RANGE }), false, 'REF_RANGE is a prefix');
143
- t.is(isFxPrefix({ type: REF_STRUCT }), false, 'REF_STRUCT is not a prefix');
144
- t.is(isFxPrefix({ type: REF_TERNARY }), false, 'REF_TERNARY is a prefix');
145
- t.is(isFxPrefix({ type: STRING }), false, 'STRING is not a prefix');
146
- t.is(isFxPrefix({ type: WHITESPACE }), false, 'WHITESPACE is not a prefix');
147
- t.end();
148
- });
149
-
150
- test('isOperator', t => {
151
- t.is(isOperator(null), false, 'null is not a operator');
152
- t.is(isOperator({}), false, 'plain object is not a operator');
153
- t.is(isOperator({ type: BOOLEAN }), false, 'BOOLEAN is not a operator');
154
- t.is(isOperator({ type: ERROR }), false, 'ERROR is not a operator');
155
- t.is(isOperator({ type: FUNCTION }), false, 'FUNCTION is not a operator');
156
- t.is(isOperator({ type: FX_PREFIX }), false, 'FX_PREFIX is not a operator');
157
- t.is(isOperator({ type: NEWLINE }), false, 'NEWLINE is not a operator');
158
- t.is(isOperator({ type: NUMBER }), false, 'NUMBER is not a operator');
159
- t.is(isOperator({ type: OPERATOR }), true, 'OPERATOR is not a operator');
160
- t.is(isOperator({ type: REF_BEAM }), false, 'REF_BEAM is a operator');
161
- t.is(isOperator({ type: REF_NAMED }), false, 'REF_NAMED is not a operator');
162
- t.is(isOperator({ type: REF_RANGE }), false, 'REF_RANGE is a operator');
163
- t.is(isOperator({ type: REF_STRUCT }), false, 'REF_STRUCT is not a operator');
164
- t.is(isOperator({ type: REF_TERNARY }), false, 'REF_TERNARY is a operator');
165
- t.is(isOperator({ type: STRING }), false, 'STRING is not a operator');
166
- t.is(isOperator({ type: WHITESPACE }), false, 'WHITESPACE is not a operator');
167
- t.end();
168
- });
@@ -1,324 +0,0 @@
1
- import { test, Test } from 'tape';
2
- import {
3
- FX_PREFIX, UNKNOWN,
4
- OPERATOR, WHITESPACE,
5
- REF_NAMED, CONTEXT_QUOTE, REF_STRUCT, REF_RANGE
6
- } from './constants.js';
7
- import { tokenize } from './lexer.js';
8
-
9
- Test.prototype.isTokens = function isTokens (expr, result, opts) {
10
- this.deepEqual(tokenize(expr, { negativeNumbers: false, ...opts }), result, expr);
11
- };
12
- Test.prototype.isTokensNeg = function isTokensNeg (expr, result, opts) {
13
- this.deepEqual(tokenize(expr, { ...opts, negativeNumbers: true }), result, expr);
14
- };
15
-
16
- test('tokenize structured references (merges on)', t => {
17
- // keyword specifiers
18
- t.isTokens('[@]', [
19
- { type: REF_STRUCT, value: '[@]' }
20
- ]);
21
- t.isTokens('[[@]]', [
22
- { type: UNKNOWN, value: '[' },
23
- { type: REF_STRUCT, value: '[@]' },
24
- { type: UNKNOWN, value: ']' }
25
- ]);
26
- t.isTokens('[@foo]', [
27
- { type: REF_STRUCT, value: '[@foo]' }
28
- ]);
29
- t.isTokens('[Column Name]', [
30
- { type: REF_STRUCT, value: '[Column Name]' }
31
- ]);
32
- t.isTokens('[@foo:bar]', [
33
- { type: REF_STRUCT, value: '[@foo:bar]' }
34
- ]);
35
- t.isTokens('[@[foo]:bar]', [
36
- { type: REF_STRUCT, value: '[@[foo]:bar]' }
37
- ]);
38
- t.isTokens('[@[foo]:[bar]]', [
39
- { type: REF_STRUCT, value: '[@[foo]:[bar]]' }
40
- ]);
41
- t.isTokens('[@foo:[bar]]', [
42
- { type: REF_STRUCT, value: '[@foo:[bar]]' }
43
- ]);
44
- t.isTokens('[@[foo]]', [
45
- { type: REF_STRUCT, value: '[@[foo]]' }
46
- ]);
47
- t.isTokens('[[@foo]]', [
48
- { type: UNKNOWN, value: '[' },
49
- { type: REF_STRUCT, value: '[@foo]' },
50
- { type: UNKNOWN, value: ']' }
51
- ]);
52
- t.isTokens('[[\'@foo]]', [
53
- { type: REF_STRUCT, value: '[[\'@foo]]' }
54
- ]);
55
- t.isTokens('[#All]', [
56
- { type: REF_STRUCT, value: '[#All]' }
57
- ]);
58
- t.isTokens('[#All]', [
59
- { type: REF_STRUCT, value: '[#All]' }
60
- ]);
61
- t.isTokens('[#Data]', [
62
- { type: REF_STRUCT, value: '[#Data]' }
63
- ]);
64
- t.isTokens('[#Headers]', [
65
- { type: REF_STRUCT, value: '[#Headers]' }
66
- ]);
67
- t.isTokens('[#Totals]', [
68
- { type: REF_STRUCT, value: '[#Totals]' }
69
- ]);
70
- t.isTokens('[#This Row]', [
71
- { type: REF_STRUCT, value: '[#This Row]' }
72
- ]);
73
- t.isTokens('[#Totals]', [
74
- { type: REF_STRUCT, value: '[#Totals]' }
75
- ]);
76
- t.isTokens('[#totals]', [
77
- { type: REF_STRUCT, value: '[#totals]' }
78
- ]);
79
- t.isTokens('[#tOtAlS]', [
80
- { type: REF_STRUCT, value: '[#tOtAlS]' }
81
- ]);
82
- t.isTokens('[#This Row]', [
83
- { type: UNKNOWN, value: '[' },
84
- { type: OPERATOR, value: '#' },
85
- { type: REF_NAMED, value: 'This' },
86
- { type: WHITESPACE, value: ' ' },
87
- { type: UNKNOWN, value: 'Row]' }
88
- ]);
89
- t.isTokens('[ #tOtAlS]', [
90
- { type: UNKNOWN, value: '[' },
91
- { type: WHITESPACE, value: ' ' },
92
- { type: OPERATOR, value: '#' },
93
- { type: UNKNOWN, value: 'tOtAlS]' }
94
- ]);
95
- t.isTokens('[#tOtAlS ]', [
96
- { type: UNKNOWN, value: '[' },
97
- { type: OPERATOR, value: '#' },
98
- { type: REF_NAMED, value: 'tOtAlS' },
99
- { type: WHITESPACE, value: ' ' },
100
- { type: UNKNOWN, value: ']' }
101
- ]);
102
- t.isTokens('[# tOtAlS ]', [
103
- { type: UNKNOWN, value: '[' },
104
- { type: OPERATOR, value: '#' },
105
- { type: WHITESPACE, value: ' ' },
106
- { type: REF_NAMED, value: 'tOtAlS' },
107
- { type: WHITESPACE, value: ' ' },
108
- { type: UNKNOWN, value: ']' }
109
- ]);
110
- t.isTokens('[[#all],@[foo]]', [
111
- { type: UNKNOWN, value: '[' },
112
- { type: REF_STRUCT, value: '[#all]' },
113
- { type: OPERATOR, value: ',' },
114
- { type: OPERATOR, value: '@' },
115
- { type: REF_STRUCT, value: '[foo]' },
116
- { type: UNKNOWN, value: ']' }
117
- ]);
118
- t.isTokens('[[#all],]', [
119
- { type: UNKNOWN, value: '[' },
120
- { type: REF_STRUCT, value: '[#all]' },
121
- { type: OPERATOR, value: ',' },
122
- { type: UNKNOWN, value: ']' }
123
- ]);
124
- t.isTokens('[[#data][#headers]]', [
125
- { type: UNKNOWN, value: '[' },
126
- { type: REF_STRUCT, value: '[#data]' },
127
- { type: REF_STRUCT, value: '[#headers]' },
128
- { type: UNKNOWN, value: ']' }
129
- ]);
130
- t.isTokens('[[#data]foo]', [
131
- { type: UNKNOWN, value: '[' },
132
- { type: REF_STRUCT, value: '[#data]' },
133
- { type: UNKNOWN, value: 'foo]' }
134
- ]);
135
- t.isTokens('[[#all],[foo]]', [
136
- { type: REF_STRUCT, value: '[[#all],[foo]]' }
137
- ]);
138
- t.isTokens('[[#all],foo]', [
139
- { type: REF_STRUCT, value: '[[#all],foo]' }
140
- ]);
141
- t.isTokens('[[#all],foo:bar]', [
142
- { type: REF_STRUCT, value: '[[#all],foo:bar]' }
143
- ]);
144
- t.isTokens('[[#all],[foo]:[bar]]', [
145
- { type: REF_STRUCT, value: '[[#all],[foo]:[bar]]' }
146
- ]);
147
- // this may not be what users expect, but "foo:bar baz" is a legit column name
148
- t.isTokens('[foo:bar baz]', [
149
- { type: REF_STRUCT, value: '[foo:bar baz]' }
150
- ]);
151
- t.isTokens('[foo:[bar baz]]', [
152
- { type: REF_STRUCT, value: '[foo:[bar baz]]' }
153
- ]);
154
- t.isTokens('[foo:]', [
155
- { type: REF_STRUCT, value: '[foo:]' }
156
- ]);
157
- t.isTokens('[[foo]:[bar baz]]', [
158
- { type: REF_STRUCT, value: '[[foo]:[bar baz]]' }
159
- ]);
160
- t.isTokens('[[#headers],[#data],[#headers],[#data],[#headers],[#data],[Baz]]', [
161
- { type: REF_STRUCT, value: '[[#headers],[#data],[#headers],[#data],[#headers],[#data],[Baz]]' }
162
- ]);
163
- t.isTokens('[[#all],[#all],[#all],[#all],[ColumnName]]', [
164
- { type: REF_STRUCT, value: '[[#all],[#all],[#all],[#all],[ColumnName]]' }
165
- ]);
166
- t.isTokens('[[#Totals],col name:Foo]', [
167
- { type: REF_STRUCT, value: '[[#Totals],col name:Foo]' }
168
- ]);
169
- t.isTokens('Table1[[#This Row],[a]]*[1]Sheet1!$A$1', [
170
- { type: REF_STRUCT, value: 'Table1[[#This Row],[a]]' },
171
- { type: OPERATOR, value: '*' },
172
- { type: REF_RANGE, value: '[1]Sheet1!$A$1' }
173
- ], { xlsx: true });
174
- t.isTokens("Sheet1!Table1[foo '[bar']]", [
175
- { type: REF_STRUCT, value: "Sheet1!Table1[foo '[bar']]" }
176
- ]);
177
- t.end();
178
- });
179
-
180
- test('tokenize structured references (merges off)', t => {
181
- t.isTokens('Table1[[#This Row],[Column]]', [
182
- { type: REF_NAMED, value: 'Table1' },
183
- { type: REF_STRUCT, value: '[[#This Row],[Column]]' }
184
- ], { mergeRefs: false });
185
- t.isTokens('DeptSales[[#Headers],[#Data],[% Commission]]', [
186
- { type: REF_NAMED, value: 'DeptSales' },
187
- { type: REF_STRUCT, value: '[[#Headers],[#Data],[% Commission]]' }
188
- ], { mergeRefs: false });
189
- t.isTokens('Table1[[#This Row],[Column Name]]', [
190
- { type: REF_NAMED, value: 'Table1' },
191
- { type: REF_STRUCT, value: '[[#This Row],[Column Name]]' }
192
- ], { mergeRefs: false });
193
- t.isTokens('Table1[@[Column]]', [
194
- { type: REF_NAMED, value: 'Table1' },
195
- { type: REF_STRUCT, value: '[@[Column]]' }
196
- ], { mergeRefs: false });
197
- t.isTokens('Table1[@Column]', [
198
- { type: REF_NAMED, value: 'Table1' },
199
- { type: REF_STRUCT, value: '[@Column]' }
200
- ], { mergeRefs: false });
201
- t.isTokens('Table1[ [#Data], [Surf]:[Rod] ]', [
202
- { type: REF_NAMED, value: 'Table1' },
203
- { type: REF_STRUCT, value: '[ [#Data], [Surf]:[Rod] ]' }
204
- ], { mergeRefs: false });
205
- // Excel does pick this up but normalizes to DeptSales[@[Commission Amount]]
206
- t.isTokens('DeptSales[@Commission Amount]', [
207
- { type: REF_NAMED, value: 'DeptSales' },
208
- { type: REF_STRUCT, value: '[@Commission Amount]' }
209
- ], { mergeRefs: false });
210
- t.isTokens('DeptSales[[#Totals],[Sales Amount]:[Commission Amount]]', [
211
- { type: REF_NAMED, value: 'DeptSales' },
212
- { type: REF_STRUCT, value: '[[#Totals],[Sales Amount]:[Commission Amount]]' }
213
- ], { mergeRefs: false });
214
- t.isTokens('DeptSales[[#Headers],[Region]:[Commission Amount]]', [
215
- { type: REF_NAMED, value: 'DeptSales' },
216
- { type: REF_STRUCT, value: '[[#Headers],[Region]:[Commission Amount]]' }
217
- ], { mergeRefs: false });
218
- t.isTokens('DeptSales[\'#OfItems]', [
219
- { type: REF_NAMED, value: 'DeptSales' },
220
- { type: REF_STRUCT, value: '[\'#OfItems]' }
221
- ], { mergeRefs: false });
222
- t.isTokens('Table1[[#Data],[#Totals],Bar:Baz]', [
223
- { type: REF_NAMED, value: 'Table1' },
224
- { type: REF_STRUCT, value: '[[#Data],[#Totals],Bar:Baz]' }
225
- ], { mergeRefs: false });
226
- t.isTokens('Table1[[Foo]:[Bar]]:Table1[Baz]', [
227
- { type: REF_NAMED, value: 'Table1' },
228
- { type: REF_STRUCT, value: '[[Foo]:[Bar]]' },
229
- { type: OPERATOR, value: ':' },
230
- { type: REF_NAMED, value: 'Table1' },
231
- { type: REF_STRUCT, value: '[Baz]' }
232
- ], { mergeRefs: false });
233
- t.isTokens('Table1[Bar]:Table1[Baz]', [
234
- { type: REF_NAMED, value: 'Table1' },
235
- { type: REF_STRUCT, value: '[Bar]' },
236
- { type: OPERATOR, value: ':' },
237
- { type: REF_NAMED, value: 'Table1' },
238
- { type: REF_STRUCT, value: '[Baz]' }
239
- ], { mergeRefs: false });
240
- t.isTokens('Table1[[#Headers],[My\'#thing]]', [
241
- { type: REF_NAMED, value: 'Table1' },
242
- { type: REF_STRUCT, value: '[[#Headers],[My\'#thing]]' }
243
- ], { mergeRefs: false });
244
- t.isTokens('DeptSales[Sales Amount]*DeptSales[% Commission]', [
245
- { type: REF_NAMED, value: 'DeptSales' },
246
- { type: REF_STRUCT, value: '[Sales Amount]' },
247
- { type: OPERATOR, value: '*' },
248
- { type: REF_NAMED, value: 'DeptSales' },
249
- { type: REF_STRUCT, value: '[% Commission]' }
250
- ], { mergeRefs: false });
251
- t.isTokens('=\'Sales - May2020.xlsx\'!Table1[ [#Data], [#Totals], [Surf]:[Rod] ]', [
252
- { type: FX_PREFIX, value: '=' },
253
- { type: CONTEXT_QUOTE, value: '\'Sales - May2020.xlsx\'' },
254
- { type: OPERATOR, value: '!' },
255
- { type: REF_NAMED, value: 'Table1' },
256
- { type: REF_STRUCT, value: '[ [#Data], [#Totals], [Surf]:[Rod] ]' }
257
- ], { mergeRefs: false });
258
- t.end();
259
- });
260
-
261
- test('tokenize structured references (merges on)', t => {
262
- t.isTokens('Table1[[#This Row],[Column]]', [
263
- { type: REF_STRUCT, value: 'Table1[[#This Row],[Column]]' }
264
- ]);
265
- t.isTokens('DeptSales[[#Headers],[#Data],[% Commission]]', [
266
- { type: REF_STRUCT, value: 'DeptSales[[#Headers],[#Data],[% Commission]]' }
267
- ]);
268
- t.isTokens('Table1[[#This Row],[Column Name]]', [
269
- { type: REF_STRUCT, value: 'Table1[[#This Row],[Column Name]]' }
270
- ]);
271
- t.isTokens('Table1[@[Column]]', [
272
- { type: REF_STRUCT, value: 'Table1[@[Column]]' }
273
- ]);
274
- t.isTokens('Table1[@Column]', [
275
- { type: REF_STRUCT, value: 'Table1[@Column]' }
276
- ]);
277
- t.isTokens('Table1[ [#Data], [Surf]:[Rod] ]', [
278
- { type: REF_STRUCT, value: 'Table1[ [#Data], [Surf]:[Rod] ]' }
279
- ]);
280
- // Excel does pick this up but normalizes to DeptSales[@[Commission Amount]]
281
- t.isTokens('DeptSales[@Commission Amount]', [
282
- { type: REF_STRUCT, value: 'DeptSales[@Commission Amount]' }
283
- ]);
284
- t.isTokens('DeptSales[[#Totals],[Sales Amount]:[Commission Amount]]', [
285
- { type: REF_STRUCT, value: 'DeptSales[[#Totals],[Sales Amount]:[Commission Amount]]' }
286
- ]);
287
- t.isTokens('DeptSales[[#Headers],[Region]:[Commission Amount]]', [
288
- { type: REF_STRUCT, value: 'DeptSales[[#Headers],[Region]:[Commission Amount]]' }
289
- ]);
290
- t.isTokens('DeptSales[\'#OfItems]', [
291
- { type: REF_STRUCT, value: 'DeptSales[\'#OfItems]' }
292
- ]);
293
- t.isTokens('Table1[[#Data],[#Totals],Bar:Baz]', [
294
- { type: REF_STRUCT, value: 'Table1[[#Data],[#Totals],Bar:Baz]' }
295
- ]);
296
- t.isTokens('Table1[[Foo]:[Bar]]:Table1[Baz]', [
297
- { type: REF_STRUCT, value: 'Table1[[Foo]:[Bar]]' },
298
- { type: OPERATOR, value: ':' },
299
- { type: REF_STRUCT, value: 'Table1[Baz]' }
300
- ]);
301
- t.isTokens('Table1[Bar]:Table1[Baz]', [
302
- { type: REF_STRUCT, value: 'Table1[Bar]' },
303
- { type: OPERATOR, value: ':' },
304
- { type: REF_STRUCT, value: 'Table1[Baz]' }
305
- ]);
306
- t.isTokens('Table1[[#Headers],[My\'#thing]]', [
307
- { type: REF_STRUCT, value: 'Table1[[#Headers],[My\'#thing]]' }
308
- ]);
309
- t.isTokens('DeptSales[Sales Amount]*DeptSales[% Commission]', [
310
- { type: REF_STRUCT, value: 'DeptSales[Sales Amount]' },
311
- { type: OPERATOR, value: '*' },
312
- { type: REF_STRUCT, value: 'DeptSales[% Commission]' }
313
- ]);
314
- t.isTokens('=\'Sales - May2020.xlsx\'!Table1[ [#Data], [#Totals], [Surf]:[Rod] ]', [
315
- { type: FX_PREFIX, value: '=' },
316
- { type: REF_STRUCT, value: '\'Sales - May2020.xlsx\'!Table1[ [#Data], [#Totals], [Surf]:[Rod] ]' }
317
- ]);
318
-
319
- t.isTokens('=[myworkbook.xlsx]Sheet1!TMP8w0habhr[#All]', [
320
- { type: FX_PREFIX, value: '=' },
321
- { type: REF_STRUCT, value: '[myworkbook.xlsx]Sheet1!TMP8w0habhr[#All]' }
322
- ]);
323
- t.end();
324
- });