@datarecce/ui 0.1.29 → 0.1.31

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 (601) hide show
  1. package/dist/{RecceCheckContext-fAKHgsGz.js → RecceCheckContext-DPpu9nG5.js} +2 -2
  2. package/dist/{RecceCheckContext-fAKHgsGz.js.map → RecceCheckContext-DPpu9nG5.js.map} +1 -1
  3. package/dist/{RecceCheckContext-PT4-g1bW.mjs → RecceCheckContext-bXdfQLGG.mjs} +2 -2
  4. package/dist/{RecceCheckContext-PT4-g1bW.mjs.map → RecceCheckContext-bXdfQLGG.mjs.map} +1 -1
  5. package/dist/api.d.mts +1 -1
  6. package/dist/api.d.ts +1 -1
  7. package/dist/api.js +4 -3
  8. package/dist/api.mjs +4 -3
  9. package/dist/{components-B9F5oJbK.js → components-B-YxuuPz.js} +66 -65
  10. package/dist/{components-B9F5oJbK.js.map → components-B-YxuuPz.js.map} +1 -1
  11. package/dist/{components-D2DRqJsz.css → components-BeAjVBV3.css} +1 -1
  12. package/dist/{components-D2DRqJsz.css.map → components-BeAjVBV3.css.map} +1 -1
  13. package/dist/{components-gDC1ucjo.mjs → components-DCOI1YlQ.mjs} +8 -7
  14. package/dist/{components-gDC1ucjo.mjs.map → components-DCOI1YlQ.mjs.map} +1 -1
  15. package/dist/{components-dVXbmdqd.css → components-iUxcqtUB.css} +1 -1
  16. package/dist/{components-dVXbmdqd.css.map → components-iUxcqtUB.css.map} +1 -1
  17. package/dist/components.d.mts +1 -1
  18. package/dist/components.d.ts +1 -1
  19. package/dist/components.js +6 -5
  20. package/dist/components.mjs +6 -5
  21. package/dist/{hooks-C2jUJ9EN.js → hooks-B9hsc1oD.js} +3 -3
  22. package/dist/{hooks-C2jUJ9EN.js.map → hooks-B9hsc1oD.js.map} +1 -1
  23. package/dist/{hooks-4hRUjy9Q.mjs → hooks-DjBNmTdh.mjs} +3 -3
  24. package/dist/{hooks-4hRUjy9Q.mjs.map → hooks-DjBNmTdh.mjs.map} +1 -1
  25. package/dist/hooks.d.mts +1 -1
  26. package/dist/hooks.d.ts +1 -1
  27. package/dist/hooks.js +5 -4
  28. package/dist/hooks.mjs +5 -4
  29. package/dist/{html2canvas-pro.esm-BR5xeFe-.mjs → html2canvas-pro.esm-BInzOtWO.mjs} +1 -1
  30. package/dist/{html2canvas-pro.esm-BR5xeFe-.mjs.map → html2canvas-pro.esm-BInzOtWO.mjs.map} +1 -1
  31. package/dist/{html2canvas-pro.esm-CVOsBdk0.js → html2canvas-pro.esm-WJxOmKlq.js} +1 -1
  32. package/dist/{html2canvas-pro.esm-CVOsBdk0.js.map → html2canvas-pro.esm-WJxOmKlq.js.map} +1 -1
  33. package/dist/{index-Bv5R8iLo.d.mts → index-B9lSPJTi.d.ts} +192 -12
  34. package/dist/index-B9lSPJTi.d.ts.map +1 -0
  35. package/dist/{index-CUtFlKOo.d.ts → index-IIXVIoOL.d.mts} +262 -78
  36. package/dist/index-IIXVIoOL.d.mts.map +1 -0
  37. package/dist/index.d.mts +2 -2
  38. package/dist/index.d.ts +2 -2
  39. package/dist/index.js +15 -7
  40. package/dist/index.js.map +1 -1
  41. package/dist/index.mjs +10 -8
  42. package/dist/index.mjs.map +1 -1
  43. package/dist/mui-theme-B2wm_cvZ.js +732 -0
  44. package/dist/mui-theme-B2wm_cvZ.js.map +1 -0
  45. package/dist/mui-theme-CUhybmBq.mjs +696 -0
  46. package/dist/mui-theme-CUhybmBq.mjs.map +1 -0
  47. package/dist/{state-CELzQ0tM.mjs → state-B9yzhuKs.mjs} +5 -694
  48. package/dist/state-B9yzhuKs.mjs.map +1 -0
  49. package/dist/{state-eEsMhIy4.css → state-DOUPNifc.css} +1 -1
  50. package/dist/{state-eEsMhIy4.css.map → state-DOUPNifc.css.map} +1 -1
  51. package/dist/{state-CemiRRon.js → state-lPCQsWy5.js} +24 -737
  52. package/dist/state-lPCQsWy5.js.map +1 -0
  53. package/dist/styles.css +4 -0
  54. package/dist/theme.d.mts +3 -0
  55. package/dist/theme.d.ts +3 -0
  56. package/dist/theme.js +9 -0
  57. package/dist/theme.mjs +4 -0
  58. package/dist/{tooltipMessage-CrXjOmVM.mjs → tooltipMessage-B--I3p1V.mjs} +1 -1
  59. package/dist/{tooltipMessage-CrXjOmVM.mjs.map → tooltipMessage-B--I3p1V.mjs.map} +1 -1
  60. package/dist/{tooltipMessage-Dbi1kkfi.js → tooltipMessage-DosF13kZ.js} +1 -1
  61. package/dist/{tooltipMessage-Dbi1kkfi.js.map → tooltipMessage-DosF13kZ.js.map} +1 -1
  62. package/dist/types.d.mts +1 -1
  63. package/dist/types.d.ts +1 -1
  64. package/dist/types.js +2 -2
  65. package/dist/types.mjs +2 -2
  66. package/dist/{urls-D7PrPolY.mjs → urls-B1Ymdoz-.mjs} +1 -1
  67. package/dist/{urls-D7PrPolY.mjs.map → urls-B1Ymdoz-.mjs.map} +1 -1
  68. package/dist/{urls-SazAekCZ.js → urls-C4eAc82S.js} +1 -1
  69. package/dist/{urls-SazAekCZ.js.map → urls-C4eAc82S.js.map} +1 -1
  70. package/dist/{version-bWg7XwOu.js → version-Dh8sZhvs.js} +2 -2
  71. package/dist/{version-bWg7XwOu.js.map → version-Dh8sZhvs.js.map} +1 -1
  72. package/dist/{version-paZ9esBk.mjs → version-OnOKzBeQ.mjs} +2 -2
  73. package/dist/{version-paZ9esBk.mjs.map → version-OnOKzBeQ.mjs.map} +1 -1
  74. package/package.json +9 -2
  75. package/recce-source/.editorconfig +26 -0
  76. package/recce-source/.flake8 +37 -0
  77. package/recce-source/.github/ISSUE_TEMPLATE/bug_report.yml +67 -0
  78. package/recce-source/.github/ISSUE_TEMPLATE/custom.md +10 -0
  79. package/recce-source/.github/ISSUE_TEMPLATE/feature_request.yml +42 -0
  80. package/recce-source/.github/PULL_REQUEST_TEMPLATE.md +21 -0
  81. package/recce-source/.github/copilot-instructions.md +331 -0
  82. package/recce-source/.github/instructions/backend-instructions.md +541 -0
  83. package/recce-source/.github/instructions/frontend-instructions.md +317 -0
  84. package/recce-source/.github/workflows/build-statics.yaml +72 -0
  85. package/recce-source/.github/workflows/bump.yaml +48 -0
  86. package/recce-source/.github/workflows/integration-tests-cloud.yaml +92 -0
  87. package/recce-source/.github/workflows/integration-tests-sqlmesh.yaml +33 -0
  88. package/recce-source/.github/workflows/integration-tests.yaml +52 -0
  89. package/recce-source/.github/workflows/nightly.yaml +246 -0
  90. package/recce-source/.github/workflows/release.yaml +196 -0
  91. package/recce-source/.github/workflows/tests-js.yaml +58 -0
  92. package/recce-source/.github/workflows/tests-python.yaml +128 -0
  93. package/recce-source/.pre-commit-config.yaml +26 -0
  94. package/recce-source/CLAUDE.md +483 -0
  95. package/recce-source/CODE_OF_CONDUCT.md +128 -0
  96. package/recce-source/CONTRIBUTING.md +107 -0
  97. package/recce-source/LICENSE +201 -0
  98. package/recce-source/Makefile +126 -0
  99. package/recce-source/README.md +182 -0
  100. package/recce-source/RECCE_CLOUD.md +81 -0
  101. package/recce-source/SECURITY.md +25 -0
  102. package/recce-source/docs/PACKAGING.md +340 -0
  103. package/recce-source/docs/README.md +1 -0
  104. package/recce-source/integration_tests/dbt/dbt_project.yml +26 -0
  105. package/recce-source/integration_tests/dbt/models/customers.sql +69 -0
  106. package/recce-source/integration_tests/dbt/models/docs.md +14 -0
  107. package/recce-source/integration_tests/dbt/models/orders.sql +56 -0
  108. package/recce-source/integration_tests/dbt/models/schema.yml +82 -0
  109. package/recce-source/integration_tests/dbt/models/staging/schema.yml +31 -0
  110. package/recce-source/integration_tests/dbt/models/staging/stg_customers.sql +22 -0
  111. package/recce-source/integration_tests/dbt/models/staging/stg_orders.sql +23 -0
  112. package/recce-source/integration_tests/dbt/models/staging/stg_payments.sql +25 -0
  113. package/recce-source/integration_tests/dbt/packages.yml +7 -0
  114. package/recce-source/integration_tests/dbt/profiles.yml +8 -0
  115. package/recce-source/integration_tests/dbt/seeds/raw_customers.csv +101 -0
  116. package/recce-source/integration_tests/dbt/seeds/raw_orders.csv +100 -0
  117. package/recce-source/integration_tests/dbt/seeds/raw_payments.csv +114 -0
  118. package/recce-source/integration_tests/dbt/seeds/raw_statuses.csv +5 -0
  119. package/recce-source/integration_tests/dbt/smoke_test.sh +72 -0
  120. package/recce-source/integration_tests/dbt/smoke_test_cloud.sh +71 -0
  121. package/recce-source/integration_tests/sqlmesh/__init__.py +0 -0
  122. package/recce-source/integration_tests/sqlmesh/audits/assert_item_price_above_zero.sql +9 -0
  123. package/recce-source/integration_tests/sqlmesh/audits/items.sql +7 -0
  124. package/recce-source/integration_tests/sqlmesh/audits/order_items.sql +7 -0
  125. package/recce-source/integration_tests/sqlmesh/config.py +171 -0
  126. package/recce-source/integration_tests/sqlmesh/helper.py +20 -0
  127. package/recce-source/integration_tests/sqlmesh/hooks/__init__.py +0 -0
  128. package/recce-source/integration_tests/sqlmesh/macros/__init__.py +0 -0
  129. package/recce-source/integration_tests/sqlmesh/macros/macros.py +8 -0
  130. package/recce-source/integration_tests/sqlmesh/macros/macros.sql +8 -0
  131. package/recce-source/integration_tests/sqlmesh/macros/utils.py +11 -0
  132. package/recce-source/integration_tests/sqlmesh/metrics/metrics.sql +25 -0
  133. package/recce-source/integration_tests/sqlmesh/models/customer_revenue_by_day.sql +41 -0
  134. package/recce-source/integration_tests/sqlmesh/models/customer_revenue_lifetime.sql +60 -0
  135. package/recce-source/integration_tests/sqlmesh/models/customers.sql +32 -0
  136. package/recce-source/integration_tests/sqlmesh/models/items.py +95 -0
  137. package/recce-source/integration_tests/sqlmesh/models/marketing.sql +15 -0
  138. package/recce-source/integration_tests/sqlmesh/models/order_items.py +95 -0
  139. package/recce-source/integration_tests/sqlmesh/models/orders.py +70 -0
  140. package/recce-source/integration_tests/sqlmesh/models/raw_marketing.py +62 -0
  141. package/recce-source/integration_tests/sqlmesh/models/top_waiters.sql +23 -0
  142. package/recce-source/integration_tests/sqlmesh/models/waiter_as_customer_by_day.sql +29 -0
  143. package/recce-source/integration_tests/sqlmesh/models/waiter_names.sql +10 -0
  144. package/recce-source/integration_tests/sqlmesh/models/waiter_revenue_by_day.sql +29 -0
  145. package/recce-source/integration_tests/sqlmesh/models/waiters.py +62 -0
  146. package/recce-source/integration_tests/sqlmesh/prep_env.sh +16 -0
  147. package/recce-source/integration_tests/sqlmesh/schema.yaml +5 -0
  148. package/recce-source/integration_tests/sqlmesh/seeds/waiter_names.csv +11 -0
  149. package/recce-source/integration_tests/sqlmesh/test_server.sh +29 -0
  150. package/recce-source/integration_tests/sqlmesh/tests/test_customer_revenue_by_day.yaml +63 -0
  151. package/recce-source/integration_tests/sqlmesh/tests/test_order_items.yaml +72 -0
  152. package/recce-source/js/.editorconfig +27 -0
  153. package/recce-source/js/.env.development +5 -0
  154. package/recce-source/js/.husky/pre-commit +29 -0
  155. package/recce-source/js/.nvmrc +1 -0
  156. package/recce-source/js/README.md +39 -0
  157. package/recce-source/js/app/(mainComponents)/DisplayModeToggle.tsx +65 -0
  158. package/recce-source/js/app/(mainComponents)/NavBar.tsx +228 -0
  159. package/recce-source/js/app/(mainComponents)/RecceVersionBadge.tsx +107 -0
  160. package/recce-source/js/app/(mainComponents)/TopBar.tsx +252 -0
  161. package/recce-source/js/app/@lineage/default.tsx +20 -0
  162. package/recce-source/js/app/@lineage/page.tsx +14 -0
  163. package/recce-source/js/app/MainLayout.tsx +170 -0
  164. package/recce-source/js/app/Providers.tsx +49 -0
  165. package/recce-source/js/app/checks/page.tsx +296 -0
  166. package/recce-source/js/app/error.tsx +93 -0
  167. package/recce-source/js/app/favicon.ico +0 -0
  168. package/recce-source/js/app/global-error.tsx +115 -0
  169. package/recce-source/js/app/global.css +82 -0
  170. package/recce-source/js/app/layout.tsx +48 -0
  171. package/recce-source/js/app/lineage/page.tsx +15 -0
  172. package/recce-source/js/app/page.tsx +12 -0
  173. package/recce-source/js/app/query/page.tsx +8 -0
  174. package/recce-source/js/biome.json +313 -0
  175. package/recce-source/js/jest.config.js +34 -0
  176. package/recce-source/js/jest.globals.d.ts +32 -0
  177. package/recce-source/js/jest.setup.js +91 -0
  178. package/recce-source/js/next.config.js +16 -0
  179. package/recce-source/js/package-lock.json +13843 -0
  180. package/recce-source/js/package.json +123 -0
  181. package/recce-source/js/pnpm-lock.yaml +9235 -0
  182. package/recce-source/js/pnpm-workspace.yaml +6 -0
  183. package/recce-source/js/postcss.config.js +5 -0
  184. package/recce-source/js/public/auth_callback.html +68 -0
  185. package/recce-source/js/public/imgs/feedback/thumbs-down.png +0 -0
  186. package/recce-source/js/public/imgs/feedback/thumbs-up.png +0 -0
  187. package/recce-source/js/public/imgs/reload-image.svg +4 -0
  188. package/recce-source/js/public/logo/recce-logo-white.png +0 -0
  189. package/recce-source/js/src/components/AuthModal/AuthModal.tsx +202 -0
  190. package/recce-source/js/src/components/app/AvatarDropdown.tsx +159 -0
  191. package/recce-source/js/src/components/app/EnvInfo.tsx +357 -0
  192. package/recce-source/js/src/components/app/Filename.tsx +388 -0
  193. package/recce-source/js/src/components/app/SetupConnectionPopover.tsx +91 -0
  194. package/recce-source/js/src/components/app/StateExporter.tsx +57 -0
  195. package/recce-source/js/src/components/app/StateImporter.tsx +198 -0
  196. package/recce-source/js/src/components/app/StateSharing.tsx +145 -0
  197. package/recce-source/js/src/components/app/StateSynchronizer.tsx +205 -0
  198. package/recce-source/js/src/components/charts/HistogramChart.tsx +291 -0
  199. package/recce-source/js/src/components/charts/SquareIcon.tsx +51 -0
  200. package/recce-source/js/src/components/charts/TopKSummaryList.tsx +457 -0
  201. package/recce-source/js/src/components/charts/chartTheme.ts +74 -0
  202. package/recce-source/js/src/components/check/CheckBreadcrumb.tsx +97 -0
  203. package/recce-source/js/src/components/check/CheckDescription.tsx +134 -0
  204. package/recce-source/js/src/components/check/CheckDetail.tsx +797 -0
  205. package/recce-source/js/src/components/check/CheckEmptyState.tsx +84 -0
  206. package/recce-source/js/src/components/check/CheckList.tsx +320 -0
  207. package/recce-source/js/src/components/check/LineageDiffView.tsx +32 -0
  208. package/recce-source/js/src/components/check/PresetCheckTemplateView.tsx +48 -0
  209. package/recce-source/js/src/components/check/SchemaDiffView.tsx +290 -0
  210. package/recce-source/js/src/components/check/check.ts +25 -0
  211. package/recce-source/js/src/components/check/timeline/CheckTimeline.tsx +163 -0
  212. package/recce-source/js/src/components/check/timeline/CommentInput.tsx +84 -0
  213. package/recce-source/js/src/components/check/timeline/TimelineEvent.tsx +468 -0
  214. package/recce-source/js/src/components/check/timeline/index.ts +12 -0
  215. package/recce-source/js/src/components/check/utils.ts +12 -0
  216. package/recce-source/js/src/components/data-grid/ScreenshotDataGrid.tsx +333 -0
  217. package/recce-source/js/src/components/data-grid/agGridStyles.css +55 -0
  218. package/recce-source/js/src/components/data-grid/agGridTheme.ts +43 -0
  219. package/recce-source/js/src/components/editor/CodeEditor.tsx +107 -0
  220. package/recce-source/js/src/components/editor/DiffEditor.tsx +162 -0
  221. package/recce-source/js/src/components/editor/index.ts +12 -0
  222. package/recce-source/js/src/components/errorboundary/ErrorBoundary.tsx +87 -0
  223. package/recce-source/js/src/components/histogram/HistogramDiffForm.tsx +147 -0
  224. package/recce-source/js/src/components/histogram/HistogramDiffResultView.tsx +63 -0
  225. package/recce-source/js/src/components/icons/index.tsx +142 -0
  226. package/recce-source/js/src/components/lineage/ActionControl.tsx +63 -0
  227. package/recce-source/js/src/components/lineage/ActionTag.tsx +141 -0
  228. package/recce-source/js/src/components/lineage/ChangeStatusLegend.tsx +46 -0
  229. package/recce-source/js/src/components/lineage/ColumnLevelLineageControl.tsx +327 -0
  230. package/recce-source/js/src/components/lineage/ColumnLevelLineageLegend.tsx +57 -0
  231. package/recce-source/js/src/components/lineage/GraphColumnNode.tsx +199 -0
  232. package/recce-source/js/src/components/lineage/GraphEdge.tsx +59 -0
  233. package/recce-source/js/src/components/lineage/GraphNode.tsx +555 -0
  234. package/recce-source/js/src/components/lineage/LineagePage.tsx +10 -0
  235. package/recce-source/js/src/components/lineage/LineageView.tsx +1384 -0
  236. package/recce-source/js/src/components/lineage/LineageViewContext.tsx +86 -0
  237. package/recce-source/js/src/components/lineage/LineageViewContextMenu.tsx +637 -0
  238. package/recce-source/js/src/components/lineage/LineageViewNotification.tsx +64 -0
  239. package/recce-source/js/src/components/lineage/LineageViewTopBar.tsx +596 -0
  240. package/recce-source/js/src/components/lineage/NodeSqlView.tsx +136 -0
  241. package/recce-source/js/src/components/lineage/NodeTag.tsx +278 -0
  242. package/recce-source/js/src/components/lineage/NodeView.tsx +642 -0
  243. package/recce-source/js/src/components/lineage/SandboxView.tsx +436 -0
  244. package/recce-source/js/src/components/lineage/ServerDisconnectedModalContent.tsx +105 -0
  245. package/recce-source/js/src/components/lineage/SetupConnectionBanner.tsx +52 -0
  246. package/recce-source/js/src/components/lineage/SingleEnvironmentQueryView.tsx +152 -0
  247. package/recce-source/js/src/components/lineage/graph.test.ts +31 -0
  248. package/recce-source/js/src/components/lineage/graph.ts +58 -0
  249. package/recce-source/js/src/components/lineage/lineage.test.ts +169 -0
  250. package/recce-source/js/src/components/lineage/lineage.ts +521 -0
  251. package/recce-source/js/src/components/lineage/styles.css +42 -0
  252. package/recce-source/js/src/components/lineage/styles.tsx +165 -0
  253. package/recce-source/js/src/components/lineage/useMultiNodesAction.ts +352 -0
  254. package/recce-source/js/src/components/lineage/useValueDiffAlertDialog.tsx +108 -0
  255. package/recce-source/js/src/components/onboarding-guide/Notification.tsx +62 -0
  256. package/recce-source/js/src/components/profile/ProfileDiffForm.tsx +134 -0
  257. package/recce-source/js/src/components/profile/ProfileDiffResultView.tsx +245 -0
  258. package/recce-source/js/src/components/query/ChangedOnlyCheckbox.tsx +29 -0
  259. package/recce-source/js/src/components/query/DiffText.tsx +120 -0
  260. package/recce-source/js/src/components/query/QueryDiffResultView.tsx +470 -0
  261. package/recce-source/js/src/components/query/QueryForm.tsx +80 -0
  262. package/recce-source/js/src/components/query/QueryPage.tsx +282 -0
  263. package/recce-source/js/src/components/query/QueryResultView.tsx +180 -0
  264. package/recce-source/js/src/components/query/SetupConnectionGuide.tsx +57 -0
  265. package/recce-source/js/src/components/query/SqlEditor.tsx +245 -0
  266. package/recce-source/js/src/components/query/ToggleSwitch.tsx +84 -0
  267. package/recce-source/js/src/components/query/styles.css +21 -0
  268. package/recce-source/js/src/components/routing/DirectUrlAccess.test.tsx +428 -0
  269. package/recce-source/js/src/components/routing/LineageStatePreservation.test.tsx +311 -0
  270. package/recce-source/js/src/components/routing/Navigation.test.tsx +256 -0
  271. package/recce-source/js/src/components/rowcount/RowCountDiffResultView.tsx +109 -0
  272. package/recce-source/js/src/components/rowcount/delta.ts +11 -0
  273. package/recce-source/js/src/components/run/RunList.tsx +303 -0
  274. package/recce-source/js/src/components/run/RunModal.tsx +191 -0
  275. package/recce-source/js/src/components/run/RunPage.tsx +26 -0
  276. package/recce-source/js/src/components/run/RunResultPane.tsx +454 -0
  277. package/recce-source/js/src/components/run/RunStatusAndDate.tsx +106 -0
  278. package/recce-source/js/src/components/run/RunToolbar.tsx +70 -0
  279. package/recce-source/js/src/components/run/RunView.tsx +196 -0
  280. package/recce-source/js/src/components/run/registry.ts +214 -0
  281. package/recce-source/js/src/components/run/types.ts +14 -0
  282. package/recce-source/js/src/components/schema/ColumnNameCell.test.tsx +169 -0
  283. package/recce-source/js/src/components/schema/ColumnNameCell.tsx +198 -0
  284. package/recce-source/js/src/components/schema/SchemaView.tsx +337 -0
  285. package/recce-source/js/src/components/schema/schemaDiff.ts +32 -0
  286. package/recce-source/js/src/components/schema/style.css +134 -0
  287. package/recce-source/js/src/components/screenshot/ScreenshotBox.tsx +39 -0
  288. package/recce-source/js/src/components/shared/HistoryToggle.tsx +35 -0
  289. package/recce-source/js/src/components/split/Split.tsx +40 -0
  290. package/recce-source/js/src/components/split/styles.css +24 -0
  291. package/recce-source/js/src/components/summary/ChangeSummary.tsx +264 -0
  292. package/recce-source/js/src/components/summary/SchemaSummary.tsx +123 -0
  293. package/recce-source/js/src/components/summary/SummaryView.tsx +29 -0
  294. package/recce-source/js/src/components/timeout/IdleTimeoutBadge.tsx +48 -0
  295. package/recce-source/js/src/components/top-k/TopKDiffForm.tsx +58 -0
  296. package/recce-source/js/src/components/top-k/TopKDiffResultView.tsx +73 -0
  297. package/recce-source/js/src/components/ui/dataGrid/DataFrameColumnGroupHeader.tsx +228 -0
  298. package/recce-source/js/src/components/ui/dataGrid/DataFrameColumnHeader.tsx +113 -0
  299. package/recce-source/js/src/components/ui/dataGrid/defaultRenderCell.tsx +72 -0
  300. package/recce-source/js/src/components/ui/dataGrid/index.ts +23 -0
  301. package/recce-source/js/src/components/ui/dataGrid/inlineRenderCell.test.tsx +607 -0
  302. package/recce-source/js/src/components/ui/dataGrid/inlineRenderCell.tsx +211 -0
  303. package/recce-source/js/src/components/ui/dataGrid/schemaCells.test.tsx +452 -0
  304. package/recce-source/js/src/components/ui/dataGrid/schemaCells.tsx +142 -0
  305. package/recce-source/js/src/components/ui/dataGrid/valueDiffCells.test.tsx +178 -0
  306. package/recce-source/js/src/components/ui/dataGrid/valueDiffCells.tsx +275 -0
  307. package/recce-source/js/src/components/ui/markdown/ExternalLinkConfirmDialog.tsx +134 -0
  308. package/recce-source/js/src/components/ui/markdown/MarkdownContent.tsx +364 -0
  309. package/recce-source/js/src/components/ui/mui/index.ts +13 -0
  310. package/recce-source/js/src/components/ui/mui-provider.tsx +67 -0
  311. package/recce-source/js/src/components/ui/mui-theme.ts +1039 -0
  312. package/recce-source/js/src/components/ui/mui-utils.ts +113 -0
  313. package/recce-source/js/src/components/ui/toaster.tsx +288 -0
  314. package/recce-source/js/src/components/valuediff/ValueDiffDetailResultView.tsx +217 -0
  315. package/recce-source/js/src/components/valuediff/ValueDiffForm.tsx +246 -0
  316. package/recce-source/js/src/components/valuediff/ValueDiffResultView.tsx +82 -0
  317. package/recce-source/js/src/components/valuediff/shared.ts +33 -0
  318. package/recce-source/js/src/constants/tooltipMessage.ts +3 -0
  319. package/recce-source/js/src/constants/urls.ts +1 -0
  320. package/recce-source/js/src/lib/UrlHash.ts +12 -0
  321. package/recce-source/js/src/lib/api/adhocQuery.ts +70 -0
  322. package/recce-source/js/src/lib/api/axiosClient.ts +9 -0
  323. package/recce-source/js/src/lib/api/cacheKeys.ts +13 -0
  324. package/recce-source/js/src/lib/api/checkEvents.ts +252 -0
  325. package/recce-source/js/src/lib/api/checks.ts +129 -0
  326. package/recce-source/js/src/lib/api/cll.ts +53 -0
  327. package/recce-source/js/src/lib/api/connectToCloud.ts +13 -0
  328. package/recce-source/js/src/lib/api/flag.ts +37 -0
  329. package/recce-source/js/src/lib/api/info.ts +198 -0
  330. package/recce-source/js/src/lib/api/instanceInfo.ts +25 -0
  331. package/recce-source/js/src/lib/api/keepAlive.ts +108 -0
  332. package/recce-source/js/src/lib/api/lineagecheck.ts +35 -0
  333. package/recce-source/js/src/lib/api/localStorageKeys.ts +7 -0
  334. package/recce-source/js/src/lib/api/models.ts +59 -0
  335. package/recce-source/js/src/lib/api/profile.ts +65 -0
  336. package/recce-source/js/src/lib/api/rowcount.ts +19 -0
  337. package/recce-source/js/src/lib/api/runs.ts +174 -0
  338. package/recce-source/js/src/lib/api/schemacheck.ts +31 -0
  339. package/recce-source/js/src/lib/api/select.ts +25 -0
  340. package/recce-source/js/src/lib/api/sessionStorageKeys.ts +8 -0
  341. package/recce-source/js/src/lib/api/state.ts +117 -0
  342. package/recce-source/js/src/lib/api/track.ts +281 -0
  343. package/recce-source/js/src/lib/api/types.ts +284 -0
  344. package/recce-source/js/src/lib/api/user.ts +42 -0
  345. package/recce-source/js/src/lib/api/valuediff.ts +46 -0
  346. package/recce-source/js/src/lib/api/version.ts +40 -0
  347. package/recce-source/js/src/lib/const.ts +9 -0
  348. package/recce-source/js/src/lib/dataGrid/crossFunctionConsistency.test.ts +626 -0
  349. package/recce-source/js/src/lib/dataGrid/dataGridFactory.test.ts +2140 -0
  350. package/recce-source/js/src/lib/dataGrid/dataGridFactory.ts +397 -0
  351. package/recce-source/js/src/lib/dataGrid/generators/rowCountUtils.test.ts +132 -0
  352. package/recce-source/js/src/lib/dataGrid/generators/rowCountUtils.ts +126 -0
  353. package/recce-source/js/src/lib/dataGrid/generators/toDataDiffGrid.test.ts +1627 -0
  354. package/recce-source/js/src/lib/dataGrid/generators/toDataDiffGrid.ts +140 -0
  355. package/recce-source/js/src/lib/dataGrid/generators/toDataGrid.ts +67 -0
  356. package/recce-source/js/src/lib/dataGrid/generators/toRowCountDataGrid.test.ts +142 -0
  357. package/recce-source/js/src/lib/dataGrid/generators/toRowCountDataGrid.ts +71 -0
  358. package/recce-source/js/src/lib/dataGrid/generators/toRowCountDiffDataGrid.test.ts +258 -0
  359. package/recce-source/js/src/lib/dataGrid/generators/toRowCountDiffDataGrid.ts +153 -0
  360. package/recce-source/js/src/lib/dataGrid/generators/toSchemaDataGrid.test.ts +951 -0
  361. package/recce-source/js/src/lib/dataGrid/generators/toSchemaDataGrid.ts +221 -0
  362. package/recce-source/js/src/lib/dataGrid/generators/toValueDataGrid.test.ts +395 -0
  363. package/recce-source/js/src/lib/dataGrid/generators/toValueDataGrid.ts +184 -0
  364. package/recce-source/js/src/lib/dataGrid/generators/toValueDiffGrid.test.ts +884 -0
  365. package/recce-source/js/src/lib/dataGrid/generators/toValueDiffGrid.ts +113 -0
  366. package/recce-source/js/src/lib/dataGrid/index.ts +51 -0
  367. package/recce-source/js/src/lib/dataGrid/propertyBased.test.ts +858 -0
  368. package/recce-source/js/src/lib/dataGrid/shared/columnBuilders.test.ts +482 -0
  369. package/recce-source/js/src/lib/dataGrid/shared/columnBuilders.ts +345 -0
  370. package/recce-source/js/src/lib/dataGrid/shared/dataTypeEdgeCases.test.ts +698 -0
  371. package/recce-source/js/src/lib/dataGrid/shared/diffColumnBuilder.test.tsx +820 -0
  372. package/recce-source/js/src/lib/dataGrid/shared/diffColumnBuilder.tsx +277 -0
  373. package/recce-source/js/src/lib/dataGrid/shared/gridUtils.test.ts +785 -0
  374. package/recce-source/js/src/lib/dataGrid/shared/gridUtils.ts +370 -0
  375. package/recce-source/js/src/lib/dataGrid/shared/index.ts +81 -0
  376. package/recce-source/js/src/lib/dataGrid/shared/rowBuilders.test.ts +909 -0
  377. package/recce-source/js/src/lib/dataGrid/shared/rowBuilders.ts +325 -0
  378. package/recce-source/js/src/lib/dataGrid/shared/simpleColumnBuilder.tsx +240 -0
  379. package/recce-source/js/src/lib/dataGrid/shared/toDiffColumn.test.tsx +719 -0
  380. package/recce-source/js/src/lib/dataGrid/shared/toDiffColumn.tsx +231 -0
  381. package/recce-source/js/src/lib/dataGrid/shared/validation.test.ts +559 -0
  382. package/recce-source/js/src/lib/dataGrid/shared/validation.ts +367 -0
  383. package/recce-source/js/src/lib/dataGrid/warehouseNamingConventions.test.ts +1117 -0
  384. package/recce-source/js/src/lib/formatSelect.ts +50 -0
  385. package/recce-source/js/src/lib/hooks/ApiConfigContext.tsx +181 -0
  386. package/recce-source/js/src/lib/hooks/IdleTimeoutContext.tsx +177 -0
  387. package/recce-source/js/src/lib/hooks/LineageGraphContext.tsx +512 -0
  388. package/recce-source/js/src/lib/hooks/RecceActionContext.tsx +269 -0
  389. package/recce-source/js/src/lib/hooks/RecceCheckContext.tsx +33 -0
  390. package/recce-source/js/src/lib/hooks/RecceContextProvider.tsx +54 -0
  391. package/recce-source/js/src/lib/hooks/RecceInstanceContext.tsx +129 -0
  392. package/recce-source/js/src/lib/hooks/RecceQueryContext.tsx +98 -0
  393. package/recce-source/js/src/lib/hooks/RecceShareStateContext.tsx +59 -0
  394. package/recce-source/js/src/lib/hooks/ScreenShot.tsx +399 -0
  395. package/recce-source/js/src/lib/hooks/useAppRouter.test.ts +211 -0
  396. package/recce-source/js/src/lib/hooks/useAppRouter.ts +200 -0
  397. package/recce-source/js/src/lib/hooks/useCheckEvents.ts +99 -0
  398. package/recce-source/js/src/lib/hooks/useCheckToast.tsx +14 -0
  399. package/recce-source/js/src/lib/hooks/useClipBoardToast.tsx +27 -0
  400. package/recce-source/js/src/lib/hooks/useCountdownToast.tsx +102 -0
  401. package/recce-source/js/src/lib/hooks/useFeedbackCollectionToast.tsx +130 -0
  402. package/recce-source/js/src/lib/hooks/useGuideToast.tsx +45 -0
  403. package/recce-source/js/src/lib/hooks/useIdleDetection.tsx +185 -0
  404. package/recce-source/js/src/lib/hooks/useModelColumns.tsx +113 -0
  405. package/recce-source/js/src/lib/hooks/useRecceInstanceInfo.tsx +13 -0
  406. package/recce-source/js/src/lib/hooks/useRecceServerFlag.tsx +13 -0
  407. package/recce-source/js/src/lib/hooks/useRun.tsx +89 -0
  408. package/recce-source/js/src/lib/hooks/useThemeColors.ts +115 -0
  409. package/recce-source/js/src/lib/mergeKeys.test.ts +89 -0
  410. package/recce-source/js/src/lib/mergeKeys.ts +86 -0
  411. package/recce-source/js/src/lib/result/ResultErrorFallback.tsx +9 -0
  412. package/recce-source/js/src/lib/utils/formatTime.ts +84 -0
  413. package/recce-source/js/src/lib/utils/urls.ts +16 -0
  414. package/recce-source/js/src/utils/DropdownValuesInput.tsx +297 -0
  415. package/recce-source/js/src/utils/formatters.tsx +237 -0
  416. package/recce-source/js/src/utils/transforms.ts +81 -0
  417. package/recce-source/js/tsconfig.json +47 -0
  418. package/recce-source/macros/README.md +8 -0
  419. package/recce-source/macros/recce_athena.sql +73 -0
  420. package/recce-source/pyproject.toml +109 -0
  421. package/recce-source/recce/VERSION +1 -0
  422. package/recce-source/recce/__init__.py +84 -0
  423. package/recce-source/recce/adapter/__init__.py +0 -0
  424. package/recce-source/recce/adapter/base.py +109 -0
  425. package/recce-source/recce/adapter/dbt_adapter/__init__.py +1699 -0
  426. package/recce-source/recce/adapter/dbt_adapter/dbt_version.py +42 -0
  427. package/recce-source/recce/adapter/sqlmesh_adapter.py +141 -0
  428. package/recce-source/recce/apis/__init__.py +0 -0
  429. package/recce-source/recce/apis/check_api.py +203 -0
  430. package/recce-source/recce/apis/check_events_api.py +353 -0
  431. package/recce-source/recce/apis/check_func.py +130 -0
  432. package/recce-source/recce/apis/run_api.py +130 -0
  433. package/recce-source/recce/apis/run_func.py +258 -0
  434. package/recce-source/recce/artifact.py +266 -0
  435. package/recce-source/recce/cli.py +1846 -0
  436. package/recce-source/recce/config.py +127 -0
  437. package/recce-source/recce/connect_to_cloud.py +138 -0
  438. package/recce-source/recce/core.py +334 -0
  439. package/recce-source/recce/diff.py +26 -0
  440. package/recce-source/recce/event/CONFIG +1 -0
  441. package/recce-source/recce/event/SENTRY_DNS +1 -0
  442. package/recce-source/recce/event/__init__.py +304 -0
  443. package/recce-source/recce/event/collector.py +184 -0
  444. package/recce-source/recce/event/track.py +158 -0
  445. package/recce-source/recce/exceptions.py +21 -0
  446. package/recce-source/recce/git.py +77 -0
  447. package/recce-source/recce/github.py +222 -0
  448. package/recce-source/recce/mcp_server.py +861 -0
  449. package/recce-source/recce/models/__init__.py +6 -0
  450. package/recce-source/recce/models/check.py +473 -0
  451. package/recce-source/recce/models/run.py +46 -0
  452. package/recce-source/recce/models/types.py +218 -0
  453. package/recce-source/recce/pull_request.py +124 -0
  454. package/recce-source/recce/run.py +390 -0
  455. package/recce-source/recce/server.py +877 -0
  456. package/recce-source/recce/state/__init__.py +31 -0
  457. package/recce-source/recce/state/cloud.py +644 -0
  458. package/recce-source/recce/state/const.py +26 -0
  459. package/recce-source/recce/state/local.py +56 -0
  460. package/recce-source/recce/state/state.py +119 -0
  461. package/recce-source/recce/state/state_loader.py +174 -0
  462. package/recce-source/recce/summary.py +575 -0
  463. package/recce-source/recce/tasks/__init__.py +23 -0
  464. package/recce-source/recce/tasks/core.py +134 -0
  465. package/recce-source/recce/tasks/dataframe.py +170 -0
  466. package/recce-source/recce/tasks/histogram.py +433 -0
  467. package/recce-source/recce/tasks/lineage.py +19 -0
  468. package/recce-source/recce/tasks/profile.py +298 -0
  469. package/recce-source/recce/tasks/query.py +450 -0
  470. package/recce-source/recce/tasks/rowcount.py +277 -0
  471. package/recce-source/recce/tasks/schema.py +65 -0
  472. package/recce-source/recce/tasks/top_k.py +172 -0
  473. package/recce-source/recce/tasks/utils.py +147 -0
  474. package/recce-source/recce/tasks/valuediff.py +497 -0
  475. package/recce-source/recce/util/__init__.py +4 -0
  476. package/recce-source/recce/util/api_token.py +80 -0
  477. package/recce-source/recce/util/breaking.py +330 -0
  478. package/recce-source/recce/util/cache.py +25 -0
  479. package/recce-source/recce/util/cll.py +355 -0
  480. package/recce-source/recce/util/cloud/__init__.py +15 -0
  481. package/recce-source/recce/util/cloud/base.py +115 -0
  482. package/recce-source/recce/util/cloud/check_events.py +190 -0
  483. package/recce-source/recce/util/cloud/checks.py +242 -0
  484. package/recce-source/recce/util/io.py +120 -0
  485. package/recce-source/recce/util/lineage.py +83 -0
  486. package/recce-source/recce/util/logger.py +25 -0
  487. package/recce-source/recce/util/onboarding_state.py +45 -0
  488. package/recce-source/recce/util/perf_tracking.py +85 -0
  489. package/recce-source/recce/util/pydantic_model.py +22 -0
  490. package/recce-source/recce/util/recce_cloud.py +454 -0
  491. package/recce-source/recce/util/singleton.py +18 -0
  492. package/recce-source/recce/util/startup_perf.py +121 -0
  493. package/recce-source/recce/yaml/__init__.py +58 -0
  494. package/recce-source/recce_cloud/README.md +780 -0
  495. package/recce-source/recce_cloud/VERSION +1 -0
  496. package/recce-source/recce_cloud/__init__.py +24 -0
  497. package/recce-source/recce_cloud/api/__init__.py +17 -0
  498. package/recce-source/recce_cloud/api/base.py +132 -0
  499. package/recce-source/recce_cloud/api/client.py +186 -0
  500. package/recce-source/recce_cloud/api/exceptions.py +26 -0
  501. package/recce-source/recce_cloud/api/factory.py +63 -0
  502. package/recce-source/recce_cloud/api/github.py +106 -0
  503. package/recce-source/recce_cloud/api/gitlab.py +111 -0
  504. package/recce-source/recce_cloud/artifact.py +57 -0
  505. package/recce-source/recce_cloud/ci_providers/__init__.py +9 -0
  506. package/recce-source/recce_cloud/ci_providers/base.py +82 -0
  507. package/recce-source/recce_cloud/ci_providers/detector.py +147 -0
  508. package/recce-source/recce_cloud/ci_providers/github_actions.py +136 -0
  509. package/recce-source/recce_cloud/ci_providers/gitlab_ci.py +130 -0
  510. package/recce-source/recce_cloud/cli.py +434 -0
  511. package/recce-source/recce_cloud/download.py +230 -0
  512. package/recce-source/recce_cloud/hatch_build.py +20 -0
  513. package/recce-source/recce_cloud/pyproject.toml +49 -0
  514. package/recce-source/recce_cloud/upload.py +214 -0
  515. package/recce-source/test.py +0 -0
  516. package/recce-source/tests/__init__.py +0 -0
  517. package/recce-source/tests/adapter/__init__.py +0 -0
  518. package/recce-source/tests/adapter/dbt_adapter/__init__.py +0 -0
  519. package/recce-source/tests/adapter/dbt_adapter/conftest.py +17 -0
  520. package/recce-source/tests/adapter/dbt_adapter/dbt_test_helper.py +298 -0
  521. package/recce-source/tests/adapter/dbt_adapter/test_dbt_adapter.py +25 -0
  522. package/recce-source/tests/adapter/dbt_adapter/test_dbt_cll.py +717 -0
  523. package/recce-source/tests/adapter/dbt_adapter/test_proj/dbt_project.yml +4 -0
  524. package/recce-source/tests/adapter/dbt_adapter/test_proj/manifest.json +1 -0
  525. package/recce-source/tests/adapter/dbt_adapter/test_proj/package-lock.yml +8 -0
  526. package/recce-source/tests/adapter/dbt_adapter/test_proj/packages.yml +7 -0
  527. package/recce-source/tests/adapter/dbt_adapter/test_proj/profiles.yml +6 -0
  528. package/recce-source/tests/adapter/dbt_adapter/test_selector.py +205 -0
  529. package/recce-source/tests/apis/__init__.py +0 -0
  530. package/recce-source/tests/apis/row_count_diff.json +59 -0
  531. package/recce-source/tests/apis/test_check_events_api.py +615 -0
  532. package/recce-source/tests/apis/test_run_func.py +433 -0
  533. package/recce-source/tests/catalog.json +527 -0
  534. package/recce-source/tests/data/manifest/base/catalog.json +1 -0
  535. package/recce-source/tests/data/manifest/base/manifest.json +1 -0
  536. package/recce-source/tests/data/manifest/pr2/catalog.json +1 -0
  537. package/recce-source/tests/data/manifest/pr2/manifest.json +1 -0
  538. package/recce-source/tests/manifest.json +10655 -0
  539. package/recce-source/tests/models/__init__.py +0 -0
  540. package/recce-source/tests/models/test_check.py +731 -0
  541. package/recce-source/tests/models/test_run_models.py +295 -0
  542. package/recce-source/tests/recce_cloud/__init__.py +0 -0
  543. package/recce-source/tests/recce_cloud/test_ci_providers.py +351 -0
  544. package/recce-source/tests/recce_cloud/test_cli.py +735 -0
  545. package/recce-source/tests/recce_cloud/test_client.py +379 -0
  546. package/recce-source/tests/recce_cloud/test_platform_clients.py +483 -0
  547. package/recce-source/tests/recce_state.json +1 -0
  548. package/recce-source/tests/state/test_cloud.py +719 -0
  549. package/recce-source/tests/state/test_local.py +164 -0
  550. package/recce-source/tests/state/test_state_loader.py +211 -0
  551. package/recce-source/tests/tasks/__init__.py +0 -0
  552. package/recce-source/tests/tasks/conftest.py +4 -0
  553. package/recce-source/tests/tasks/test_histogram.py +129 -0
  554. package/recce-source/tests/tasks/test_lineage.py +55 -0
  555. package/recce-source/tests/tasks/test_preset_checks.py +64 -0
  556. package/recce-source/tests/tasks/test_profile.py +397 -0
  557. package/recce-source/tests/tasks/test_query.py +528 -0
  558. package/recce-source/tests/tasks/test_row_count.py +133 -0
  559. package/recce-source/tests/tasks/test_schema.py +122 -0
  560. package/recce-source/tests/tasks/test_top_k.py +77 -0
  561. package/recce-source/tests/tasks/test_utils.py +439 -0
  562. package/recce-source/tests/tasks/test_valuediff.py +361 -0
  563. package/recce-source/tests/test_cli.py +236 -0
  564. package/recce-source/tests/test_cli_mcp_optional.py +45 -0
  565. package/recce-source/tests/test_cloud_listing_cli.py +324 -0
  566. package/recce-source/tests/test_config.py +43 -0
  567. package/recce-source/tests/test_connect_to_cloud.py +82 -0
  568. package/recce-source/tests/test_core.py +174 -0
  569. package/recce-source/tests/test_dbt.py +36 -0
  570. package/recce-source/tests/test_mcp_server.py +505 -0
  571. package/recce-source/tests/test_pull_request.py +130 -0
  572. package/recce-source/tests/test_server.py +202 -0
  573. package/recce-source/tests/test_server_lifespan.py +138 -0
  574. package/recce-source/tests/test_summary.py +73 -0
  575. package/recce-source/tests/util/__init__.py +0 -0
  576. package/recce-source/tests/util/cloud/__init__.py +0 -0
  577. package/recce-source/tests/util/cloud/test_check_events.py +255 -0
  578. package/recce-source/tests/util/cloud/test_checks.py +204 -0
  579. package/recce-source/tests/util/test_api_token.py +119 -0
  580. package/recce-source/tests/util/test_breaking.py +1427 -0
  581. package/recce-source/tests/util/test_cll.py +706 -0
  582. package/recce-source/tests/util/test_lineage.py +122 -0
  583. package/recce-source/tests/util/test_onboarding_state.py +84 -0
  584. package/recce-source/tests/util/test_recce_cloud.py +231 -0
  585. package/recce-source/tox.ini +40 -0
  586. package/recce-source/uv.lock +3928 -0
  587. package/src/api/index.ts +32 -0
  588. package/src/components/index.ts +154 -0
  589. package/src/global.d.ts +14 -0
  590. package/src/hooks/index.ts +56 -0
  591. package/src/index.ts +17 -0
  592. package/src/lib/hooks/RouteConfigContext.ts +139 -0
  593. package/src/lib/hooks/useAppRouter.ts +240 -0
  594. package/src/mui-augmentation.d.ts +139 -0
  595. package/src/theme/index.ts +13 -0
  596. package/src/theme.ts +23 -0
  597. package/src/types/index.ts +23 -0
  598. package/dist/index-Bv5R8iLo.d.mts.map +0 -1
  599. package/dist/index-CUtFlKOo.d.ts.map +0 -1
  600. package/dist/state-CELzQ0tM.mjs.map +0 -1
  601. package/dist/state-CemiRRon.js.map +0 -1
