@gooddata/sdk-maql-language-server 0.0.0-stage → 11.65.0-alpha.3

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 (312) hide show
  1. package/LICENSE +7 -0
  2. package/README.md +118 -2
  3. package/esm/completions/complete.d.ts +12 -0
  4. package/esm/completions/complete.d.ts.map +1 -0
  5. package/esm/completions/complete.js +316 -0
  6. package/esm/completions/descriptions.d.ts +42 -0
  7. package/esm/completions/descriptions.d.ts.map +1 -0
  8. package/esm/completions/descriptions.js +290 -0
  9. package/esm/completions/findContext.d.ts +19 -0
  10. package/esm/completions/findContext.d.ts.map +1 -0
  11. package/esm/completions/findContext.js +172 -0
  12. package/esm/completions/functionDescriptions.d.ts +3 -0
  13. package/esm/completions/functionDescriptions.d.ts.map +1 -0
  14. package/esm/completions/functionDescriptions.js +99 -0
  15. package/esm/completions/sort.d.ts +4 -0
  16. package/esm/completions/sort.d.ts.map +1 -0
  17. package/esm/completions/sort.js +88 -0
  18. package/esm/constants.d.ts +21 -0
  19. package/esm/constants.d.ts.map +1 -0
  20. package/esm/constants.js +22 -0
  21. package/esm/dateElementFormat.d.ts +9 -0
  22. package/esm/dateElementFormat.d.ts.map +1 -0
  23. package/esm/dateElementFormat.js +60 -0
  24. package/esm/decorations.d.ts +39 -0
  25. package/esm/decorations.d.ts.map +1 -0
  26. package/esm/decorations.js +42 -0
  27. package/esm/diagnostics.d.ts +12 -0
  28. package/esm/diagnostics.d.ts.map +1 -0
  29. package/esm/diagnostics.js +260 -0
  30. package/esm/docs/en/docs/create-metrics/maql/aggregation/approximate_count.d.ts +2 -0
  31. package/esm/docs/en/docs/create-metrics/maql/aggregation/approximate_count.d.ts.map +1 -0
  32. package/esm/docs/en/docs/create-metrics/maql/aggregation/approximate_count.js +61 -0
  33. package/esm/docs/en/docs/create-metrics/maql/aggregation/avg.d.ts +2 -0
  34. package/esm/docs/en/docs/create-metrics/maql/aggregation/avg.d.ts.map +1 -0
  35. package/esm/docs/en/docs/create-metrics/maql/aggregation/avg.js +19 -0
  36. package/esm/docs/en/docs/create-metrics/maql/aggregation/count.d.ts +2 -0
  37. package/esm/docs/en/docs/create-metrics/maql/aggregation/count.d.ts.map +1 -0
  38. package/esm/docs/en/docs/create-metrics/maql/aggregation/count.js +72 -0
  39. package/esm/docs/en/docs/create-metrics/maql/aggregation/first.d.ts +2 -0
  40. package/esm/docs/en/docs/create-metrics/maql/aggregation/first.d.ts.map +1 -0
  41. package/esm/docs/en/docs/create-metrics/maql/aggregation/first.js +41 -0
  42. package/esm/docs/en/docs/create-metrics/maql/aggregation/last.d.ts +2 -0
  43. package/esm/docs/en/docs/create-metrics/maql/aggregation/last.d.ts.map +1 -0
  44. package/esm/docs/en/docs/create-metrics/maql/aggregation/last.js +69 -0
  45. package/esm/docs/en/docs/create-metrics/maql/aggregation/max.d.ts +2 -0
  46. package/esm/docs/en/docs/create-metrics/maql/aggregation/max.d.ts.map +1 -0
  47. package/esm/docs/en/docs/create-metrics/maql/aggregation/max.js +61 -0
  48. package/esm/docs/en/docs/create-metrics/maql/aggregation/median.d.ts +2 -0
  49. package/esm/docs/en/docs/create-metrics/maql/aggregation/median.d.ts.map +1 -0
  50. package/esm/docs/en/docs/create-metrics/maql/aggregation/median.js +25 -0
  51. package/esm/docs/en/docs/create-metrics/maql/aggregation/min.d.ts +2 -0
  52. package/esm/docs/en/docs/create-metrics/maql/aggregation/min.d.ts.map +1 -0
  53. package/esm/docs/en/docs/create-metrics/maql/aggregation/min.js +63 -0
  54. package/esm/docs/en/docs/create-metrics/maql/aggregation/sum.d.ts +2 -0
  55. package/esm/docs/en/docs/create-metrics/maql/aggregation/sum.d.ts.map +1 -0
  56. package/esm/docs/en/docs/create-metrics/maql/aggregation/sum.js +20 -0
  57. package/esm/docs/en/docs/create-metrics/maql/conditionals/case.d.ts +2 -0
  58. package/esm/docs/en/docs/create-metrics/maql/conditionals/case.d.ts.map +1 -0
  59. package/esm/docs/en/docs/create-metrics/maql/conditionals/case.js +73 -0
  60. package/esm/docs/en/docs/create-metrics/maql/conditionals/if-then-else.d.ts +2 -0
  61. package/esm/docs/en/docs/create-metrics/maql/conditionals/if-then-else.d.ts.map +1 -0
  62. package/esm/docs/en/docs/create-metrics/maql/conditionals/if-then-else.js +29 -0
  63. package/esm/docs/en/docs/create-metrics/maql/conditionals/ifnull.d.ts +2 -0
  64. package/esm/docs/en/docs/create-metrics/maql/conditionals/ifnull.d.ts.map +1 -0
  65. package/esm/docs/en/docs/create-metrics/maql/conditionals/ifnull.js +96 -0
  66. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-ranking-filters.d.ts +2 -0
  67. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-ranking-filters.d.ts.map +1 -0
  68. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-ranking-filters.js +71 -0
  69. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-having-clause.d.ts +2 -0
  70. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-having-clause.d.ts.map +1 -0
  71. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-having-clause.js +65 -0
  72. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-like-clause.d.ts +2 -0
  73. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-like-clause.d.ts.map +1 -0
  74. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-like-clause.js +36 -0
  75. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-where-clause.d.ts +2 -0
  76. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-where-clause.d.ts.map +1 -0
  77. package/esm/docs/en/docs/create-metrics/maql/filters/filtering-with-the-where-clause.js +36 -0
  78. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions-except-for-attribute.d.ts +2 -0
  79. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions-except-for-attribute.d.ts.map +1 -0
  80. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions-except-for-attribute.js +21 -0
  81. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions.d.ts +2 -0
  82. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions.d.ts.map +1 -0
  83. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all-in-all-other-dimensions.js +27 -0
  84. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all.d.ts +2 -0
  85. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all.d.ts.map +1 -0
  86. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-all.js +64 -0
  87. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-attribute-all-in-all-other-dimensions.d.ts +2 -0
  88. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-attribute-all-in-all-other-dimensions.d.ts.map +1 -0
  89. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by-attribute-all-in-all-other-dimensions.js +22 -0
  90. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by.d.ts +2 -0
  91. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by.d.ts.map +1 -0
  92. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-attribute-filters/by.js +85 -0
  93. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-except.d.ts +2 -0
  94. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-except.d.ts.map +1 -0
  95. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-except.js +37 -0
  96. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-filter.d.ts +2 -0
  97. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-filter.d.ts.map +1 -0
  98. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/with-parent-filter.js +42 -0
  99. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-except.d.ts +2 -0
  100. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-except.d.ts.map +1 -0
  101. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-except.js +94 -0
  102. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-filter.d.ts +2 -0
  103. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-filter.d.ts.map +1 -0
  104. package/esm/docs/en/docs/create-metrics/maql/filters/overriding-parent/without-parent-filter.js +33 -0
  105. package/esm/docs/en/docs/create-metrics/maql/for-each.d.ts +2 -0
  106. package/esm/docs/en/docs/create-metrics/maql/for-each.d.ts.map +1 -0
  107. package/esm/docs/en/docs/create-metrics/maql/for-each.js +17 -0
  108. package/esm/docs/en/docs/create-metrics/maql/logical-operators/and.d.ts +2 -0
  109. package/esm/docs/en/docs/create-metrics/maql/logical-operators/and.d.ts.map +1 -0
  110. package/esm/docs/en/docs/create-metrics/maql/logical-operators/and.js +37 -0
  111. package/esm/docs/en/docs/create-metrics/maql/logical-operators/not.d.ts +2 -0
  112. package/esm/docs/en/docs/create-metrics/maql/logical-operators/not.d.ts.map +1 -0
  113. package/esm/docs/en/docs/create-metrics/maql/logical-operators/not.js +12 -0
  114. package/esm/docs/en/docs/create-metrics/maql/logical-operators/or.d.ts +2 -0
  115. package/esm/docs/en/docs/create-metrics/maql/logical-operators/or.d.ts.map +1 -0
  116. package/esm/docs/en/docs/create-metrics/maql/logical-operators/or.js +22 -0
  117. package/esm/docs/en/docs/create-metrics/maql/maql-and-multidimensionality.d.ts +2 -0
  118. package/esm/docs/en/docs/create-metrics/maql/maql-and-multidimensionality.d.ts.map +1 -0
  119. package/esm/docs/en/docs/create-metrics/maql/maql-and-multidimensionality.js +59 -0
  120. package/esm/docs/en/docs/create-metrics/maql/math/abs.d.ts +2 -0
  121. package/esm/docs/en/docs/create-metrics/maql/math/abs.d.ts.map +1 -0
  122. package/esm/docs/en/docs/create-metrics/maql/math/abs.js +23 -0
  123. package/esm/docs/en/docs/create-metrics/maql/math/arithmetic-operations.d.ts +2 -0
  124. package/esm/docs/en/docs/create-metrics/maql/math/arithmetic-operations.d.ts.map +1 -0
  125. package/esm/docs/en/docs/create-metrics/maql/math/arithmetic-operations.js +29 -0
  126. package/esm/docs/en/docs/create-metrics/maql/math/ceiling.d.ts +2 -0
  127. package/esm/docs/en/docs/create-metrics/maql/math/ceiling.d.ts.map +1 -0
  128. package/esm/docs/en/docs/create-metrics/maql/math/ceiling.js +21 -0
  129. package/esm/docs/en/docs/create-metrics/maql/math/exp.d.ts +2 -0
  130. package/esm/docs/en/docs/create-metrics/maql/math/exp.d.ts.map +1 -0
  131. package/esm/docs/en/docs/create-metrics/maql/math/exp.js +27 -0
  132. package/esm/docs/en/docs/create-metrics/maql/math/floor.d.ts +2 -0
  133. package/esm/docs/en/docs/create-metrics/maql/math/floor.d.ts.map +1 -0
  134. package/esm/docs/en/docs/create-metrics/maql/math/floor.js +21 -0
  135. package/esm/docs/en/docs/create-metrics/maql/math/greatest.d.ts +2 -0
  136. package/esm/docs/en/docs/create-metrics/maql/math/greatest.d.ts.map +1 -0
  137. package/esm/docs/en/docs/create-metrics/maql/math/greatest.js +13 -0
  138. package/esm/docs/en/docs/create-metrics/maql/math/least.d.ts +2 -0
  139. package/esm/docs/en/docs/create-metrics/maql/math/least.d.ts.map +1 -0
  140. package/esm/docs/en/docs/create-metrics/maql/math/least.js +13 -0
  141. package/esm/docs/en/docs/create-metrics/maql/math/ln.d.ts +2 -0
  142. package/esm/docs/en/docs/create-metrics/maql/math/ln.d.ts.map +1 -0
  143. package/esm/docs/en/docs/create-metrics/maql/math/ln.js +33 -0
  144. package/esm/docs/en/docs/create-metrics/maql/math/log.d.ts +2 -0
  145. package/esm/docs/en/docs/create-metrics/maql/math/log.d.ts.map +1 -0
  146. package/esm/docs/en/docs/create-metrics/maql/math/log.js +29 -0
  147. package/esm/docs/en/docs/create-metrics/maql/math/power.d.ts +2 -0
  148. package/esm/docs/en/docs/create-metrics/maql/math/power.d.ts.map +1 -0
  149. package/esm/docs/en/docs/create-metrics/maql/math/power.js +33 -0
  150. package/esm/docs/en/docs/create-metrics/maql/math/round.d.ts +2 -0
  151. package/esm/docs/en/docs/create-metrics/maql/math/round.d.ts.map +1 -0
  152. package/esm/docs/en/docs/create-metrics/maql/math/round.js +34 -0
  153. package/esm/docs/en/docs/create-metrics/maql/math/sign.d.ts +2 -0
  154. package/esm/docs/en/docs/create-metrics/maql/math/sign.d.ts.map +1 -0
  155. package/esm/docs/en/docs/create-metrics/maql/math/sign.js +30 -0
  156. package/esm/docs/en/docs/create-metrics/maql/math/sqrt.d.ts +2 -0
  157. package/esm/docs/en/docs/create-metrics/maql/math/sqrt.d.ts.map +1 -0
  158. package/esm/docs/en/docs/create-metrics/maql/math/sqrt.js +32 -0
  159. package/esm/docs/en/docs/create-metrics/maql/math/trunc.d.ts +2 -0
  160. package/esm/docs/en/docs/create-metrics/maql/math/trunc.d.ts.map +1 -0
  161. package/esm/docs/en/docs/create-metrics/maql/math/trunc.js +36 -0
  162. package/esm/docs/en/docs/create-metrics/maql/ranking/percentile.d.ts +2 -0
  163. package/esm/docs/en/docs/create-metrics/maql/ranking/percentile.d.ts.map +1 -0
  164. package/esm/docs/en/docs/create-metrics/maql/ranking/percentile.js +57 -0
  165. package/esm/docs/en/docs/create-metrics/maql/ranking/rank-variations.d.ts +2 -0
  166. package/esm/docs/en/docs/create-metrics/maql/ranking/rank-variations.d.ts.map +1 -0
  167. package/esm/docs/en/docs/create-metrics/maql/ranking/rank-variations.js +90 -0
  168. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-in.d.ts +2 -0
  169. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-in.d.ts.map +1 -0
  170. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-in.js +53 -0
  171. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-of.d.ts +2 -0
  172. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-of.d.ts.map +1 -0
  173. package/esm/docs/en/docs/create-metrics/maql/ranking/where-top-or-bottom-of.js +29 -0
  174. package/esm/docs/en/docs/create-metrics/maql/ranking/within-clause.d.ts +2 -0
  175. package/esm/docs/en/docs/create-metrics/maql/ranking/within-clause.d.ts.map +1 -0
  176. package/esm/docs/en/docs/create-metrics/maql/ranking/within-clause.js +101 -0
  177. package/esm/docs/en/docs/create-metrics/maql/relational-operators.d.ts +2 -0
  178. package/esm/docs/en/docs/create-metrics/maql/relational-operators.d.ts.map +1 -0
  179. package/esm/docs/en/docs/create-metrics/maql/relational-operators.js +50 -0
  180. package/esm/docs/en/docs/create-metrics/maql/runing-totals/rolling-window.d.ts +2 -0
  181. package/esm/docs/en/docs/create-metrics/maql/runing-totals/rolling-window.d.ts.map +1 -0
  182. package/esm/docs/en/docs/create-metrics/maql/runing-totals/rolling-window.js +71 -0
  183. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-total-statistical-functions.d.ts +2 -0
  184. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-total-statistical-functions.d.ts.map +1 -0
  185. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-total-statistical-functions.js +54 -0
  186. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-totals-for-core-functions.d.ts +2 -0
  187. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-totals-for-core-functions.d.ts.map +1 -0
  188. package/esm/docs/en/docs/create-metrics/maql/runing-totals/running-totals-for-core-functions.js +37 -0
  189. package/esm/docs/en/docs/create-metrics/maql/statistic/correl.d.ts +2 -0
  190. package/esm/docs/en/docs/create-metrics/maql/statistic/correl.d.ts.map +1 -0
  191. package/esm/docs/en/docs/create-metrics/maql/statistic/correl.js +47 -0
  192. package/esm/docs/en/docs/create-metrics/maql/statistic/covariance-functions.d.ts +2 -0
  193. package/esm/docs/en/docs/create-metrics/maql/statistic/covariance-functions.d.ts.map +1 -0
  194. package/esm/docs/en/docs/create-metrics/maql/statistic/covariance-functions.js +46 -0
  195. package/esm/docs/en/docs/create-metrics/maql/statistic/forecast.d.ts +2 -0
  196. package/esm/docs/en/docs/create-metrics/maql/statistic/forecast.d.ts.map +1 -0
  197. package/esm/docs/en/docs/create-metrics/maql/statistic/forecast.js +74 -0
  198. package/esm/docs/en/docs/create-metrics/maql/statistic/least-squares-functions.d.ts +2 -0
  199. package/esm/docs/en/docs/create-metrics/maql/statistic/least-squares-functions.d.ts.map +1 -0
  200. package/esm/docs/en/docs/create-metrics/maql/statistic/least-squares-functions.js +44 -0
  201. package/esm/docs/en/docs/create-metrics/maql/statistic/standard-deviation-functions.d.ts +2 -0
  202. package/esm/docs/en/docs/create-metrics/maql/statistic/standard-deviation-functions.d.ts.map +1 -0
  203. package/esm/docs/en/docs/create-metrics/maql/statistic/standard-deviation-functions.js +88 -0
  204. package/esm/docs/en/docs/create-metrics/maql/statistic/variance-functions.d.ts +2 -0
  205. package/esm/docs/en/docs/create-metrics/maql/statistic/variance-functions.d.ts.map +1 -0
  206. package/esm/docs/en/docs/create-metrics/maql/statistic/variance-functions.js +54 -0
  207. package/esm/docs/en/docs/create-metrics/maql/time/for-each.d.ts +2 -0
  208. package/esm/docs/en/docs/create-metrics/maql/time/for-each.d.ts.map +1 -0
  209. package/esm/docs/en/docs/create-metrics/maql/time/for-each.js +96 -0
  210. package/esm/docs/en/docs/create-metrics/maql/time/for-next-period.d.ts +2 -0
  211. package/esm/docs/en/docs/create-metrics/maql/time/for-next-period.d.ts.map +1 -0
  212. package/esm/docs/en/docs/create-metrics/maql/time/for-next-period.js +38 -0
  213. package/esm/docs/en/docs/create-metrics/maql/time/for-next.d.ts +2 -0
  214. package/esm/docs/en/docs/create-metrics/maql/time/for-next.d.ts.map +1 -0
  215. package/esm/docs/en/docs/create-metrics/maql/time/for-next.js +27 -0
  216. package/esm/docs/en/docs/create-metrics/maql/time/for-previous-period.d.ts +2 -0
  217. package/esm/docs/en/docs/create-metrics/maql/time/for-previous-period.d.ts.map +1 -0
  218. package/esm/docs/en/docs/create-metrics/maql/time/for-previous-period.js +26 -0
  219. package/esm/docs/en/docs/create-metrics/maql/time/for-previous.d.ts +2 -0
  220. package/esm/docs/en/docs/create-metrics/maql/time/for-previous.d.ts.map +1 -0
  221. package/esm/docs/en/docs/create-metrics/maql/time/for-previous.js +30 -0
  222. package/esm/docs/en/docs/create-metrics/maql/time/functions-for-referring-to-past-time-periods.d.ts +2 -0
  223. package/esm/docs/en/docs/create-metrics/maql/time/functions-for-referring-to-past-time-periods.d.ts.map +1 -0
  224. package/esm/docs/en/docs/create-metrics/maql/time/functions-for-referring-to-past-time-periods.js +36 -0
  225. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-add.d.ts +2 -0
  226. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-add.d.ts.map +1 -0
  227. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-add.js +53 -0
  228. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-diff.d.ts +2 -0
  229. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-diff.d.ts.map +1 -0
  230. package/esm/docs/en/docs/create-metrics/maql/time-arithmetics/datetime-diff.js +55 -0
  231. package/esm/docs/en/docs/create-metrics/maql/time-macros.d.ts +2 -0
  232. package/esm/docs/en/docs/create-metrics/maql/time-macros.d.ts.map +1 -0
  233. package/esm/docs/en/docs/create-metrics/maql/time-macros.js +79 -0
  234. package/esm/docs/index.d.ts +77 -0
  235. package/esm/docs/index.d.ts.map +1 -0
  236. package/esm/docs/index.js +141 -0
  237. package/esm/findObjects.d.ts +13 -0
  238. package/esm/findObjects.d.ts.map +1 -0
  239. package/esm/findObjects.js +72 -0
  240. package/esm/format.d.ts +4 -0
  241. package/esm/format.d.ts.map +1 -0
  242. package/esm/format.js +581 -0
  243. package/esm/highlight/convert.d.ts +3 -0
  244. package/esm/highlight/convert.d.ts.map +1 -0
  245. package/esm/highlight/convert.js +12 -0
  246. package/esm/highlight/semanticsHighlight.d.ts +29 -0
  247. package/esm/highlight/semanticsHighlight.d.ts.map +1 -0
  248. package/esm/highlight/semanticsHighlight.js +326 -0
  249. package/esm/highlight/utils.d.ts +3 -0
  250. package/esm/highlight/utils.d.ts.map +1 -0
  251. package/esm/highlight/utils.js +14 -0
  252. package/esm/hover.d.ts +17 -0
  253. package/esm/hover.d.ts.map +1 -0
  254. package/esm/hover.js +60 -0
  255. package/esm/index.d.ts +9 -0
  256. package/esm/index.d.ts.map +1 -0
  257. package/esm/index.js +7 -0
  258. package/esm/labelElements.d.ts +22 -0
  259. package/esm/labelElements.d.ts.map +1 -0
  260. package/esm/labelElements.js +225 -0
  261. package/esm/maqlLanguageService.d.ts +51 -0
  262. package/esm/maqlLanguageService.d.ts.map +1 -0
  263. package/esm/maqlLanguageService.js +102 -0
  264. package/esm/maqlObjectTypes.d.ts +15 -0
  265. package/esm/maqlObjectTypes.d.ts.map +1 -0
  266. package/esm/maqlObjectTypes.js +28 -0
  267. package/esm/maqlServer.d.ts +4 -0
  268. package/esm/maqlServer.d.ts.map +1 -0
  269. package/esm/maqlServer.js +78 -0
  270. package/esm/metadata/model.d.ts +116 -0
  271. package/esm/metadata/model.d.ts.map +1 -0
  272. package/esm/metadata/model.js +137 -0
  273. package/esm/metadata/parameters.d.ts +16 -0
  274. package/esm/metadata/parameters.d.ts.map +1 -0
  275. package/esm/metadata/parameters.js +38 -0
  276. package/esm/metadata/types.d.ts +14 -0
  277. package/esm/metadata/types.d.ts.map +1 -0
  278. package/esm/metadata/types.js +2 -0
  279. package/esm/metadataService.d.ts +50 -0
  280. package/esm/metadataService.d.ts.map +1 -0
  281. package/esm/metadataService.js +156 -0
  282. package/esm/node/main.d.ts +2 -0
  283. package/esm/node/main.d.ts.map +1 -0
  284. package/esm/node/main.js +18 -0
  285. package/esm/parameterConstraints.d.ts +5 -0
  286. package/esm/parameterConstraints.d.ts.map +1 -0
  287. package/esm/parameterConstraints.js +198 -0
  288. package/esm/parseMaql.d.ts +43 -0
  289. package/esm/parseMaql.d.ts.map +1 -0
  290. package/esm/parseMaql.js +97 -0
  291. package/esm/renderParameters.d.ts +33 -0
  292. package/esm/renderParameters.d.ts.map +1 -0
  293. package/esm/renderParameters.js +72 -0
  294. package/esm/tests/metadata.test.helpers.d.ts +8 -0
  295. package/esm/tests/metadata.test.helpers.d.ts.map +1 -0
  296. package/esm/tests/metadata.test.helpers.js +468 -0
  297. package/esm/tokenRanges.d.ts +36 -0
  298. package/esm/tokenRanges.d.ts.map +1 -0
  299. package/esm/tokenRanges.js +54 -0
  300. package/esm/types/hierarchy.d.ts +37 -0
  301. package/esm/types/hierarchy.d.ts.map +1 -0
  302. package/esm/types/hierarchy.js +165 -0
  303. package/esm/types/signatures.d.ts +40 -0
  304. package/esm/types/signatures.d.ts.map +1 -0
  305. package/esm/types/signatures.js +142 -0
  306. package/esm/types/typeChecking.d.ts +56 -0
  307. package/esm/types/typeChecking.d.ts.map +1 -0
  308. package/esm/types/typeChecking.js +296 -0
  309. package/esm/types/typeModel.d.ts +18 -0
  310. package/esm/types/typeModel.d.ts.map +1 -0
  311. package/esm/types/typeModel.js +84 -0
  312. package/package.json +89 -3