@@ -0,0 +1,575 @@
1
+ import os
2
+ import sys
3
+ from typing import Dict, List, Optional, Set, Type, Union
4
+ from uuid import UUID
5
+
6
+ from pydantic import BaseModel
7
+
8
+ from recce.apis.check_func import get_node_name_by_id
9
+ from recce.core import RecceContext
10
+ from recce.models import CheckDAO, Run, RunDAO, RunType
11
+ from recce.tasks.core import TaskResultDiffer
12
+ from recce.tasks.histogram import HistogramDiffTaskResultDiffer
13
+ from recce.tasks.profile import ProfileDiffResultDiffer
14
+ from recce.tasks.query import QueryDiffResultDiffer
15
+ from recce.tasks.rowcount import RowCountDiffResultDiffer
16
+ from recce.tasks.schema import SchemaDiffResultDiffer
17
+ from recce.tasks.top_k import TopKDiffTaskResultDiffer
18
+ from recce.tasks.valuediff import (
19
+ ValueDiffDetailTaskResultDiffer,
20
+ ValueDiffTaskResultDiffer,
21
+ )
22
+
23
+ RECCE_CLOUD_HOST = os.environ.get("RECCE_CLOUD_HOST", "https://cloud.datarecce.io")
24
+
25
+ ADD_COLOR = "#1dce00"
26
+ MODIFIED_COLOR = "#ffa502"
27
+ REMOVE_COLOR = "#ff067e"
28
+
29
+ MAX_MERMAID_TEXT_SIZE = 50000 # source: https://mermaid.js.org/config/schema-docs/config.html#maxtextsize
30
+
31
+
32
+ def _warn(msg):
33
+ # print to stderr
34
+ print(f"warning: {msg}", file=sys.stderr)
35
+
36
+
37
+ class Node:
38
+ id: str
39
+ name: str
40
+ data_from: str
41
+ resource_type: str
42
+ package_name: str
43
+ parents: List[str]
44
+ children: List[str]
45
+ base_data: dict
46
+ current_data: dict
47
+
48
+ def __init__(self, node_id: str, node_data: dict, data_from: str = "base"):
49
+ self.id = node_id
50
+ self.name = node_data["name"]
51
+ self.data_from = data_from
52
+ self.resource_type = node_data["resource_type"]
53
+ self.package_name = node_data["package_name"]
54
+ self.children = []
55
+ self.parents = []
56
+
57
+ self.base_data = {}
58
+ self.current_data = {}
59
+
60
+ if data_from == "base":
61
+ self.base_data = node_data
62
+ elif data_from == "current":
63
+ self.current_data = node_data
64
+
65
+ @property
66
+ def change_status(self):
67
+ base_checksum = self.base_data.get("checksum", {}).get("checksum")
68
+ curr_checksum = self.current_data.get("checksum", {}).get("checksum")
69
+ if self.data_from == "base":
70
+ return "removed"
71
+ elif self.data_from == "current":
72
+ return "added"
73
+ elif base_checksum and curr_checksum and base_checksum != curr_checksum:
74
+ return "modified"
75
+ return None
76
+
77
+ def update_data(self, node_data: dict, data_from: str):
78
+ if data_from not in ["base", "current"]:
79
+ raise ValueError(f"Invalid data_from value: {data_from}")
80
+ if self.data_from != data_from:
81
+ self.data_from = "both"
82
+
83
+ if data_from == "base":
84
+ self.base_data = node_data
85
+ elif data_from == "current":
86
+ self.current_data = node_data
87
+
88
+ def append_parent(self, parent_id: str):
89
+ if parent_id not in self.parents:
90
+ self.parents.append(parent_id)
91
+
92
+ def append_child(self, child_id: str):
93
+ if child_id not in self.children:
94
+ self.children.append(child_id)
95
+
96
+ def _cal_row_count_delta_percentage(self):
97
+ row_count_diff, run_result = _get_node_row_count_diff(self.id, self.name)
98
+ if row_count_diff:
99
+ base = run_result.get("base", 0)
100
+ current = run_result.get("curr", 0)
101
+ if int(current) > int(base):
102
+ p = (int(current) - int(base)) / int(current) * 100
103
+ return f'🔼 +{round(p, 2) if p > 0.1 else "<0.1"}%'
104
+ else:
105
+ p = (int(base) - int(current)) / int(current) * 100
106
+ return f'🔽 -{round(p, 2) if p > 0.1 else "<0.1"}%'
107
+ return None
108
+
109
+ def _get_schema_diff(self):
110
+ base_schema = self.base_data.get("columns", {})
111
+ current_schema = self.current_data.get("columns", {})
112
+ schema_diff = TaskResultDiffer.diff(base_schema, current_schema)
113
+ return schema_diff
114
+
115
+ def _what_changed(self, checks=None):
116
+ changes = []
117
+ if self.change_status == "added":
118
+ return ["Added Node"]
119
+ elif self.change_status == "removed":
120
+ return ["Removed Node"]
121
+ elif self.change_status == "modified":
122
+ changes.append("Code")
123
+ row_count_delta_percentage = self._cal_row_count_delta_percentage()
124
+ if row_count_delta_percentage:
125
+ changes.append(f"Row Count {row_count_delta_percentage}")
126
+ schema_diff = self._get_schema_diff()
127
+ if schema_diff:
128
+ changes.append("Schema")
129
+
130
+ if checks:
131
+ for check in checks:
132
+ check_type = check.type
133
+ if check_type == RunType.ROW_COUNT_DIFF or check_type == RunType.SCHEMA_DIFF:
134
+ # Skip the row count and schema diff check, since we already have it.
135
+ continue
136
+ if check.node_ids and self.id in check.node_ids:
137
+ changes.append(str(check.type).replace("_", " ").title())
138
+ return changes
139
+
140
+ def get_node_str(self, checks=None):
141
+ is_changed = False
142
+ style = None
143
+
144
+ if self.change_status is not None:
145
+ is_changed = True
146
+ if self.change_status == "added":
147
+ style = f"style {self.id} stroke:{ADD_COLOR}"
148
+ elif self.change_status == "modified":
149
+ style = f"style {self.id} stroke:{MODIFIED_COLOR}"
150
+ elif self.change_status == "removed":
151
+ style = f"style {self.id} stroke:{REMOVE_COLOR}"
152
+
153
+ if checks:
154
+ for check in checks:
155
+ if check.node_ids and self.id in check.node_ids:
156
+ is_changed = True
157
+
158
+ content_output = f'{self.id}["{self.name}'
159
+ if is_changed:
160
+ content_output += "\n\n[What's Changed]\n"
161
+ changes = self._what_changed(checks)
162
+ content_output += ", ".join(changes)
163
+
164
+ content_output += '"]\n'
165
+ if style:
166
+ content_output += f"{style}\n"
167
+ return content_output
168
+
169
+
170
+ class Edge:
171
+ id: str
172
+ edge_from: str
173
+ child_id: str
174
+ parent_id: str
175
+ change_status: Union[str, None]
176
+
177
+ def __init__(self, edge_id: str, parent_id: str, child_id: str, edge_from: str = "base"):
178
+ self.id = edge_id
179
+ self.edge_from = edge_from
180
+ self.child_id = child_id
181
+ self.parent_id = parent_id
182
+
183
+ def update_edge_from(self, edge_from: str):
184
+ if self.edge_from != edge_from:
185
+ self.edge_from = "both"
186
+
187
+
188
+ class CheckSummary(BaseModel):
189
+ id: UUID
190
+ type: RunType
191
+ name: str
192
+ description: str
193
+ changes: dict
194
+ node_ids: Optional[List[str]]
195
+ changed_nodes: Optional[List[str]]
196
+
197
+ @property
198
+ def related_nodes(self):
199
+ nodes = []
200
+
201
+ for node_id in self.node_ids or []:
202
+ name = get_node_name_by_id(node_id)
203
+ nodes.append(name)
204
+
205
+ return nodes
206
+
207
+
208
+ check_result_differ_registry: Dict[RunType, Type[TaskResultDiffer]] = {
209
+ RunType.VALUE_DIFF: ValueDiffTaskResultDiffer,
210
+ RunType.VALUE_DIFF_DETAIL: ValueDiffDetailTaskResultDiffer,
211
+ RunType.ROW_COUNT_DIFF: RowCountDiffResultDiffer,
212
+ RunType.QUERY_DIFF: QueryDiffResultDiffer,
213
+ RunType.TOP_K_DIFF: TopKDiffTaskResultDiffer,
214
+ RunType.HISTOGRAM_DIFF: HistogramDiffTaskResultDiffer,
215
+ RunType.PROFILE_DIFF: ProfileDiffResultDiffer,
216
+ }
217
+
218
+
219
+ def differ_factory(run: Run):
220
+ differ_clz = check_result_differ_registry.get(run.type)
221
+ if not differ_clz:
222
+ raise NotImplementedError()
223
+ return differ_clz(run)
224
+
225
+
226
+ class LineageGraph:
227
+ nodes: Dict[str, Node] = {}
228
+ edges: Dict[str, Edge] = {}
229
+ checks: List[CheckSummary] = None
230
+
231
+ def create_node(self, node_id: str, node_data: dict, data_from: str = "base"):
232
+ if node_id not in self.nodes:
233
+ self.nodes[node_id] = Node(node_id, node_data, data_from)
234
+ else:
235
+ self.nodes[node_id].update_data(node_data, data_from)
236
+
237
+ def create_edge(self, parent_id: str, child_id: str, edge_from: str = "base"):
238
+ if parent_id not in self.nodes:
239
+ _warn(f"Parent node {parent_id} not found in graph")
240
+ return
241
+ if child_id not in self.nodes:
242
+ _warn(f"Child node {child_id} not found in graph")
243
+ return
244
+
245
+ edge_id = f"{parent_id}-->{child_id}"
246
+ if edge_id in self.edges:
247
+ self.edges[edge_id].update_edge_from(edge_from)
248
+ else:
249
+ self.edges[edge_id] = Edge(edge_id, parent_id, child_id, edge_from)
250
+ self.nodes[parent_id].append_child(child_id)
251
+ self.nodes[child_id].append_parent(parent_id)
252
+
253
+ @property
254
+ def modified_set(self) -> Set[str]:
255
+ return set(
256
+ [node_id for node_id, node in self.nodes.items() if node.change_status in ["added", "removed", "modified"]]
257
+ )
258
+
259
+ def get_edge_str(self, edge_id):
260
+ edge = self.edges[edge_id]
261
+ child = self.nodes[edge.child_id]
262
+
263
+ if child.change_status == "removed":
264
+ return f"{edge.parent_id}-.->{edge.child_id}\n"
265
+ if child.change_status is None or child.change_status == "modified":
266
+ return f"{edge.parent_id}---->{edge.child_id}\n"
267
+ if child.change_status == "added":
268
+ return f"{edge.parent_id}-...->{edge.child_id}\n"
269
+
270
+
271
+ def _build_lineage_graph(base, current) -> LineageGraph:
272
+ graph = LineageGraph()
273
+
274
+ # Get the current package name to filter nodes (from the current manifest metadata)
275
+ package_name = None
276
+ manifest_metadata = current.get("manifest_metadata")
277
+ if manifest_metadata and hasattr(manifest_metadata, "project_name"):
278
+ # The default package name is the project name
279
+ package_name = manifest_metadata.project_name
280
+
281
+ # Init Graph nodes with base & current nodes
282
+ for node_id, node_data in base.get("nodes", {}).items():
283
+ # Skip nodes that are not from the current package
284
+ if package_name and node_data.get("package_name") != package_name:
285
+ continue
286
+ graph.create_node(node_id, node_data, "base")
287
+
288
+ for node_id, node_data in current.get("nodes", {}).items():
289
+ # Skip nodes that are not from the current package
290
+ if package_name and node_data.get("package_name") != package_name:
291
+ continue
292
+ if node_id not in graph.nodes:
293
+ node = Node(node_id, node_data, "current")
294
+ graph.nodes[node_id] = node
295
+ else:
296
+ node = graph.nodes[node_id]
297
+ node.update_data(node_data, "current")
298
+
299
+ # Build edges
300
+ for child_id, parents in base.get("parent_map", {}).items():
301
+ for parent_id in parents:
302
+ if child_id not in graph.nodes or parent_id not in graph.nodes:
303
+ continue
304
+
305
+ graph.create_edge(parent_id, child_id, "base")
306
+ for child_id, parents in current.get("parent_map", {}).items():
307
+ for parent_id in parents:
308
+ if child_id not in graph.nodes or parent_id not in graph.nodes:
309
+ continue
310
+
311
+ graph.create_edge(parent_id, child_id, "current")
312
+
313
+ return graph
314
+
315
+
316
+ def _build_node_schema(lineage, node_id):
317
+ return lineage.get("nodes", {}).get(node_id, {}).get("columns", {})
318
+
319
+
320
+ def _get_node_row_count_diff(node_id, node_name):
321
+ row_count_runs = RunDAO().list(type_filter=RunType.ROW_COUNT_DIFF)
322
+ for run in row_count_runs:
323
+ node_ids = (run.params or {}).get("node_ids") or []
324
+ if node_id in node_ids:
325
+ result = run.result.get(node_name, {})
326
+ diff = TaskResultDiffer.diff(result.get("base"), result.get("curr"))
327
+ return diff, result
328
+ elif run.params.get("node_id") == node_id:
329
+ result = run.result.get(node_name, {})
330
+ diff = TaskResultDiffer.diff(result.get("base"), result.get("curr"))
331
+ return diff, result
332
+ return None, None
333
+
334
+
335
+ def _generate_mismatched_nodes_summary(check: CheckSummary, limit: int = 3) -> str:
336
+ if not check.related_nodes:
337
+ return "N/A"
338
+
339
+ nodes = check.related_nodes
340
+ if check.changed_nodes:
341
+ # the mismatch nodes within the related nodes (when apply node selection)
342
+ # currently only schema_diff and row_count_diff are supported to apply node selection
343
+ nodes = check.changed_nodes
344
+
345
+ if len(nodes) <= limit:
346
+ return ", ".join(nodes)
347
+
348
+ display_nodes = nodes[: limit - 1]
349
+ return ", ".join(display_nodes) + f", and {len(nodes) - len(display_nodes)} more nodes"
350
+
351
+
352
+ def generate_summary_metadata(base_lineage, curr_lineage):
353
+ from py_markdown_table.markdown_table import markdown_table
354
+
355
+ base_manifest = base_lineage.get("manifest_metadata")
356
+ base_catalog = base_lineage.get("catalog_metadata")
357
+ curr_manifest = curr_lineage.get("manifest_metadata")
358
+ curr_catalog = curr_lineage.get("catalog_metadata")
359
+
360
+ metadata = [
361
+ {
362
+ "": "Base",
363
+ "Manifest": base_manifest.generated_at.strftime("%Y-%m-%d %H:%M:%S"),
364
+ "Catalog": base_catalog.generated_at.strftime("%Y-%m-%d %H:%M:%S") if base_catalog else "N/A",
365
+ },
366
+ {
367
+ "": "Current",
368
+ "Manifest": curr_manifest.generated_at.strftime("%Y-%m-%d %H:%M:%S"),
369
+ "Catalog": curr_catalog.generated_at.strftime("%Y-%m-%d %H:%M:%S") if curr_catalog else "N/A",
370
+ },
371
+ ]
372
+
373
+ return (
374
+ markdown_table(metadata)
375
+ .set_params(
376
+ quote=False,
377
+ row_sep="markdown",
378
+ padding_width=1,
379
+ padding_weight="right", # Aligns the cell's contents to the beginning of the cell
380
+ )
381
+ .get_markdown()
382
+ )
383
+
384
+
385
+ def generate_check_summary(base_lineage, curr_lineage) -> (List[CheckSummary], Dict[str, int]):
386
+ runs = RunDAO().list()
387
+ checks = CheckDAO().list()
388
+ checks_summary: List[CheckSummary] = []
389
+ failed_checks_count = 0
390
+
391
+ # TODO: find a way to count failed checks, currently the state file won't include failed checks
392
+
393
+ def _find_run_by_check_id(check_id):
394
+ runs_for_check = [r for r in runs if str(check_id) == str(r.check_id)]
395
+ if runs_for_check:
396
+ return runs_for_check[-1]
397
+ return None
398
+
399
+ for check in checks:
400
+ run = _find_run_by_check_id(check.check_id)
401
+ differ = None
402
+ if run is not None and run.error is not None:
403
+ failed_checks_count += 1
404
+ continue
405
+ elif check.type == RunType.SCHEMA_DIFF:
406
+ differ = SchemaDiffResultDiffer(check, base_lineage, curr_lineage)
407
+ elif (
408
+ check.type
409
+ in [
410
+ RunType.ROW_COUNT_DIFF,
411
+ RunType.QUERY_DIFF,
412
+ RunType.VALUE_DIFF,
413
+ RunType.VALUE_DIFF_DETAIL,
414
+ RunType.PROFILE_DIFF,
415
+ RunType.TOP_K_DIFF,
416
+ RunType.HISTOGRAM_DIFF,
417
+ ]
418
+ and run is not None
419
+ ):
420
+ # Check the result is changed or not
421
+ differ = differ_factory(run)
422
+
423
+ if differ and differ.changes is not None:
424
+ checks_summary.append(
425
+ CheckSummary(
426
+ id=check.check_id,
427
+ type=check.type,
428
+ name=check.name,
429
+ description=check.description,
430
+ changes=differ.changes,
431
+ node_ids=differ.related_node_ids,
432
+ changed_nodes=differ.changed_nodes,
433
+ )
434
+ )
435
+
436
+ return checks_summary, {
437
+ "total": len(checks),
438
+ "mismatch": len(checks_summary),
439
+ "failed": failed_checks_count,
440
+ }
441
+
442
+
443
+ def generate_mermaid_lineage_graph(graph: LineageGraph):
444
+ content = up_to_level_content = "graph LR\n"
445
+ is_not_modified = False
446
+ # Only show the modified nodes and there children
447
+ queue = list(graph.modified_set)
448
+ display_nodes = set()
449
+ display_edge = set()
450
+
451
+ if len(queue) == 0:
452
+ is_not_modified = True
453
+
454
+ while len(queue) > 0:
455
+
456
+ level_nodes = len(queue)
457
+ for _ in range(level_nodes):
458
+ node_id = queue.pop(0)
459
+ if node_id in display_nodes:
460
+ # Skip if already displayed
461
+ continue
462
+
463
+ display_nodes.add(node_id)
464
+ node = graph.nodes[node_id]
465
+ content += node.get_node_str(graph.checks)
466
+ for child_id in node.children:
467
+ queue.append(child_id)
468
+ edge_id = f"{node_id}-->{child_id}"
469
+ if edge_id not in display_edge:
470
+ display_edge.add(edge_id)
471
+ content += graph.get_edge_str(edge_id)
472
+
473
+ if len(content) > MAX_MERMAID_TEXT_SIZE:
474
+ break
475
+
476
+ up_to_level_content = content
477
+
478
+ return up_to_level_content, is_not_modified, len(content) > MAX_MERMAID_TEXT_SIZE
479
+
480
+
481
+ def generate_markdown_summary(ctx: RecceContext, summary_format: str = "markdown"):
482
+ lineage_diff = ctx.get_lineage_diff()
483
+ summary_metadata = generate_summary_metadata(lineage_diff.base, lineage_diff.current)
484
+ graph = _build_lineage_graph(lineage_diff.base, lineage_diff.current)
485
+ graph.checks, check_statistics = generate_check_summary(lineage_diff.base, lineage_diff.current)
486
+ mermaid_content, is_empty_graph, is_partial_graph = generate_mermaid_lineage_graph(graph)
487
+ check_content = generate_check_content(graph, check_statistics)
488
+
489
+ if summary_format == "mermaid":
490
+ return mermaid_content
491
+ elif summary_format == "check":
492
+ return check_content
493
+ elif summary_format == "markdown":
494
+
495
+ content = "# Recce Summary\n"
496
+ content += f"## Manifest Information\n{summary_metadata}\n"
497
+
498
+ if is_empty_graph is False:
499
+ content += f"""
500
+ ## Lineage Graph
501
+ {"_Too many nodes to generate! Please see the full lineage graph on Recce instance._" if is_partial_graph else ''}
502
+ ```mermaid
503
+ {mermaid_content}
504
+ ```
505
+ """
506
+ else:
507
+ content += """
508
+ ## Lineage Graph
509
+ No changed module was detected.
510
+ """
511
+ if check_content:
512
+ content += check_content
513
+
514
+ if ctx.state_loader.cloud_mode and ctx.state_loader.pr_info is not None:
515
+ pr_info = ctx.state_loader.pr_info
516
+ if pr_info.repository is not None and pr_info.id is not None:
517
+ # the classic route will be deprecated soon
518
+ content += f"\nSee PR page: {RECCE_CLOUD_HOST}/classic/{pr_info.repository}/pulls/{pr_info.id}\n"
519
+
520
+ return content
521
+
522
+
523
+ def generate_check_content(graph, check_statistics):
524
+ from py_markdown_table.markdown_table import markdown_table
525
+
526
+ content = ""
527
+ check_content = None
528
+ # Generate the check summary if we found any changes
529
+ if len(graph.checks) > 0:
530
+ data = []
531
+ for check in graph.checks:
532
+ data.append(
533
+ {
534
+ "Name": check.name,
535
+ "Type": str(check.type).replace("_", " ").title(),
536
+ "Mismatched Nodes": _generate_mismatched_nodes_summary(check),
537
+ # Temporarily remove the type of changes, until we implement a better way to display it.
538
+ # 'Type of Changes': _formate_changes(check.changes)
539
+ }
540
+ )
541
+ check_content = (
542
+ markdown_table(data)
543
+ .set_params(
544
+ quote=False,
545
+ row_sep="markdown",
546
+ padding_width=1,
547
+ padding_weight="right", # Aligns the cell's contents to the beginning of the cell
548
+ )
549
+ .get_markdown()
550
+ )
551
+
552
+ if check_statistics.get("total", 0) > 0:
553
+ warning_message = ""
554
+ statistics = {
555
+ "Checks Run": check_statistics.get("total", 0),
556
+ "Data Mismatch Detected": check_statistics.get("mismatch", 0),
557
+ }
558
+ if check_statistics.get("failed", 0) > 0:
559
+ statistics["Incomplete Checks"] = check_statistics.get("failed", 0)
560
+ warning_message = """
561
+ :warning: **Incomplete Checks** refers to checks that did not successfully run due to configuration or SQL errors.
562
+ Please check the output of `recce run` for more information
563
+ """
564
+ check_summary = markdown_table([statistics]).set_params(quote=False, row_sep="markdown").get_markdown()
565
+ content += f"""
566
+ ## Checks Summary
567
+ {check_summary}
568
+ {warning_message}
569
+ """
570
+ if check_content:
571
+ content += f"""
572
+ ### Checks of Data Mismatch Detected
573
+ {check_content}
574
+ """
575
+ return content
@@ -0,0 +1,23 @@
1
+ from .core import Task
2
+ from .histogram import HistogramDiffTask
3
+ from .profile import ProfileDiffTask, ProfileTask
4
+ from .query import QueryBaseTask, QueryDiffTask, QueryTask
5
+ from .rowcount import RowCountDiffTask, RowCountTask
6
+ from .top_k import TopKDiffTask
7
+ from .valuediff import ValueDiffDetailTask, ValueDiffTask
8
+
9
+ # Explicitly declare exports
10
+ __all__ = [
11
+ "Task",
12
+ "HistogramDiffTask",
13
+ "ProfileDiffTask",
14
+ "ProfileTask",
15
+ "QueryBaseTask",
16
+ "QueryDiffTask",
17
+ "QueryTask",
18
+ "RowCountDiffTask",
19
+ "RowCountTask",
20
+ "TopKDiffTask",
21
+ "ValueDiffDetailTask",
22
+ "ValueDiffTask",
23
+ ]