@@ -0,0 +1,88 @@
1
+ // (C) 2022-2026 GoodData Corporation
2
+ import { Kind } from "./descriptions.js";
3
+ const defaultPrefix = "90__";
4
+ const sortPrefixes = {
5
+ [Kind.LabelElement]: "00__",
6
+ [Kind.Attribute]: "20__",
7
+ // [Kind.Label]: "20__", // this is the same as Kind.Label is the same as Kind.Attribute
8
+ [Kind.Dataset]: "21__",
9
+ [Kind.Fact]: "22__",
10
+ [Kind.Metric]: "25__",
11
+ [Kind.Granularity]: "30__",
12
+ [Kind.Function]: "40__",
13
+ [Kind.Keyword]: "41__",
14
+ [Kind.Boolean]: "42__",
15
+ [Kind.Operator]: "99__",
16
+ };
17
+ function getFunctionSortTemplate(functionName, prefixes) {
18
+ // Handle IFNULL function
19
+ if (functionName === "IFNULL") {
20
+ return prefixes([Kind.Metric, Kind.Function]);
21
+ }
22
+ // Handle statistical functions
23
+ const statisticalFunctions = [
24
+ "CORREL",
25
+ "COVAR",
26
+ "COVARP",
27
+ "FORECAST",
28
+ "RSQ",
29
+ "STDEV",
30
+ "STDEVP",
31
+ "VAR",
32
+ "VARP",
33
+ ];
34
+ if (statisticalFunctions.includes(functionName)) {
35
+ return prefixes([Kind.Fact, Kind.Metric]);
36
+ }
37
+ // Default case for other functions
38
+ return prefixes([Kind.Granularity, Kind.Label, Kind.Fact, Kind.Metric, Kind.Function]);
39
+ }
40
+ export function adjustSortText(list, context) {
41
+ let template = Object.assign({}, sortPrefixes);
42
+ const prefixes = (order) => order.reduce((prev, curr, idx) => ({
43
+ ...prev,
44
+ [curr]: `${String(idx + 1).padStart(2, "0")}__`,
45
+ }), template);
46
+ // Find the lowest non-empty (therefore complete and valid) AST node if such exists
47
+ const lowestNode = context.nodeStack.find((node) => node.type !== "");
48
+ switch (lowestNode?.type) {
49
+ case "metric":
50
+ template = prefixes([Kind.Function, Kind.Metric, Kind.Fact]);
51
+ break;
52
+ case "and":
53
+ case "or":
54
+ case "not":
55
+ template = prefixes([Kind.Label, Kind.Metric, Kind.Fact]);
56
+ break;
57
+ case "case":
58
+ case "when":
59
+ template = prefixes([Kind.Metric, Kind.Fact, Kind.Label, Kind.Function]);
60
+ break;
61
+ case "where":
62
+ case "having":
63
+ template = prefixes([Kind.Label, Kind.Metric, Kind.Fact, Kind.Function]);
64
+ break;
65
+ case "by":
66
+ template = prefixes([Kind.Dataset, Kind.Label, Kind.Keyword]);
67
+ break;
68
+ case "+":
69
+ case "=":
70
+ case "/":
71
+ case "*":
72
+ template = prefixes([Kind.Fact, Kind.Metric]);
73
+ break;
74
+ case "function":
75
+ case "time macro":
76
+ template = getFunctionSortTemplate(lowestNode.name, prefixes);
77
+ break;
78
+ }
79
+ list.items = list.items.map((it) => {
80
+ const prefix = it.kind ? (template[it.kind] ?? defaultPrefix) : defaultPrefix;
81
+ return {
82
+ ...it,
83
+ sortText: prefix + (it.sortText ?? it.label),
84
+ preselect: true, // a hack to force the client to use sortText
85
+ };
86
+ });
87
+ return list;
88
+ }
@@ -0,0 +1,21 @@
1
+ export declare const LanguageId: string;
2
+ export declare const diagnosticsSource: string;
3
+ export declare enum ErrorCodes {
4
+ InputMismatch = 0,
5
+ NoViableAlternative = 1,
6
+ FailedPredicate = 2,
7
+ UnspecifiedError = 3,
8
+ UnrecognizedInput = 4,
9
+ UnterminatedString = 5,
10
+ UndefinedKeyword = 6,
11
+ InvalidType = 7,
12
+ ExtraIdentifiersInObject = 8,
13
+ ObjectNotFound = 9,
14
+ LabelElementNotFound = 10,
15
+ InvalidOperator = 11,
16
+ SuspiciousStringLiteral = 12,
17
+ ParameterValueNotAllowed = 13,
18
+ ParameterValueUncovered = 14,
19
+ InvalidLabelElementValue = 15
20
+ }
21
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAEA,eAAO,MAAM,UAAU,EAAE,MAAe,CAAC;AAEzC,eAAO,MAAM,iBAAiB,QAA2B,CAAC;AAE1D,oBAAY,UAAU;IAClB,aAAa,IAAI;IACjB,mBAAmB,IAAI;IACvB,eAAe,IAAI;IACnB,gBAAgB,IAAI;IACpB,iBAAiB,IAAI;IACrB,kBAAkB,IAAI;IACtB,gBAAgB,IAAI;IACpB,WAAW,IAAI;IACf,wBAAwB,IAAI;IAC5B,cAAc,IAAI;IAClB,oBAAoB,KAAK;IACzB,eAAe,KAAK;IACpB,uBAAuB,KAAK;IAC5B,wBAAwB,KAAK;IAC7B,uBAAuB,KAAK;IAC5B,wBAAwB,KAAK;CAChC"}
@@ -0,0 +1,22 @@
1
+ // (C) 2021-2026 GoodData Corporation
2
+ export const LanguageId = "maql";
3
+ export const diagnosticsSource = LanguageId.toUpperCase();
4
+ export var ErrorCodes;
5
+ (function (ErrorCodes) {
6
+ ErrorCodes[ErrorCodes["InputMismatch"] = 0] = "InputMismatch";
7
+ ErrorCodes[ErrorCodes["NoViableAlternative"] = 1] = "NoViableAlternative";
8
+ ErrorCodes[ErrorCodes["FailedPredicate"] = 2] = "FailedPredicate";
9
+ ErrorCodes[ErrorCodes["UnspecifiedError"] = 3] = "UnspecifiedError";
10
+ ErrorCodes[ErrorCodes["UnrecognizedInput"] = 4] = "UnrecognizedInput";
11
+ ErrorCodes[ErrorCodes["UnterminatedString"] = 5] = "UnterminatedString";
12
+ ErrorCodes[ErrorCodes["UndefinedKeyword"] = 6] = "UndefinedKeyword";
13
+ ErrorCodes[ErrorCodes["InvalidType"] = 7] = "InvalidType";
14
+ ErrorCodes[ErrorCodes["ExtraIdentifiersInObject"] = 8] = "ExtraIdentifiersInObject";
15
+ ErrorCodes[ErrorCodes["ObjectNotFound"] = 9] = "ObjectNotFound";
16
+ ErrorCodes[ErrorCodes["LabelElementNotFound"] = 10] = "LabelElementNotFound";
17
+ ErrorCodes[ErrorCodes["InvalidOperator"] = 11] = "InvalidOperator";
18
+ ErrorCodes[ErrorCodes["SuspiciousStringLiteral"] = 12] = "SuspiciousStringLiteral";
19
+ ErrorCodes[ErrorCodes["ParameterValueNotAllowed"] = 13] = "ParameterValueNotAllowed";
20
+ ErrorCodes[ErrorCodes["ParameterValueUncovered"] = 14] = "ParameterValueUncovered";
21
+ ErrorCodes[ErrorCodes["InvalidLabelElementValue"] = 15] = "InvalidLabelElementValue";
22
+ })(ErrorCodes || (ErrorCodes = {}));
@@ -0,0 +1,9 @@
1
+ import { type DateAttributeGranularity } from "@gooddata/sdk-model";
2
+ /**
3
+ * Checks that the value of a date attribute element has the format the backend expects for the granularity.
4
+ *
5
+ * @returns the expected pattern when the value does not match it, undefined when the value is valid
6
+ * or the granularity is not checked
7
+ */
8
+ export declare function getInvalidDateElementPattern(value: string, granularity: DateAttributeGranularity | undefined): string | undefined;
9
+ //# sourceMappingURL=dateElementFormat.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dateElementFormat.d.ts","sourceRoot":"","sources":["../src/dateElementFormat.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,wBAAwB,EAAE,MAAM,qBAAqB,CAAC;AAuDpE;;;;;GAKG;AACH,wBAAgB,4BAA4B,CACxC,KAAK,EAAE,MAAM,EACb,WAAW,EAAE,wBAAwB,GAAG,SAAS,GAClD,MAAM,GAAG,SAAS,CAMpB"}
@@ -0,0 +1,60 @@
1
+ // (C) 2026 GoodData Corporation
2
+ /**
3
+ * Value patterns the backend expects for date attribute elements used in MAQL, per granularity.
4
+ *
5
+ * Mirrors the backend (gdc-nas) implementation, which is the source of truth:
6
+ * - patterns: `libraries/calq/calcique-lib/src/main/kotlin/generator/model/date/GregorianChronological.kt`
7
+ * and `FiscalChronological.kt` (`pattern` of each granularity object)
8
+ * - regex derivation: `Chronological.valueRegex` in `.../generator/model/date/Chronological.kt`
9
+ * - check: `TypeHandler.checkDateFormat` in `libraries/calq/calcique-lib/src/main/kotlin/interpreter/TypeHandler.kt`
10
+ *
11
+ * The backend regex is deliberately loose (e.g. month `[01]?\d` accepts "13"), and this check must accept
12
+ * exactly the same values, otherwise the editor would reject expressions the backend accepts.
13
+ * Any change on the backend side has to be aligned here manually.
14
+ *
15
+ * Periodical granularities (day of week, month of year, ...) are validated by the backend as integer ranges
16
+ * that partly depend on the workspace configuration; they are not checked here and rely on the backend
17
+ * error returned by the elements query instead.
18
+ */
19
+ const granularityPatterns = {
20
+ "GDC.time.second": "YYYY-MM-DD HH24:MI:SS",
21
+ "GDC.time.minute": "YYYY-MM-DD HH24:MI",
22
+ "GDC.time.hour": "YYYY-MM-DD HH24",
23
+ "GDC.time.date": "YYYY-MM-DD",
24
+ "GDC.time.week_us": "IYYY-IW",
25
+ "GDC.time.month": "YYYY-MM",
26
+ "GDC.time.quarter": "YYYY-Q",
27
+ "GDC.time.year": "YYYY",
28
+ "GDC.time.fiscal_month": "YYYY-MM",
29
+ "GDC.time.fiscal_quarter": "YYYY-Q",
30
+ "GDC.time.fiscal_year": "YYYY",
31
+ };
32
+ // Same replacement order as Chronological.valueRegex on the backend
33
+ const patternTokens = [
34
+ ["YYYY", "(\\d{1,4})"],
35
+ ["IYYY", "(\\d{1,4})"],
36
+ ["Q", "([1-4])"],
37
+ ["MM", "([01]?\\d)"],
38
+ ["IW", "([0-5]?\\d)"],
39
+ ["DD", "([0-3]?\\d)"],
40
+ ["HH24", "([0-2]?\\d)"],
41
+ ["MI", "([0-5]?\\d)"],
42
+ ["SS", "([0-5]?\\d)"],
43
+ ];
44
+ const granularityRegexes = new Map(Object.entries(granularityPatterns).map(([granularity, pattern]) => [
45
+ granularity,
46
+ new RegExp(`^${patternTokens.reduce((regex, [token, replacement]) => regex.replaceAll(token, replacement), pattern)}$`),
47
+ ]));
48
+ /**
49
+ * Checks that the value of a date attribute element has the format the backend expects for the granularity.
50
+ *
51
+ * @returns the expected pattern when the value does not match it, undefined when the value is valid
52
+ * or the granularity is not checked
53
+ */
54
+ export function getInvalidDateElementPattern(value, granularity) {
55
+ if (!granularity || value === "") {
56
+ return undefined; // the backend considers an empty string to be NULL for dates
57
+ }
58
+ const regex = granularityRegexes.get(granularity);
59
+ return regex && !regex.test(value) ? granularityPatterns[granularity] : undefined;
60
+ }
@@ -0,0 +1,39 @@
1
+ import { type MarkupContent, type Range } from "vscode-languageserver";
2
+ import { type ITigerMetadataObject, type LdmObjects } from "./metadata/model.js";
3
+ /**
4
+ * The decorations as defined in this file are heavily inspired by Monaco editor decorations.
5
+ */
6
+ /**
7
+ * A decoration in the model.
8
+ */
9
+ export interface IDecoration {
10
+ /**
11
+ * Range that this decoration covers.
12
+ */
13
+ range: Range;
14
+ /**
15
+ * Options associated with this decoration.
16
+ */
17
+ options: IDecorationOptions;
18
+ }
19
+ /**
20
+ * Options for a decoration.
21
+ */
22
+ export interface IDecorationOptions {
23
+ /**
24
+ * Array of MarkdownString to render as the decoration message.
25
+ */
26
+ hoverMessage?: MarkupContent | MarkupContent[];
27
+ /**
28
+ * If set, text will be injected in the view after the range.
29
+ */
30
+ label: string;
31
+ /**
32
+ * Type of current decorator
33
+ */
34
+ type: DecorationType;
35
+ }
36
+ export type DecorationType = ITigerMetadataObject["tigerType"] | "dateAttribute" | "dateLabel";
37
+ export declare function decorate(query: string, ldmObjects?: LdmObjects): IDecoration[];
38
+ export declare function createDecoration(range: Range, label: string, type: DecorationType): IDecoration;
39
+ //# sourceMappingURL=decorations.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"decorations.d.ts","sourceRoot":"","sources":["../src/decorations.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,aAAa,EAAE,KAAK,KAAK,EAAE,MAAM,uBAAuB,CAAC;AAGvE,OAAO,EACH,KAAK,oBAAoB,EACzB,KAAK,UAAU,EAGlB,MAAM,qBAAqB,CAAC;AAI7B;;GAEG;AAEH;;GAEG;AACH,MAAM,WAAW,WAAW;IACxB;;OAEG;IACH,KAAK,EAAE,KAAK,CAAC;IACb;;OAEG;IACH,OAAO,EAAE,kBAAkB,CAAC;CAC/B;AAED;;GAEG;AACH,MAAM,WAAW,kBAAkB;IAC/B;;OAEG;IACH,YAAY,CAAC,EAAE,aAAa,GAAG,aAAa,EAAE,CAAC;IAC/C;;OAEG;IACH,KAAK,EAAE,MAAM,CAAC;IACd;;OAEG;IACH,IAAI,EAAE,cAAc,CAAC;CACxB;AAED,MAAM,MAAM,cAAc,GAAG,oBAAoB,CAAC,WAAW,CAAC,GAAG,eAAe,GAAG,WAAW,CAAC;AAE/F,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,EAAE,UAAU,CAAC,EAAE,UAAU,GAAG,WAAW,EAAE,CAI9E;AA6BD,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,cAAc,GAAG,WAAW,CAQ/F"}
@@ -0,0 +1,42 @@
1
+ // (C) 2021-2026 GoodData Corporation
2
+ import { findAllObjects } from "./findObjects.js";
3
+ import { isITigerAttribute, isITigerLabel, } from "./metadata/model.js";
4
+ import { MaqlMetric } from "./parseMaql.js";
5
+ export function decorate(query, ldmObjects) {
6
+ const metric = new MaqlMetric(query);
7
+ // decorate objects with business names
8
+ return ldmObjects ? decorateBusinessNames(metric, ldmObjects) : [];
9
+ }
10
+ function decorateBusinessNames(metric, ldmObjects) {
11
+ const foundObjects = findAllObjects(metric);
12
+ return foundObjects
13
+ .map((objectAndRange) => {
14
+ const fullObject = ldmObjects.findObject(objectAndRange);
15
+ if (!fullObject)
16
+ return null;
17
+ return {
18
+ range: objectAndRange.range.toRange(),
19
+ ...fullObject,
20
+ };
21
+ })
22
+ .filter((foundObject) => !!foundObject)
23
+ .map((foundObject) => createDecoration(foundObject.range, foundObject.title, toDecorationType(foundObject)));
24
+ }
25
+ function toDecorationType(object) {
26
+ if (isITigerAttribute(object)) {
27
+ return object.tigerTypeModifier === "date" ? "dateAttribute" : object.tigerType;
28
+ }
29
+ if (isITigerLabel(object)) {
30
+ return object.tigerTypeModifier === "date" ? "dateLabel" : object.tigerType;
31
+ }
32
+ return object.tigerType;
33
+ }
34
+ export function createDecoration(range, label, type) {
35
+ return {
36
+ range,
37
+ options: {
38
+ label,
39
+ type,
40
+ },
41
+ };
42
+ }
@@ -0,0 +1,12 @@
1
+ import { Diagnostic } from "vscode-languageserver";
2
+ import { ErrorCodes } from "./constants.js";
3
+ import { type LabelElementsFunc, type LdmObjects } from "./metadata/model.js";
4
+ interface IErrorDescription {
5
+ message(tokenText?: string): string;
6
+ code: ErrorCodes;
7
+ }
8
+ export declare const errorTokenDescriptions: Map<number, IErrorDescription>;
9
+ export declare const errorTokens: number[];
10
+ export declare function validate(query: string, ldmObjects?: LdmObjects, labelElementsFunc?: LabelElementsFunc): Promise<Diagnostic[]>;
11
+ export {};
12
+ //# sourceMappingURL=diagnostics.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"diagnostics.d.ts","sourceRoot":"","sources":["../src/diagnostics.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,UAAU,EAA6B,MAAM,uBAAuB,CAAC;AAY9E,OAAO,EAAE,UAAU,EAAqB,MAAM,gBAAgB,CAAC;AAI/D,OAAO,EAEH,KAAK,iBAAiB,EACtB,KAAK,UAAU,EAGlB,MAAM,qBAAqB,CAAC;AAO7B,UAAU,iBAAiB;IACvB,OAAO,CAAC,SAAS,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IAEpC,IAAI,EAAE,UAAU,CAAC;CACpB;AAED,eAAO,MAAM,sBAAsB,gCAgDjC,CAAC;AAEH,eAAO,MAAM,WAAW,EAAE,MAAM,EAA8C,CAAC;AAE/E,wBAAsB,QAAQ,CAC1B,KAAK,EAAE,MAAM,EACb,UAAU,CAAC,EAAE,UAAU,EACvB,iBAAiB,CAAC,EAAE,iBAAiB,GACtC,OAAO,CAAC,UAAU,EAAE,CAAC,CAsBvB"}
@@ -0,0 +1,260 @@
1
+ // (C) 2021-2026 GoodData Corporation
2
+ import { DefaultErrorStrategy, FailedPredicateException, InputMismatchException, NoViableAltException, } from "antlr4ts";
3
+ import { groupBy } from "lodash-es";
4
+ import { Diagnostic, DiagnosticSeverity, Range } from "vscode-languageserver";
5
+ import MaqlPkg from "@gooddata/maql-antlr4ts";
6
+ const { AbstractAstVisitor, MaqlLexer, SyntaxErrorListener } = MaqlPkg;
7
+ import { isUnexpectedResponseError } from "@gooddata/sdk-backend-spi";
8
+ import { areObjRefsEqual, serializeObjRef } from "@gooddata/sdk-model";
9
+ import { ErrorCodes, diagnosticsSource } from "./constants.js";
10
+ import { getInvalidDateElementPattern } from "./dateElementFormat.js";
11
+ import { findAllObjects } from "./findObjects.js";
12
+ import { labelElementsFinder } from "./labelElements.js";
13
+ import { isITigerAttribute, isITigerLabel, } from "./metadata/model.js";
14
+ import { validateParameterConstraints } from "./parameterConstraints.js";
15
+ import { MaqlMetric } from "./parseMaql.js";
16
+ import { AntlrRange, defaultRange, tokenRange } from "./tokenRanges.js";
17
+ import { AstTypeChecker } from "./types/typeChecking.js";
18
+ import { TypeModel } from "./types/typeModel.js";
19
+ export const errorTokenDescriptions = new Map([
20
+ [
21
+ MaqlLexer.UnterminatedString,
22
+ {
23
+ message() {
24
+ return "missing '\"' at the end of a string";
25
+ },
26
+ code: ErrorCodes.UnterminatedString,
27
+ },
28
+ ],
29
+ // [
30
+ // // TODO Reuse for "no function definition found"
31
+ // MaqlLexer.Identifier,
32
+ // {
33
+ // message(tokenText: string): string {
34
+ // return `undefined keyword '${tokenText}'`;
35
+ // },
36
+ // code: ErrorCodes.UndefinedKeyword,
37
+ // },
38
+ // ],
39
+ [
40
+ MaqlLexer.ERROR_CHARACTER,
41
+ {
42
+ message(tokenText) {
43
+ return `unexpected character '${tokenText}'`;
44
+ },
45
+ code: ErrorCodes.UnrecognizedInput,
46
+ },
47
+ ],
48
+ [
49
+ MaqlLexer.UNKNOWN_TYPE,
50
+ {
51
+ message(tokenText) {
52
+ return `invalid object type '${tokenText}'`;
53
+ },
54
+ code: ErrorCodes.InvalidType,
55
+ },
56
+ ],
57
+ // [
58
+ // // was removed with top-win identifiers, will probably be reintroduced at some point in the future
59
+ // MaqlLexer.OBJECT_EXTRA_SUFFIX,
60
+ // {
61
+ // message(tokenText: string): string {
62
+ // return `too many identifiers: ${tokenText.slice(1).replace(/\//g, ", ")}`;
63
+ // },
64
+ // code: ErrorCodes.ExtraIdentifiersInObject,
65
+ // },
66
+ // ],
67
+ ]);
68
+ export const errorTokens = Array.from(errorTokenDescriptions.keys());
69
+ export async function validate(query, ldmObjects, labelElementsFunc) {
70
+ const metric = new MaqlMetric(query);
71
+ const parserDiagnostics = validateByParser(metric);
72
+ // If any errors were encountered, go through all tokens and match any error tokens to specific diagnostics
73
+ const lexerDiagnostics = parserDiagnostics.length > 0 ? validateByLexer(metric) : [];
74
+ // Verify that semantic rules are followed
75
+ const semanticDiagnostics = validateSemantics(metric.ast);
76
+ // Verify that objects in the query exist
77
+ const objectsDiagnostics = ldmObjects ? validateObjects(metric, ldmObjects) : [];
78
+ // Verify that strings in the query are valid label elements
79
+ const labelDiagnostics = await validateLabelElements(metric, ldmObjects, labelElementsFunc);
80
+ // Verify types
81
+ const typeDiagnostics = ldmObjects ? validateTypes(metric.ast, ldmObjects) : [];
82
+ const constraintsDiagnostics = ldmObjects ? validateParameterConstraints(metric, ldmObjects) : [];
83
+ return parserDiagnostics.concat(lexerDiagnostics, semanticDiagnostics, typeDiagnostics, objectsDiagnostics, constraintsDiagnostics, labelDiagnostics.flat());
84
+ }
85
+ function validateSemantics(root) {
86
+ const validator = new SemanticValidator();
87
+ return validator.visit(root);
88
+ }
89
+ function validateByParser(metric) {
90
+ const syntaxErrorListener = new SyntaxErrorListener();
91
+ // oxlint-disable-next-line @typescript-eslint/no-unused-expressions
92
+ metric.addErrorListener(syntaxErrorListener).setErrorHandler(new DefaultErrorStrategy()).tree; // parse MAQL
93
+ return syntaxErrorListener.antlrErrors.map((error) => {
94
+ const errorCode = ((parserError) => {
95
+ // only the actual instance of error will match 'true'
96
+ switch (true) {
97
+ case parserError instanceof InputMismatchException:
98
+ return ErrorCodes.InputMismatch;
99
+ case parserError instanceof NoViableAltException:
100
+ return ErrorCodes.NoViableAlternative;
101
+ case parserError instanceof FailedPredicateException:
102
+ return ErrorCodes.FailedPredicate;
103
+ default:
104
+ return ErrorCodes.UnspecifiedError;
105
+ }
106
+ })(error.error);
107
+ const range = error.offendingToken
108
+ ? tokenRange(error.offendingToken)
109
+ : defaultRange(error.position.line, error.position.character);
110
+ return Diagnostic.create(range, error.message, DiagnosticSeverity.Error, errorCode, diagnosticsSource);
111
+ });
112
+ }
113
+ function validateByLexer(metric) {
114
+ return metric.lexer
115
+ .getAllTokens()
116
+ .map((token) => handleErrorToken(token))
117
+ .filter((diagnostic) => !!diagnostic);
118
+ }
119
+ function validateObjects(metric, ldmObjects) {
120
+ const foundObjects = findAllObjects(metric);
121
+ return foundObjects
122
+ .map((foundObject) => {
123
+ const existingObjects = foundObject.tigerType ? ldmObjects.get(foundObject.tigerType) : undefined;
124
+ if (!existingObjects) {
125
+ return Diagnostic.create(foundObject.range.toRange(), `type '${foundObject.actualType}' is not valid`, DiagnosticSeverity.Error, ErrorCodes.InvalidType, diagnosticsSource);
126
+ }
127
+ return existingObjects.find((obj) => areObjRefsEqual(obj.ref, foundObject.ref))
128
+ ? null
129
+ : Diagnostic.create(foundObject.range.toRange(), `${foundObject.tigerType} '${foundObject.id}' not found`, DiagnosticSeverity.Error, ErrorCodes.ObjectNotFound, diagnosticsSource);
130
+ })
131
+ .filter((diagnostic) => !!diagnostic);
132
+ }
133
+ async function validateLabelElements(metric, ldmObjects, labelElementsFunc) {
134
+ if (!ldmObjects && !labelElementsFunc) {
135
+ return [];
136
+ }
137
+ const foundPairs = labelElementsFinder(metric);
138
+ const stringsGrouped = groupBy(foundPairs, (pair) => serializeObjRef(pair[0].ref));
139
+ return Promise.all(Object.entries(stringsGrouped).map(async ([_ref, pairs]) => {
140
+ const label = pairs[0][0]; // all the labels from 'pairs' have the same ref (identity)
141
+ const granularity = getDateGranularity(label, ldmObjects);
142
+ const formatDiagnostics = [];
143
+ const elements = [];
144
+ pairs.forEach(([, element]) => {
145
+ const expectedPattern = getInvalidDateElementPattern(element.string, granularity);
146
+ if (expectedPattern) {
147
+ formatDiagnostics.push(invalidLabelElementDiagnostic(element, `"${element.string}" does not match the format ${expectedPattern} expected by {${label.tigerType}/${label.id}}`));
148
+ }
149
+ else {
150
+ elements.push(element);
151
+ }
152
+ });
153
+ if (!labelElementsFunc || elements.length === 0) {
154
+ return formatDiagnostics; // malformed values are not sent to the backend, it would reject them anyway
155
+ }
156
+ const result = await labelElementsFunc([label], [], { elements: { values: elements.map((element) => element.string) } }, elements.length);
157
+ if (result.rejected.includes(label)) {
158
+ // the query for the label was rejected, only a rejection of the values themselves allows a claim
159
+ return formatDiagnostics.concat(rejectedElementsDiagnostics(elements, result.rejectionReasons?.get(label)));
160
+ }
161
+ if (result.list.elements.length === elements.length) {
162
+ return formatDiagnostics; // all label elements were returned
163
+ }
164
+ const resultElements = result.list.elements.map((element) => element.title);
165
+ return formatDiagnostics.concat(elements
166
+ .map((element) => labelElementInResult(element, label, resultElements))
167
+ .filter((diagnostic) => !!diagnostic));
168
+ }));
169
+ }
170
+ function getDateGranularity(label, ldmObjects) {
171
+ const object = ldmObjects?.findObject(label);
172
+ return object &&
173
+ (isITigerLabel(object) || isITigerAttribute(object)) &&
174
+ object.tigerTypeModifier === "date"
175
+ ? object.granularity
176
+ : undefined;
177
+ }
178
+ /**
179
+ * The backend rejects the elements query with 400 Bad Request when the values are invalid for the label,
180
+ * e.g. a date value in a wrong format for a granularity the client-side check does not cover.
181
+ * Any other failure (network, server error, ...) allows no claim about the values.
182
+ */
183
+ function rejectedElementsDiagnostics(elements, reason) {
184
+ if (!isUnexpectedResponseError(reason) || reason.httpStatus !== 400) {
185
+ return [];
186
+ }
187
+ const responseBody = reason.responseBody;
188
+ const detail = typeof responseBody === "object" &&
189
+ responseBody !== null &&
190
+ "detail" in responseBody &&
191
+ typeof responseBody.detail === "string"
192
+ ? responseBody.detail
193
+ : undefined;
194
+ if (!detail) {
195
+ return [];
196
+ }
197
+ // the backend reports the first offending value, mark it if it can be identified, otherwise mark all of them
198
+ const offending = elements.filter((element) => detail.includes(`'${element.string}'`));
199
+ return (offending.length > 0 ? offending : elements).map((element) => invalidLabelElementDiagnostic(element, detail));
200
+ }
201
+ function invalidLabelElementDiagnostic(element, message) {
202
+ return Diagnostic.create(element.range.toRange(), message, DiagnosticSeverity.Error, ErrorCodes.InvalidLabelElementValue, diagnosticsSource);
203
+ }
204
+ function validateTypes(ast, ldmObjects) {
205
+ const stringLabelIds = ldmObjects.get("label", "regular").map((label) => label.id);
206
+ const dateLabelIds = ldmObjects.get("label", "date").map((label) => label.id);
207
+ const typeChecker = new AstTypeChecker(new TypeModel(stringLabelIds, dateLabelIds));
208
+ typeChecker.visit(ast);
209
+ const typeViolations = typeChecker.typeConstraintsViolations;
210
+ return typeViolations.map((violation) => {
211
+ const range = violation.range
212
+ ? AntlrRange.fromAstRange(violation.range).toRange()
213
+ : Range.create(0, 0, 0, 0);
214
+ return Diagnostic.create(range, violation.message, DiagnosticSeverity.Error, ErrorCodes.InvalidType, diagnosticsSource);
215
+ });
216
+ }
217
+ /**
218
+ * @returns null if "element" is in "resultElements", diagnostic signifying the error otherwise
219
+ */
220
+ function labelElementInResult(element, label, resultElements) {
221
+ return resultElements.includes(element.string)
222
+ ? null
223
+ : Diagnostic.create(element.range.toRange(), `"${element.string}" is not an element of {${label.tigerType}/${label.id}}`, DiagnosticSeverity.Warning, ErrorCodes.LabelElementNotFound, diagnosticsSource);
224
+ }
225
+ class SemanticValidator extends AbstractAstVisitor {
226
+ EQUALITY_OPERATORS = ["=", "<>", "in", "not in"];
227
+ defaultResult() {
228
+ return [];
229
+ }
230
+ aggregateResult(aggregate, nextResult) {
231
+ return aggregate.concat(nextResult);
232
+ }
233
+ visitOperatorNode(node) {
234
+ const childrenResult = this.visitChildren(node);
235
+ if (!this.EQUALITY_OPERATORS.includes(node.type) &&
236
+ node.range !== undefined &&
237
+ // this is only a shallow check, consider expanding the type system for a full check
238
+ node.content.some((operand) => operand.type === "null")) {
239
+ return this.aggregateResult(childrenResult, [
240
+ Diagnostic.create(AntlrRange.fromAstRange(node.range).toRange(), "Only equality operators can be used with NULL", DiagnosticSeverity.Error, ErrorCodes.InvalidOperator),
241
+ ]);
242
+ }
243
+ return childrenResult;
244
+ }
245
+ visitStringLiteralNode(node) {
246
+ if (node.value.toLowerCase() === "null" && node.range) {
247
+ return [
248
+ Diagnostic.create(AntlrRange.fromAstRange(node.range).toRange(), `This is a string literal containing the word "${node.value}". ` +
249
+ "Perhaps you meant the NULL keyword (no quotes)?", DiagnosticSeverity.Warning, ErrorCodes.SuspiciousStringLiteral),
250
+ ];
251
+ }
252
+ return [];
253
+ }
254
+ }
255
+ function handleErrorToken(token) {
256
+ const errorDescription = errorTokenDescriptions.get(token.type);
257
+ if (!errorDescription)
258
+ return;
259
+ return Diagnostic.create(tokenRange(token), errorDescription.message(token.text), DiagnosticSeverity.Error, errorDescription.code, diagnosticsSource);
260
+ }
@@ -0,0 +1,2 @@
1
+ export declare const content = "# APPROXIMATE_COUNT\nUse APPROXIMATE_COUNT to return the approximate number of unique values for an attribute. Because the returned value is a statistical estimate and not an exact figure, this function can increase the processing speed when analyzing large datasets. You can use APPROXIMATE_COUNT anywhere you can use COUNT. The smaller the amount of data to process, the more likely that the returned results of APPROXIMATE_COUNT will match the results of COUNT. \n\n - APPROXIMATE_COUNT is available only for workspaces that use [Vertica](https://www.gooddata.com/developers/cloud-native/doc/hosted/connect-data/create-data-sources/vertica/) Data Sources.\n - APPROXIMATE_COUNT uses the Vertica default behavior for APPROXIMATE_COUNT_DISTINCT. It is not possible to use modifiers.\n - GoodData defaults to COUNT when APPROXIMATE_COUNT is unavailable in a workspace.\n\n## Syntax\n\nAPPROXIMATE_COUNT uses the following syntax:\n\n\n |Form | Syntax | Example|\n |------------------ |------------------------------------------------------------| --------------------------------------------|\n |single parameter |`SELECT APPROXIMATE_COUNT(attribute)` |`SELECT APPROXIMATE_COUNT({attribute/order_id})`|\n |two parameters |`SELECT APPROXIMATE_COUNT(attribute, primary_key)` |`SELECT APPROXIMATE_COUNT({attribute/order_id}, {attribute/campaign_id})`|\n |with USING |`SELECT APPROXIMATE_COUNT(attribute) USING primary_key` |`SELECT APPROXIMATE_COUNT({attribute/order_id}) USING {attribute/campaign_id}`|\n\n\n### Single-Parameter Version\n\nThe single-parameter version of APPROXIMATE_COUNT dynamically gets the context of\nwhere to count from the visualization it is used in.\n\n### Two-Parameter Version\n\nIn the two-parameter version, the context where to count the attribute\nis determined explicitly by the second parameter - the primary key of\nthe dataset.\n\nThe primary key is connection point between datasets. It connects the\nAPPROXIMATE_COUNT function's first parameter to the dataset in which the count is\nto take place.\n\n### Specifying APPROXIMATE_COUNT Context Resolution with USING\n\nIn a metric, USING provides a hint for which context should be used.\nThe context for the computation of APPROXIMATE COUNT may be ambiguous if there are\nmultiple fact datasets in your logical data model that relate to a counted attribute. \n\nThe following image shows a model with the fact datasets `Purchases` and `Sales` and\nhas both datasets connected to the `Store ID` and `Product ID` attributes.\n\n![model for count example](https://www.gooddata.com/developers/cloud-native/doc/maql/count-ldm-using.png)\n\nTo create a metric that resolves with a specific context, you can specify USING in your metric like in the following \nexample: `SELECT COUNT({label/inventory.productid}) USING {label/purchases.purchaseid}`. \n\nWith this example, the visualization will show the approximate number of uniquely purchased products per store \nbecause the attribute `Purchase ID` from the `Purchases` dataset is in the USING clause.\n\nWith the example model, if you build a visualization to display the approximate count of products per store with \n`SELECT COUNT({label/inventory.productid})` and slice it by Store without specifying USING, it is ambiguous whether \nthe visualization is displaying the approximate number of unique products that have been purchased by store or the\napproximate number of unique products that have been sold by the store.\n\nThe attribute in the USING clause can be any attribute which uniquely determines the correct context. For example, you\ncan also use an attribute from the `Purchase Date` dataset in the USING clause. This uses the `Purchases` dataset as \nthe context because the `Sales` dataset has no relationships to `Purchase Date`: \n`SELECT COUNT({label/inventory.productid}) USING {label/purchasedate.year}`";
2
+ //# sourceMappingURL=approximate_count.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"approximate_count.d.ts","sourceRoot":"","sources":["../../../../../../../src/docs/en/docs/create-metrics/maql/aggregation/approximate_count.ts"],"names":[],"mappings":"AAEA,eAAO,MAAM,OAAO,u6HA2D0D,CAAC"}
@@ -0,0 +1,61 @@
1
+ // (C) 2021-2026 GoodData Corporation
2
+ export const content = `# APPROXIMATE_COUNT
3
+ Use APPROXIMATE_COUNT to return the approximate number of unique values for an attribute. Because the returned value is a statistical estimate and not an exact figure, this function can increase the processing speed when analyzing large datasets. You can use APPROXIMATE_COUNT anywhere you can use COUNT. The smaller the amount of data to process, the more likely that the returned results of APPROXIMATE_COUNT will match the results of COUNT.
4
+
5
+ - APPROXIMATE_COUNT is available only for workspaces that use [Vertica](https://www.gooddata.com/developers/cloud-native/doc/hosted/connect-data/create-data-sources/vertica/) Data Sources.
6
+ - APPROXIMATE_COUNT uses the Vertica default behavior for APPROXIMATE_COUNT_DISTINCT. It is not possible to use modifiers.
7
+ - GoodData defaults to COUNT when APPROXIMATE_COUNT is unavailable in a workspace.
8
+
9
+ ## Syntax
10
+
11
+ APPROXIMATE_COUNT uses the following syntax:
12
+
13
+
14
+ |Form | Syntax | Example|
15
+ |------------------ |------------------------------------------------------------| --------------------------------------------|
16
+ |single parameter |\`SELECT APPROXIMATE_COUNT(attribute)\` |\`SELECT APPROXIMATE_COUNT({attribute/order_id})\`|
17
+ |two parameters |\`SELECT APPROXIMATE_COUNT(attribute, primary_key)\` |\`SELECT APPROXIMATE_COUNT({attribute/order_id}, {attribute/campaign_id})\`|
18
+ |with USING |\`SELECT APPROXIMATE_COUNT(attribute) USING primary_key\` |\`SELECT APPROXIMATE_COUNT({attribute/order_id}) USING {attribute/campaign_id}\`|
19
+
20
+
21
+ ### Single-Parameter Version
22
+
23
+ The single-parameter version of APPROXIMATE_COUNT dynamically gets the context of
24
+ where to count from the visualization it is used in.
25
+
26
+ ### Two-Parameter Version
27
+
28
+ In the two-parameter version, the context where to count the attribute
29
+ is determined explicitly by the second parameter - the primary key of
30
+ the dataset.
31
+
32
+ The primary key is connection point between datasets. It connects the
33
+ APPROXIMATE_COUNT function's first parameter to the dataset in which the count is
34
+ to take place.
35
+
36
+ ### Specifying APPROXIMATE_COUNT Context Resolution with USING
37
+
38
+ In a metric, USING provides a hint for which context should be used.
39
+ The context for the computation of APPROXIMATE COUNT may be ambiguous if there are
40
+ multiple fact datasets in your logical data model that relate to a counted attribute.
41
+
42
+ The following image shows a model with the fact datasets \`Purchases\` and \`Sales\` and
43
+ has both datasets connected to the \`Store ID\` and \`Product ID\` attributes.
44
+
45
+ ![model for count example](https://www.gooddata.com/developers/cloud-native/doc/maql/count-ldm-using.png)
46
+
47
+ To create a metric that resolves with a specific context, you can specify USING in your metric like in the following
48
+ example: \`SELECT COUNT({label/inventory.productid}) USING {label/purchases.purchaseid}\`.
49
+
50
+ With this example, the visualization will show the approximate number of uniquely purchased products per store
51
+ because the attribute \`Purchase ID\` from the \`Purchases\` dataset is in the USING clause.
52
+
53
+ With the example model, if you build a visualization to display the approximate count of products per store with
54
+ \`SELECT COUNT({label/inventory.productid})\` and slice it by Store without specifying USING, it is ambiguous whether
55
+ the visualization is displaying the approximate number of unique products that have been purchased by store or the
56
+ approximate number of unique products that have been sold by the store.
57
+
58
+ The attribute in the USING clause can be any attribute which uniquely determines the correct context. For example, you
59
+ can also use an attribute from the \`Purchase Date\` dataset in the USING clause. This uses the \`Purchases\` dataset as
60
+ the context because the \`Sales\` dataset has no relationships to \`Purchase Date\`:
61
+ \`SELECT COUNT({label/inventory.productid}) USING {label/purchasedate.year}\``;