@pipe0/react 1.0.29 → 1.0.30

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 (35) hide show
  1. package/CHANGELOG.md +8 -0
  2. package/dist/components/compound/pipe-catalog/active-filters.mjs +1 -1
  3. package/dist/components/compound/pipe-catalog/active-filters.mjs.map +1 -1
  4. package/dist/components/compound/search-catalog/active-filters.mjs +1 -1
  5. package/dist/components/compound/search-catalog/active-filters.mjs.map +1 -1
  6. package/dist/components/compound/searches-catalog/active-filters.mjs +1 -1
  7. package/dist/components/compound/searches-catalog/active-filters.mjs.map +1 -1
  8. package/dist/components/ui/button.d.mts +1 -1
  9. package/dist/hooks/catalog-table.d.mts +84 -0
  10. package/dist/hooks/catalog-table.d.mts.map +1 -0
  11. package/dist/hooks/catalog-table.mjs +39 -0
  12. package/dist/hooks/catalog-table.mjs.map +1 -0
  13. package/dist/hooks/use-effect-catalog-table.d.mts +17 -1
  14. package/dist/hooks/use-effect-catalog-table.d.mts.map +1 -1
  15. package/dist/hooks/use-effect-catalog-table.mjs +11 -20
  16. package/dist/hooks/use-effect-catalog-table.mjs.map +1 -1
  17. package/dist/hooks/use-pipe-catalog-table.d.mts +17 -1
  18. package/dist/hooks/use-pipe-catalog-table.d.mts.map +1 -1
  19. package/dist/hooks/use-pipe-catalog-table.mjs +20 -29
  20. package/dist/hooks/use-pipe-catalog-table.mjs.map +1 -1
  21. package/dist/hooks/use-search-catalog-table.d.mts +17 -1
  22. package/dist/hooks/use-search-catalog-table.d.mts.map +1 -1
  23. package/dist/hooks/use-search-catalog-table.mjs +20 -29
  24. package/dist/hooks/use-search-catalog-table.mjs.map +1 -1
  25. package/dist/hooks/use-searches-catalog-table.d.mts +17 -1
  26. package/dist/hooks/use-searches-catalog-table.d.mts.map +1 -1
  27. package/dist/hooks/use-searches-catalog-table.mjs +20 -29
  28. package/dist/hooks/use-searches-catalog-table.mjs.map +1 -1
  29. package/dist/index.d.mts +3 -2
  30. package/dist/index.mjs +3 -2
  31. package/dist/utils/catalog-helpers.d.mts +21 -4
  32. package/dist/utils/catalog-helpers.d.mts.map +1 -1
  33. package/dist/utils/catalog-helpers.mjs +33 -4
  34. package/dist/utils/catalog-helpers.mjs.map +1 -1
  35. package/package.json +3 -3
@@ -1,4 +1,5 @@
1
1
  import { SearchCardData } from "../types/catalog-adapters.mjs";
2
+ import { CatalogFilterMeta, CatalogSearchFeatures } from "../utils/catalog-helpers.mjs";
2
3
  import * as _$react from "react";
3
4
  import { CatalogFilter, OrgAccessLevel, SearchCatalogTableData, SearchCategory, SearchId } from "@pipe0/base";
4
5
  import * as _$_tanstack_react_table0 from "@tanstack/react-table";
@@ -16,7 +17,22 @@ declare function useSearchCatalogTable(config?: {
16
17
  */
17
18
  accessLevel?: OrgAccessLevel;
18
19
  }): {
19
- table: _$_tanstack_react_table0.Table<SearchCatalogTableData>;
20
+ table: _$_tanstack_react_table0.AppReactTable<{
21
+ columnFilteringFeature: _$_tanstack_react_table0.TableFeature;
22
+ globalFilteringFeature: _$_tanstack_react_table0.TableFeature;
23
+ rowSortingFeature: _$_tanstack_react_table0.TableFeature;
24
+ filteredRowModel: (table: _$_tanstack_react_table0.Table<any, any>) => () => _$_tanstack_react_table0.RowModel<any, any>;
25
+ sortedRowModel: (table: _$_tanstack_react_table0.Table<any, any>) => () => _$_tanstack_react_table0.RowModel<any, any>;
26
+ filterFns: {
27
+ includesString: _$_tanstack_react_table0.CreatedFilterFn<any, any>;
28
+ arrIncludes: _$_tanstack_react_table0.CreatedFilterFn<any, any>;
29
+ catalogSearch: _$_tanstack_react_table0.FilterFn<CatalogSearchFeatures, _$_tanstack_react_table0.RowData>;
30
+ };
31
+ sortFns: {
32
+ catalogSearch: _$_tanstack_react_table0.SortFn<CatalogSearchFeatures, _$_tanstack_react_table0.RowData>;
33
+ };
34
+ filterMeta: CatalogFilterMeta;
35
+ }, SearchCatalogTableData, _$_tanstack_react_table0.TableState_ColumnFiltering & _$_tanstack_react_table0.TableState_GlobalFiltering & _$_tanstack_react_table0.TableState_RowSorting, Record<string, _$react.ComponentType<any>>, Record<string, _$react.ComponentType<any>>, Record<string, _$react.ComponentType<any>>>;
20
36
  cards: SearchCardData[];
21
37
  cardsByCategory: {
22
38
  category: SearchCategory;
@@ -1 +1 @@
1
- {"version":3,"file":"use-search-catalog-table.d.mts","names":[],"sources":["../../src/hooks/use-search-catalog-table.ts"],"mappings":";;;;;;;KA+BY,wBAAA,GAA2B,MAAA,SAAe,QAAA;AAAA,iBAkDtC,qBAAA,CACd,MAAA;EACE,oBAAA,GAAuB,YAAA;EAEvB,MAAA,GAAS,aAAA;EAtDuB;;;;AAkDpC;EAUI,WAAA,GAAc,cAAA;AAAA;;;;cAkI4B,cAAA;WAAuB,cAAA;EAAA;;;;;0BAnDtD,cAAA;;yCAAc,OAAA,CAAA,cAAA;+EApBiC,KAAA;;;;;;;;;;;KA4IlD,2BAAA,GAA8B,UAAA,QAAkB,qBAAA"}
1
+ {"version":3,"file":"use-search-catalog-table.d.mts","names":[],"sources":["../../src/hooks/use-search-catalog-table.ts"],"mappings":";;;;;;;;KAwBY,wBAAA,GAA2B,MAAA,SAAe,QAAA;AAAA,iBAkDtC,qBAAA,CACd,MAAA;EACE,oBAAA,GAAuB,YAAA;EAEvB,MAAA,GAAS,aAAA;;AAtDb;;;;EA4DI,WAAA,GAAc,cAAA;AAAA;;4BAAc,wBAAA,CAAA,YAAA;;;;;;;;;;;;;;;;;cA+Gc,cAAA;WAAuB,cAAA;EAAA;;;;;0BA9C3B,cAAA;;yCAAc,OAAA,CAAA,cAAA;+EAhBK,KAAA;;;;;;;;;;;KAmIjD,2BAAA,GAA8B,UAAA,QAAkB,qBAAA"}
@@ -1,8 +1,7 @@
1
- import { catalogSearchFilter, catalogSearchSort } from "../utils/catalog-helpers.mjs";
1
+ import { createCatalogColumnHelper, useCatalogTable } from "./catalog-table.mjs";
2
2
  import { useDebounce } from "./use-debounce.mjs";
3
- import { useCallback, useMemo, useState } from "react";
3
+ import { useMemo, useState } from "react";
4
4
  import { filterSearchEntries, getDefaultSearchOutputFields, getInitialSearchTableData, getLoweestSearchCreditAmount, getSearchAccessLevel, getSearchSearchTarget, getSearchTableDataAggregates, getStartingCostPerSearchProvider, isEntryAccessible, isTokenBilledOperations } from "@pipe0/base";
5
- import { createColumnHelper, getCoreRowModel, getFilteredRowModel, getSortedRowModel, useReactTable } from "@tanstack/react-table";
6
5
 
7
6
  //#region src/hooks/use-search-catalog-table.ts
8
7
  /** Mirrors the pipe hook: partner-gated searches are hidden below partner. */
@@ -10,8 +9,8 @@ function hidePartnerGated(rows, accessLevel) {
10
9
  if (accessLevel === void 0 || accessLevel === "partner") return rows;
11
10
  return rows.filter((row) => getSearchAccessLevel(row.searchId) !== "partner");
12
11
  }
13
- const columnHelper = createColumnHelper();
14
- const columns = [
12
+ const columnHelper = createCatalogColumnHelper();
13
+ const columns = columnHelper.columns([
15
14
  columnHelper.accessor("searchId", {
16
15
  filterFn: "includesString",
17
16
  enableGlobalFilter: false
@@ -39,9 +38,9 @@ const columns = [
39
38
  id: "search",
40
39
  enableGlobalFilter: true,
41
40
  enableSorting: true,
42
- sortingFn: catalogSearchSort
41
+ sortFn: "catalogSearch"
43
42
  })
44
- ];
43
+ ]);
45
44
  function useSearchCatalogTable(config = {}) {
46
45
  const [category, setCategory] = useState(null);
47
46
  const { initialColumnFilters = [], filter, accessLevel } = config;
@@ -51,23 +50,15 @@ function useSearchCatalogTable(config = {}) {
51
50
  accessLevel
52
51
  ]);
53
52
  const baselineTableData = useMemo(() => hidePartnerGated(filterSearchEntries(getInitialSearchTableData(null), filter), accessLevel), [filter, accessLevel]);
54
- const table = useReactTable({
53
+ const table = useCatalogTable({
55
54
  columns,
56
55
  data: initialSearchTableData,
57
- getCoreRowModel: getCoreRowModel(),
58
- getFilteredRowModel: getFilteredRowModel(),
59
- getSortedRowModel: getSortedRowModel(),
60
- globalFilterFn: catalogSearchFilter,
61
- getColumnCanGlobalFilter: (column) => column.columnDef.enableGlobalFilter !== false,
62
- initialState: {
63
- columnFilters: initialColumnFilters,
64
- pagination: { pageSize: 10 }
65
- }
56
+ initialState: { columnFilters: initialColumnFilters }
66
57
  });
67
- const columnFilters = table.getState().columnFilters;
58
+ const columnFilters = table.state.columnFilters;
68
59
  const aggregates = useMemo(() => getSearchTableDataAggregates(initialSearchTableData, category), [category, initialSearchTableData]);
69
60
  const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {
70
- if (v === table.getState().globalFilter) return;
61
+ if (v === table.atoms.globalFilter.get()) return;
71
62
  table.setGlobalFilter(v);
72
63
  table.setSorting(v ? [{
73
64
  id: "search",
@@ -78,28 +69,28 @@ function useSearchCatalogTable(config = {}) {
78
69
  table.setColumnFilters([]);
79
70
  }
80
71
  });
81
- const addColumnFilter = useCallback((id, value) => {
72
+ const addColumnFilter = (id, value) => {
82
73
  setGlobalFilterImmediately("");
83
74
  table.setColumnFilters([{
84
75
  id,
85
76
  value
86
77
  }]);
87
- }, [setGlobalFilterImmediately, table]);
88
- const resetFilters = useCallback(() => {
78
+ };
79
+ const resetFilters = () => {
89
80
  setGlobalFilterImmediately("");
90
81
  setCategory(null);
91
- }, [setGlobalFilterImmediately]);
92
- const removeColumnFilter = useCallback((id) => {
82
+ };
83
+ const removeColumnFilter = (id) => {
93
84
  table.getColumn(id)?.setFilterValue(null);
94
- }, [table]);
95
- const handleCategoryChange = useCallback((category) => {
85
+ };
86
+ const handleCategoryChange = (category) => {
96
87
  setCategory(category);
97
88
  table.setColumnFilters([]);
98
89
  setGlobalFilterImmediately("");
99
- }, [table, setGlobalFilterImmediately]);
100
- const getColumnFilterValue = useCallback((id) => {
90
+ };
91
+ const getColumnFilterValue = (id) => {
101
92
  return columnFilters.find((f) => f.id === id)?.value;
102
- }, [columnFilters]);
93
+ };
103
94
  const rows = table.getRowModel().rows;
104
95
  const cards = useMemo(() => rows.map((row) => {
105
96
  const entry = row.original;
@@ -1 +1 @@
1
- {"version":3,"file":"use-search-catalog-table.mjs","names":[],"sources":["../../src/hooks/use-search-catalog-table.ts"],"sourcesContent":["import {\n type CatalogFilter,\n filterSearchEntries,\n getDefaultSearchOutputFields,\n getInitialSearchTableData,\n getLoweestSearchCreditAmount,\n getSearchAccessLevel,\n getSearchSearchTarget,\n getSearchTableDataAggregates,\n getStartingCostPerSearchProvider,\n isEntryAccessible,\n isTokenBilledOperations,\n type OrgAccessLevel,\n type SearchCatalogEntry,\n type SearchCatalogTableData,\n type SearchCategory,\n type SearchId,\n} from \"@pipe0/base\";\nimport {\n type ColumnFilter,\n createColumnHelper,\n getCoreRowModel,\n getFilteredRowModel,\n getSortedRowModel,\n useReactTable,\n} from \"@tanstack/react-table\";\nimport { useCallback, useMemo, useState } from \"react\";\nimport type { CostMode, SearchCardData } from \"../types/catalog-adapters.js\";\nimport { catalogSearchFilter, catalogSearchSort } from \"../utils/catalog-helpers.js\";\nimport { useDebounce } from \"./use-debounce.js\";\n\nexport type SearchOutputFieldEntries = Record<string, SearchId[]>;\n\n/** Mirrors the pipe hook: partner-gated searches are hidden below partner. */\nfunction hidePartnerGated<T extends { searchId: SearchId }>(\n rows: T[],\n accessLevel: OrgAccessLevel | undefined,\n): T[] {\n if (accessLevel === undefined || accessLevel === \"partner\") return rows;\n return rows.filter((row) => getSearchAccessLevel(row.searchId) !== \"partner\");\n}\n\nconst columnHelper = createColumnHelper<SearchCatalogTableData>();\n\nconst columns = [\n columnHelper.accessor(\"searchId\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"description\", {\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"label\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => getDefaultSearchOutputFields(row.searchId) || [], {\n id: \"outputFields\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.tags || [], {\n id: \"tags\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.provider, {\n id: \"providers\",\n enableGlobalFilter: false,\n }),\n // Hidden relevance column — the ONLY globally-filterable one, so the global\n // filter scores each row exactly once and catalogSearchSort can read the\n // score back from this column's filter meta.\n columnHelper.accessor((row) => getSearchSearchTarget(row), {\n id: \"search\",\n enableGlobalFilter: true,\n enableSorting: true,\n sortingFn: catalogSearchSort,\n }),\n];\n\nexport function useSearchCatalogTable(\n config: {\n initialColumnFilters?: ColumnFilter[];\n /** Optional whitelist/blacklist of searches and providers. Memoize. */\n filter?: CatalogFilter;\n /**\n * The viewing org's access level. Hides partner-gated searches below\n * partner and marks verified-gated cards `locked` below verified. Omit\n * for no gating (docs/playground).\n */\n accessLevel?: OrgAccessLevel;\n } = {},\n) {\n const [category, setCategory] = useState<SearchCategory | null>(null);\n const { initialColumnFilters = [] as ColumnFilter[], filter, accessLevel } = config;\n\n const initialSearchTableData = useMemo(\n () =>\n hidePartnerGated(\n filterSearchEntries(getInitialSearchTableData(category), filter),\n accessLevel,\n ),\n [category, filter, accessLevel],\n );\n\n // Baseline (config.filter applied, but no category / column / global filter).\n // Drives the stable category-button counts so the row doesn't jump.\n const baselineTableData = useMemo(\n () =>\n hidePartnerGated(filterSearchEntries(getInitialSearchTableData(null), filter), accessLevel),\n [filter, accessLevel],\n );\n\n const table = useReactTable({\n columns,\n data: initialSearchTableData,\n getCoreRowModel: getCoreRowModel(),\n getFilteredRowModel: getFilteredRowModel(),\n getSortedRowModel: getSortedRowModel(),\n globalFilterFn: catalogSearchFilter,\n getColumnCanGlobalFilter: (column) => column.columnDef.enableGlobalFilter !== false,\n initialState: {\n columnFilters: initialColumnFilters,\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n const columnFilters = table.getState().columnFilters;\n\n const aggregates = useMemo(\n () => getSearchTableDataAggregates(initialSearchTableData, category),\n [category, initialSearchTableData],\n );\n\n const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {\n if (v === table.getState().globalFilter) return;\n table.setGlobalFilter(v);\n // Relevance order only while a query is active; empty query restores\n // catalog order.\n table.setSorting(v ? [{ id: \"search\", desc: true }] : []);\n if (v) {\n setCategory(null);\n table.setColumnFilters([]);\n }\n });\n\n const addColumnFilter = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\", value: string) => {\n setGlobalFilterImmediately(\"\");\n table.setColumnFilters([{ id, value }]);\n },\n [setGlobalFilterImmediately, table],\n );\n\n const resetFilters = useCallback(() => {\n setGlobalFilterImmediately(\"\");\n setCategory(null);\n }, [setGlobalFilterImmediately]);\n\n const removeColumnFilter = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n table.getColumn(id)?.setFilterValue(null);\n },\n [table],\n );\n\n const handleCategoryChange = useCallback(\n (category: SearchCategory | null) => {\n setCategory(category);\n table.setColumnFilters([]);\n setGlobalFilterImmediately(\"\");\n },\n [table, setGlobalFilterImmediately],\n );\n\n const getColumnFilterValue = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n const res = columnFilters.find((f) => f.id === id)?.value;\n return res as string;\n },\n [columnFilters],\n );\n\n const rows = table.getRowModel().rows;\n const cards = useMemo<SearchCardData[]>(\n () =>\n rows.map((row) => {\n const entry = row.original;\n const latestEntry = (aggregates.searchEntriesByBaseSearch[entry.baseSearch]?.[0] ??\n entry) as SearchCatalogEntry & { searchId: SearchId };\n const gate = getSearchAccessLevel(latestEntry.searchId);\n const locked =\n accessLevel !== undefined && gate !== undefined && !isEntryAccessible(gate, accessLevel);\n return {\n ...(locked ? { locked, requiredAccessLevel: gate } : {}),\n searchId: latestEntry.searchId,\n baseSearch: entry.baseSearch,\n label: entry.label,\n description: entry.description,\n provider: entry.provider,\n providers: [entry.provider],\n startingCostPerProvider: getStartingCostPerSearchProvider(latestEntry.searchId),\n startingCreditAmount: getLoweestSearchCreditAmount(latestEntry),\n // A usage-metered search bills per operation and carries cost.credits 0,\n // so the flat mode would render it as free. Same branch the pipe and\n // effect hooks already use.\n costMode: isTokenBilledOperations(latestEntry.billableOperations ?? {})\n ? (\"usage\" as CostMode)\n : ((latestEntry.cost.mode ?? \"per_page\") as CostMode),\n defaultOutputFields: getDefaultSearchOutputFields(latestEntry.searchId),\n docPath: latestEntry.docPath,\n entry: entry as SearchCatalogTableData,\n latestEntry,\n };\n }),\n [rows, aggregates.searchEntriesByBaseSearch, accessLevel],\n );\n\n const cardsByCategory = useMemo<{ category: SearchCategory; cards: SearchCardData[] }[]>(() => {\n const groups = new Map<SearchCategory, SearchCardData[]>();\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n const arr = groups.get(cat);\n if (arr) arr.push(card);\n else groups.set(cat, [card]);\n }\n }\n return Array.from(groups, ([category, group]) => ({\n category,\n cards: group,\n }));\n }, [cards]);\n\n const categoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [cards]);\n\n // Stable counts based on the baseline (no category / column / global filter\n // applied).\n const baselineCardCount = baselineTableData.length;\n const baselineCategoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const entry of baselineTableData) {\n const cats = (entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [baselineTableData]);\n\n return {\n table,\n cards,\n cardsByCategory,\n categoryCounts,\n baselineCardCount,\n baselineCategoryCounts,\n\n category,\n setCategory: handleCategoryChange,\n globalFilterInput,\n setGlobalFilterInput,\n\n addColumnFilter,\n removeColumnFilter,\n resetFilters,\n getColumnFilterValue,\n\n sortedOutputFieldEntries: aggregates.sortedOutputFieldEntries,\n sortedTagEntries: aggregates.sortedTagEntries,\n sortedProviderEntries: aggregates.sortedProviderEntries,\n\n searchIdsByOutputField: aggregates.searchIdsByOutputField,\n searchIdsByProvider: aggregates.searchIdsByProvider,\n searchIdsByTag: aggregates.searchIdsByTag,\n };\n}\n\nexport type UseSearchCatalogTableReturn = ReturnType<typeof useSearchCatalogTable>;\n"],"mappings":"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"}
1
+ {"version":3,"file":"use-search-catalog-table.mjs","names":[],"sources":["../../src/hooks/use-search-catalog-table.ts"],"sourcesContent":["import {\n type CatalogFilter,\n filterSearchEntries,\n getDefaultSearchOutputFields,\n getInitialSearchTableData,\n getLoweestSearchCreditAmount,\n getSearchAccessLevel,\n getSearchSearchTarget,\n getSearchTableDataAggregates,\n getStartingCostPerSearchProvider,\n isEntryAccessible,\n isTokenBilledOperations,\n type OrgAccessLevel,\n type SearchCatalogEntry,\n type SearchCatalogTableData,\n type SearchCategory,\n type SearchId,\n} from \"@pipe0/base\";\nimport type { ColumnFilter } from \"@tanstack/react-table\";\nimport { useMemo, useState } from \"react\";\nimport type { CostMode, SearchCardData } from \"../types/catalog-adapters.js\";\nimport { createCatalogColumnHelper, useCatalogTable } from \"./catalog-table.js\";\nimport { useDebounce } from \"./use-debounce.js\";\n\nexport type SearchOutputFieldEntries = Record<string, SearchId[]>;\n\n/** Mirrors the pipe hook: partner-gated searches are hidden below partner. */\nfunction hidePartnerGated<T extends { searchId: SearchId }>(\n rows: T[],\n accessLevel: OrgAccessLevel | undefined,\n): T[] {\n if (accessLevel === undefined || accessLevel === \"partner\") return rows;\n return rows.filter((row) => getSearchAccessLevel(row.searchId) !== \"partner\");\n}\n\nconst columnHelper = createCatalogColumnHelper<SearchCatalogTableData>();\n\nconst columns = columnHelper.columns([\n columnHelper.accessor(\"searchId\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"description\", {\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"label\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => getDefaultSearchOutputFields(row.searchId) || [], {\n id: \"outputFields\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.tags || [], {\n id: \"tags\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.provider, {\n id: \"providers\",\n enableGlobalFilter: false,\n }),\n // Hidden relevance column — the ONLY globally-filterable one, so the global\n // filter scores each row exactly once and catalogSearchSort can read the\n // score back from this column's filter meta.\n columnHelper.accessor((row) => getSearchSearchTarget(row), {\n id: \"search\",\n enableGlobalFilter: true,\n enableSorting: true,\n sortFn: \"catalogSearch\",\n }),\n]);\n\nexport function useSearchCatalogTable(\n config: {\n initialColumnFilters?: ColumnFilter[];\n /** Optional whitelist/blacklist of searches and providers. Memoize. */\n filter?: CatalogFilter;\n /**\n * The viewing org's access level. Hides partner-gated searches below\n * partner and marks verified-gated cards `locked` below verified. Omit\n * for no gating (docs/playground).\n */\n accessLevel?: OrgAccessLevel;\n } = {},\n) {\n const [category, setCategory] = useState<SearchCategory | null>(null);\n const { initialColumnFilters = [] as ColumnFilter[], filter, accessLevel } = config;\n\n const initialSearchTableData = useMemo(\n () =>\n hidePartnerGated(\n filterSearchEntries(getInitialSearchTableData(category), filter),\n accessLevel,\n ),\n [category, filter, accessLevel],\n );\n\n // Baseline (config.filter applied, but no category / column / global filter).\n // Drives the stable category-button counts so the row doesn't jump.\n const baselineTableData = useMemo(\n () =>\n hidePartnerGated(filterSearchEntries(getInitialSearchTableData(null), filter), accessLevel),\n [filter, accessLevel],\n );\n\n const table = useCatalogTable({\n columns,\n data: initialSearchTableData,\n initialState: { columnFilters: initialColumnFilters },\n });\n\n const columnFilters = table.state.columnFilters;\n\n const aggregates = useMemo(\n () => getSearchTableDataAggregates(initialSearchTableData, category),\n [category, initialSearchTableData],\n );\n\n const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {\n if (v === table.atoms.globalFilter.get()) return;\n table.setGlobalFilter(v);\n // Relevance order only while a query is active; empty query restores\n // catalog order.\n table.setSorting(v ? [{ id: \"search\", desc: true }] : []);\n if (v) {\n setCategory(null);\n table.setColumnFilters([]);\n }\n });\n\n const addColumnFilter = (\n id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\",\n value: string,\n ) => {\n setGlobalFilterImmediately(\"\");\n table.setColumnFilters([{ id, value }]);\n };\n\n const resetFilters = () => {\n setGlobalFilterImmediately(\"\");\n setCategory(null);\n };\n\n const removeColumnFilter = (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n table.getColumn(id)?.setFilterValue(null);\n };\n\n const handleCategoryChange = (category: SearchCategory | null) => {\n setCategory(category);\n table.setColumnFilters([]);\n setGlobalFilterImmediately(\"\");\n };\n\n const getColumnFilterValue = (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n const res = columnFilters.find((f) => f.id === id)?.value;\n return res as string;\n };\n\n const rows = table.getRowModel().rows;\n const cards = useMemo<SearchCardData[]>(\n () =>\n rows.map((row) => {\n const entry = row.original;\n const latestEntry = (aggregates.searchEntriesByBaseSearch[entry.baseSearch]?.[0] ??\n entry) as SearchCatalogEntry & { searchId: SearchId };\n const gate = getSearchAccessLevel(latestEntry.searchId);\n const locked =\n accessLevel !== undefined && gate !== undefined && !isEntryAccessible(gate, accessLevel);\n return {\n ...(locked ? { locked, requiredAccessLevel: gate } : {}),\n searchId: latestEntry.searchId,\n baseSearch: entry.baseSearch,\n label: entry.label,\n description: entry.description,\n provider: entry.provider,\n providers: [entry.provider],\n startingCostPerProvider: getStartingCostPerSearchProvider(latestEntry.searchId),\n startingCreditAmount: getLoweestSearchCreditAmount(latestEntry),\n // A usage-metered search bills per operation and carries cost.credits 0,\n // so the flat mode would render it as free. Same branch the pipe and\n // effect hooks already use.\n costMode: isTokenBilledOperations(latestEntry.billableOperations ?? {})\n ? (\"usage\" as CostMode)\n : ((latestEntry.cost.mode ?? \"per_page\") as CostMode),\n defaultOutputFields: getDefaultSearchOutputFields(latestEntry.searchId),\n docPath: latestEntry.docPath,\n entry: entry as SearchCatalogTableData,\n latestEntry,\n };\n }),\n [rows, aggregates.searchEntriesByBaseSearch, accessLevel],\n );\n\n const cardsByCategory = useMemo<{ category: SearchCategory; cards: SearchCardData[] }[]>(() => {\n const groups = new Map<SearchCategory, SearchCardData[]>();\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n const arr = groups.get(cat);\n if (arr) arr.push(card);\n else groups.set(cat, [card]);\n }\n }\n return Array.from(groups, ([category, group]) => ({\n category,\n cards: group,\n }));\n }, [cards]);\n\n const categoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [cards]);\n\n // Stable counts based on the baseline (no category / column / global filter\n // applied).\n const baselineCardCount = baselineTableData.length;\n const baselineCategoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const entry of baselineTableData) {\n const cats = (entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [baselineTableData]);\n\n return {\n table,\n cards,\n cardsByCategory,\n categoryCounts,\n baselineCardCount,\n baselineCategoryCounts,\n\n category,\n setCategory: handleCategoryChange,\n globalFilterInput,\n setGlobalFilterInput,\n\n addColumnFilter,\n removeColumnFilter,\n resetFilters,\n getColumnFilterValue,\n\n sortedOutputFieldEntries: aggregates.sortedOutputFieldEntries,\n sortedTagEntries: aggregates.sortedTagEntries,\n sortedProviderEntries: aggregates.sortedProviderEntries,\n\n searchIdsByOutputField: aggregates.searchIdsByOutputField,\n searchIdsByProvider: aggregates.searchIdsByProvider,\n searchIdsByTag: aggregates.searchIdsByTag,\n };\n}\n\nexport type UseSearchCatalogTableReturn = ReturnType<typeof useSearchCatalogTable>;\n"],"mappings":"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"}
@@ -1,4 +1,5 @@
1
1
  import { SearchesCardData } from "../types/catalog-adapters.mjs";
2
+ import { CatalogFilterMeta, CatalogSearchFeatures } from "../utils/catalog-helpers.mjs";
2
3
  import * as _$react from "react";
3
4
  import { CatalogFilter, SearchCategory, SearchesCatalogTableData, SearchesId } from "@pipe0/base";
4
5
  import * as _$_tanstack_react_table0 from "@tanstack/react-table";
@@ -10,7 +11,22 @@ declare function useSearchesCatalogTable(config?: {
10
11
  initialColumnFilters?: ColumnFilter[];
11
12
  filter?: CatalogFilter;
12
13
  }): {
13
- table: _$_tanstack_react_table0.Table<SearchesCatalogTableData>;
14
+ table: _$_tanstack_react_table0.AppReactTable<{
15
+ columnFilteringFeature: _$_tanstack_react_table0.TableFeature;
16
+ globalFilteringFeature: _$_tanstack_react_table0.TableFeature;
17
+ rowSortingFeature: _$_tanstack_react_table0.TableFeature;
18
+ filteredRowModel: (table: _$_tanstack_react_table0.Table<any, any>) => () => _$_tanstack_react_table0.RowModel<any, any>;
19
+ sortedRowModel: (table: _$_tanstack_react_table0.Table<any, any>) => () => _$_tanstack_react_table0.RowModel<any, any>;
20
+ filterFns: {
21
+ includesString: _$_tanstack_react_table0.CreatedFilterFn<any, any>;
22
+ arrIncludes: _$_tanstack_react_table0.CreatedFilterFn<any, any>;
23
+ catalogSearch: _$_tanstack_react_table0.FilterFn<CatalogSearchFeatures, _$_tanstack_react_table0.RowData>;
24
+ };
25
+ sortFns: {
26
+ catalogSearch: _$_tanstack_react_table0.SortFn<CatalogSearchFeatures, _$_tanstack_react_table0.RowData>;
27
+ };
28
+ filterMeta: CatalogFilterMeta;
29
+ }, SearchesCatalogTableData, _$_tanstack_react_table0.TableState_ColumnFiltering & _$_tanstack_react_table0.TableState_GlobalFiltering & _$_tanstack_react_table0.TableState_RowSorting, Record<string, _$react.ComponentType<any>>, Record<string, _$react.ComponentType<any>>, Record<string, _$react.ComponentType<any>>>;
14
30
  cards: SearchesCardData[];
15
31
  cardsByCategory: {
16
32
  category: SearchCategory;
@@ -1 +1 @@
1
- {"version":3,"file":"use-searches-catalog-table.d.mts","names":[],"sources":["../../src/hooks/use-searches-catalog-table.ts"],"mappings":";;;;;;;KA2BY,0BAAA,GAA6B,MAAA,SAAe,UAAA;AAAA,iBAyCxC,uBAAA,CACd,MAAA;EAAU,oBAAA,GAAuB,YAAA;EAAgB,MAAA,GAAS,aAAA;AAAA;;;;cAmHd,cAAA;WAAuB,gBAAA;EAAA;;;;;0BA1CtD,cAAA;;yCAAc,OAAA,CAAA,cAAA;+EApBiC,KAAA;;;;;;;;;;;KAmIlD,6BAAA,GAAgC,UAAA,QAAkB,uBAAA"}
1
+ {"version":3,"file":"use-searches-catalog-table.d.mts","names":[],"sources":["../../src/hooks/use-searches-catalog-table.ts"],"mappings":";;;;;;;;KAoBY,0BAAA,GAA6B,MAAA,SAAe,UAAA;AAAA,iBAyCxC,uBAAA,CACd,MAAA;EAAU,oBAAA,GAAuB,YAAA;EAAgB,MAAA,GAAS,aAAA;AAAA;;4BAAa,wBAAA,CAAA,YAAA;;;;;;;;;;;;;;;;;cAgG3B,cAAA;WAAuB,gBAAA;EAAA;;;;;0BArC3B,cAAA;;yCAAc,OAAA,CAAA,cAAA;+EAhBK,KAAA;;;;;;;;;;;KA0HjD,6BAAA,GAAgC,UAAA,QAAkB,uBAAA"}
@@ -1,12 +1,11 @@
1
- import { catalogSearchFilter, catalogSearchSort } from "../utils/catalog-helpers.mjs";
1
+ import { createCatalogColumnHelper, useCatalogTable } from "./catalog-table.mjs";
2
2
  import { useDebounce } from "./use-debounce.mjs";
3
- import { useCallback, useMemo, useState } from "react";
3
+ import { useMemo, useState } from "react";
4
4
  import { filterSearchesEntries, getDefaultSearchesOutputFields, getInitialSearchesTableData, getLoweestSearchesCreditAmount, getSearchesSearchTarget, getSearchesTableDataAggregates, getStartingCostPerSearchesProvider } from "@pipe0/base";
5
- import { createColumnHelper, getCoreRowModel, getFilteredRowModel, getSortedRowModel, useReactTable } from "@tanstack/react-table";
6
5
 
7
6
  //#region src/hooks/use-searches-catalog-table.ts
8
- const columnHelper = createColumnHelper();
9
- const columns = [
7
+ const columnHelper = createCatalogColumnHelper();
8
+ const columns = columnHelper.columns([
10
9
  columnHelper.accessor("searchId", {
11
10
  filterFn: "includesString",
12
11
  enableGlobalFilter: false
@@ -34,31 +33,23 @@ const columns = [
34
33
  id: "search",
35
34
  enableGlobalFilter: true,
36
35
  enableSorting: true,
37
- sortingFn: catalogSearchSort
36
+ sortFn: "catalogSearch"
38
37
  })
39
- ];
38
+ ]);
40
39
  function useSearchesCatalogTable(config = {}) {
41
40
  const [category, setCategory] = useState(null);
42
41
  const { initialColumnFilters = [], filter } = config;
43
42
  const initialSearchTableData = useMemo(() => filterSearchesEntries(getInitialSearchesTableData(category), filter), [category, filter]);
44
43
  const baselineTableData = useMemo(() => filterSearchesEntries(getInitialSearchesTableData(null), filter), [filter]);
45
- const table = useReactTable({
44
+ const table = useCatalogTable({
46
45
  columns,
47
46
  data: initialSearchTableData,
48
- getCoreRowModel: getCoreRowModel(),
49
- getFilteredRowModel: getFilteredRowModel(),
50
- getSortedRowModel: getSortedRowModel(),
51
- globalFilterFn: catalogSearchFilter,
52
- getColumnCanGlobalFilter: (column) => column.columnDef.enableGlobalFilter !== false,
53
- initialState: {
54
- columnFilters: initialColumnFilters,
55
- pagination: { pageSize: 10 }
56
- }
47
+ initialState: { columnFilters: initialColumnFilters }
57
48
  });
58
- const columnFilters = table.getState().columnFilters;
49
+ const columnFilters = table.state.columnFilters;
59
50
  const aggregates = useMemo(() => getSearchesTableDataAggregates(initialSearchTableData, category), [category, initialSearchTableData]);
60
51
  const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {
61
- if (v === table.getState().globalFilter) return;
52
+ if (v === table.atoms.globalFilter.get()) return;
62
53
  table.setGlobalFilter(v);
63
54
  table.setSorting(v ? [{
64
55
  id: "search",
@@ -69,28 +60,28 @@ function useSearchesCatalogTable(config = {}) {
69
60
  table.setColumnFilters([]);
70
61
  }
71
62
  });
72
- const addColumnFilter = useCallback((id, value) => {
63
+ const addColumnFilter = (id, value) => {
73
64
  setGlobalFilterImmediately("");
74
65
  table.setColumnFilters([{
75
66
  id,
76
67
  value
77
68
  }]);
78
- }, [setGlobalFilterImmediately, table]);
79
- const resetFilters = useCallback(() => {
69
+ };
70
+ const resetFilters = () => {
80
71
  setGlobalFilterImmediately("");
81
72
  setCategory(null);
82
- }, [setGlobalFilterImmediately]);
83
- const removeColumnFilter = useCallback((id) => {
73
+ };
74
+ const removeColumnFilter = (id) => {
84
75
  table.getColumn(id)?.setFilterValue(null);
85
- }, [table]);
86
- const handleCategoryChange = useCallback((category) => {
76
+ };
77
+ const handleCategoryChange = (category) => {
87
78
  setCategory(category);
88
79
  table.setColumnFilters([]);
89
80
  setGlobalFilterImmediately("");
90
- }, [table, setGlobalFilterImmediately]);
91
- const getColumnFilterValue = useCallback((id) => {
81
+ };
82
+ const getColumnFilterValue = (id) => {
92
83
  return columnFilters.find((f) => f.id === id)?.value;
93
- }, [columnFilters]);
84
+ };
94
85
  const rows = table.getRowModel().rows;
95
86
  const cards = useMemo(() => rows.map((row) => {
96
87
  const entry = row.original;
@@ -1 +1 @@
1
- {"version":3,"file":"use-searches-catalog-table.mjs","names":[],"sources":["../../src/hooks/use-searches-catalog-table.ts"],"sourcesContent":["import {\n type CatalogFilter,\n filterSearchesEntries,\n getDefaultSearchesOutputFields,\n getInitialSearchesTableData,\n getLoweestSearchesCreditAmount,\n getSearchesSearchTarget,\n getSearchesTableDataAggregates,\n getStartingCostPerSearchesProvider,\n type SearchCategory,\n type SearchesCatalogEntry,\n type SearchesCatalogTableData,\n type SearchesId,\n} from \"@pipe0/base\";\nimport {\n type ColumnFilter,\n createColumnHelper,\n getCoreRowModel,\n getFilteredRowModel,\n getSortedRowModel,\n useReactTable,\n} from \"@tanstack/react-table\";\nimport { useCallback, useMemo, useState } from \"react\";\nimport type { CostMode, SearchesCardData } from \"../types/catalog-adapters.js\";\nimport { catalogSearchFilter, catalogSearchSort } from \"../utils/catalog-helpers.js\";\nimport { useDebounce } from \"./use-debounce.js\";\n\nexport type SearchesOutputFieldEntries = Record<string, SearchesId[]>;\n\nconst columnHelper = createColumnHelper<SearchesCatalogTableData>();\n\nconst columns = [\n columnHelper.accessor(\"searchId\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"description\", {\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"label\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => getDefaultSearchesOutputFields(row.searchId) || [], {\n id: \"outputFields\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.tags || [], {\n id: \"tags\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.provider, {\n id: \"providers\",\n enableGlobalFilter: false,\n }),\n // Hidden relevance column — the ONLY globally-filterable one, so the global\n // filter scores each row exactly once and catalogSearchSort can read the\n // score back from this column's filter meta.\n columnHelper.accessor((row) => getSearchesSearchTarget(row), {\n id: \"search\",\n enableGlobalFilter: true,\n enableSorting: true,\n sortingFn: catalogSearchSort,\n }),\n];\n\nexport function useSearchesCatalogTable(\n config: { initialColumnFilters?: ColumnFilter[]; filter?: CatalogFilter } = {},\n) {\n const [category, setCategory] = useState<SearchCategory | null>(null);\n const { initialColumnFilters = [] as ColumnFilter[], filter } = config;\n\n const initialSearchTableData = useMemo(\n () => filterSearchesEntries(getInitialSearchesTableData(category), filter),\n [category, filter],\n );\n\n // Baseline (config.filter applied, but no category / column / global filter).\n // Drives the stable category-button counts so the row doesn't jump.\n const baselineTableData = useMemo(\n () => filterSearchesEntries(getInitialSearchesTableData(null), filter),\n [filter],\n );\n\n const table = useReactTable({\n columns,\n data: initialSearchTableData,\n getCoreRowModel: getCoreRowModel(),\n getFilteredRowModel: getFilteredRowModel(),\n getSortedRowModel: getSortedRowModel(),\n globalFilterFn: catalogSearchFilter,\n getColumnCanGlobalFilter: (column) => column.columnDef.enableGlobalFilter !== false,\n initialState: {\n columnFilters: initialColumnFilters,\n pagination: {\n pageSize: 10,\n },\n },\n });\n\n const columnFilters = table.getState().columnFilters;\n\n const aggregates = useMemo(\n () => getSearchesTableDataAggregates(initialSearchTableData, category),\n [category, initialSearchTableData],\n );\n\n const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {\n if (v === table.getState().globalFilter) return;\n table.setGlobalFilter(v);\n // Relevance order only while a query is active; empty query restores\n // catalog order.\n table.setSorting(v ? [{ id: \"search\", desc: true }] : []);\n if (v) {\n setCategory(null);\n table.setColumnFilters([]);\n }\n });\n\n const addColumnFilter = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\", value: string) => {\n setGlobalFilterImmediately(\"\");\n table.setColumnFilters([{ id, value }]);\n },\n [setGlobalFilterImmediately, table],\n );\n\n const resetFilters = useCallback(() => {\n setGlobalFilterImmediately(\"\");\n setCategory(null);\n }, [setGlobalFilterImmediately]);\n\n const removeColumnFilter = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n table.getColumn(id)?.setFilterValue(null);\n },\n [table],\n );\n\n const handleCategoryChange = useCallback(\n (category: SearchCategory | null) => {\n setCategory(category);\n table.setColumnFilters([]);\n setGlobalFilterImmediately(\"\");\n },\n [table, setGlobalFilterImmediately],\n );\n\n const getColumnFilterValue = useCallback(\n (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n const res = columnFilters.find((f) => f.id === id)?.value;\n return res as string;\n },\n [columnFilters],\n );\n\n const rows = table.getRowModel().rows;\n const cards = useMemo<SearchesCardData[]>(\n () =>\n rows.map((row) => {\n const entry = row.original;\n const latestEntry = (aggregates.searchEntriesByBaseSearch[entry.baseSearch]?.[0] ??\n entry) as SearchesCatalogEntry & { searchesId: SearchesId };\n return {\n searchesId: latestEntry.searchesId,\n baseSearches: entry.baseSearch,\n label: entry.label,\n description: entry.description,\n provider: entry.provider,\n providers: [entry.provider],\n startingCostPerProvider: getStartingCostPerSearchesProvider(latestEntry.searchesId),\n startingCreditAmount: getLoweestSearchesCreditAmount(latestEntry),\n costMode: latestEntry.cost.mode as CostMode,\n defaultOutputFields: getDefaultSearchesOutputFields(latestEntry.searchesId),\n docPath: latestEntry.docPath,\n entry: entry as SearchesCatalogTableData,\n latestEntry,\n };\n }),\n [rows, aggregates.searchEntriesByBaseSearch],\n );\n\n const cardsByCategory = useMemo<{ category: SearchCategory; cards: SearchesCardData[] }[]>(() => {\n const groups = new Map<SearchCategory, SearchesCardData[]>();\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n const arr = groups.get(cat);\n if (arr) arr.push(card);\n else groups.set(cat, [card]);\n }\n }\n return Array.from(groups, ([category, group]) => ({\n category,\n cards: group,\n }));\n }, [cards]);\n\n const categoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [cards]);\n\n // Stable counts based on the baseline (no category / column / global filter\n // applied).\n const baselineCardCount = baselineTableData.length;\n const baselineCategoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const entry of baselineTableData) {\n const cats = (entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [baselineTableData]);\n\n return {\n table,\n cards,\n cardsByCategory,\n categoryCounts,\n baselineCardCount,\n baselineCategoryCounts,\n\n category,\n setCategory: handleCategoryChange,\n globalFilterInput,\n setGlobalFilterInput,\n\n addColumnFilter,\n removeColumnFilter,\n resetFilters,\n getColumnFilterValue,\n\n sortedOutputFieldEntries: aggregates.sortedOutputFieldEntries,\n sortedTagEntries: aggregates.sortedTagEntries,\n sortedProviderEntries: aggregates.sortedProviderEntries,\n\n searchIdsByOutputField: aggregates.searchIdsByOutputField,\n searchIdsByProvider: aggregates.searchIdsByProvider,\n searchIdsByTag: aggregates.searchIdsByTag,\n };\n}\n\nexport type UseSearchesCatalogTableReturn = ReturnType<typeof useSearchesCatalogTable>;\n"],"mappings":"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"}
1
+ {"version":3,"file":"use-searches-catalog-table.mjs","names":[],"sources":["../../src/hooks/use-searches-catalog-table.ts"],"sourcesContent":["import {\n type CatalogFilter,\n filterSearchesEntries,\n getDefaultSearchesOutputFields,\n getInitialSearchesTableData,\n getLoweestSearchesCreditAmount,\n getSearchesSearchTarget,\n getSearchesTableDataAggregates,\n getStartingCostPerSearchesProvider,\n type SearchCategory,\n type SearchesCatalogEntry,\n type SearchesCatalogTableData,\n type SearchesId,\n} from \"@pipe0/base\";\nimport type { ColumnFilter } from \"@tanstack/react-table\";\nimport { useMemo, useState } from \"react\";\nimport type { CostMode, SearchesCardData } from \"../types/catalog-adapters.js\";\nimport { createCatalogColumnHelper, useCatalogTable } from \"./catalog-table.js\";\nimport { useDebounce } from \"./use-debounce.js\";\n\nexport type SearchesOutputFieldEntries = Record<string, SearchesId[]>;\n\nconst columnHelper = createCatalogColumnHelper<SearchesCatalogTableData>();\n\nconst columns = columnHelper.columns([\n columnHelper.accessor(\"searchId\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"description\", {\n enableGlobalFilter: false,\n }),\n columnHelper.accessor(\"label\", {\n filterFn: \"includesString\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => getDefaultSearchesOutputFields(row.searchId) || [], {\n id: \"outputFields\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.tags || [], {\n id: \"tags\",\n filterFn: \"arrIncludes\",\n enableGlobalFilter: false,\n }),\n columnHelper.accessor((row) => row.provider, {\n id: \"providers\",\n enableGlobalFilter: false,\n }),\n // Hidden relevance column — the ONLY globally-filterable one, so the global\n // filter scores each row exactly once and catalogSearchSort can read the\n // score back from this column's filter meta.\n columnHelper.accessor((row) => getSearchesSearchTarget(row), {\n id: \"search\",\n enableGlobalFilter: true,\n enableSorting: true,\n sortFn: \"catalogSearch\",\n }),\n]);\n\nexport function useSearchesCatalogTable(\n config: { initialColumnFilters?: ColumnFilter[]; filter?: CatalogFilter } = {},\n) {\n const [category, setCategory] = useState<SearchCategory | null>(null);\n const { initialColumnFilters = [] as ColumnFilter[], filter } = config;\n\n const initialSearchTableData = useMemo(\n () => filterSearchesEntries(getInitialSearchesTableData(category), filter),\n [category, filter],\n );\n\n // Baseline (config.filter applied, but no category / column / global filter).\n // Drives the stable category-button counts so the row doesn't jump.\n const baselineTableData = useMemo(\n () => filterSearchesEntries(getInitialSearchesTableData(null), filter),\n [filter],\n );\n\n const table = useCatalogTable({\n columns,\n data: initialSearchTableData,\n initialState: { columnFilters: initialColumnFilters },\n });\n\n const columnFilters = table.state.columnFilters;\n\n const aggregates = useMemo(\n () => getSearchesTableDataAggregates(initialSearchTableData, category),\n [category, initialSearchTableData],\n );\n\n const [globalFilterInput, setGlobalFilterInput, setGlobalFilterImmediately] = useDebounce((v) => {\n if (v === table.atoms.globalFilter.get()) return;\n table.setGlobalFilter(v);\n // Relevance order only while a query is active; empty query restores\n // catalog order.\n table.setSorting(v ? [{ id: \"search\", desc: true }] : []);\n if (v) {\n setCategory(null);\n table.setColumnFilters([]);\n }\n });\n\n const addColumnFilter = (\n id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\",\n value: string,\n ) => {\n setGlobalFilterImmediately(\"\");\n table.setColumnFilters([{ id, value }]);\n };\n\n const resetFilters = () => {\n setGlobalFilterImmediately(\"\");\n setCategory(null);\n };\n\n const removeColumnFilter = (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n table.getColumn(id)?.setFilterValue(null);\n };\n\n const handleCategoryChange = (category: SearchCategory | null) => {\n setCategory(category);\n table.setColumnFilters([]);\n setGlobalFilterImmediately(\"\");\n };\n\n const getColumnFilterValue = (id: \"inputFields\" | \"outputFields\" | \"tags\" | \"providers\") => {\n const res = columnFilters.find((f) => f.id === id)?.value;\n return res as string;\n };\n\n const rows = table.getRowModel().rows;\n const cards = useMemo<SearchesCardData[]>(\n () =>\n rows.map((row) => {\n const entry = row.original;\n const latestEntry = (aggregates.searchEntriesByBaseSearch[entry.baseSearch]?.[0] ??\n entry) as SearchesCatalogEntry & { searchesId: SearchesId };\n return {\n searchesId: latestEntry.searchesId,\n baseSearches: entry.baseSearch,\n label: entry.label,\n description: entry.description,\n provider: entry.provider,\n providers: [entry.provider],\n startingCostPerProvider: getStartingCostPerSearchesProvider(latestEntry.searchesId),\n startingCreditAmount: getLoweestSearchesCreditAmount(latestEntry),\n costMode: latestEntry.cost.mode as CostMode,\n defaultOutputFields: getDefaultSearchesOutputFields(latestEntry.searchesId),\n docPath: latestEntry.docPath,\n entry: entry as SearchesCatalogTableData,\n latestEntry,\n };\n }),\n [rows, aggregates.searchEntriesByBaseSearch],\n );\n\n const cardsByCategory = useMemo<{ category: SearchCategory; cards: SearchesCardData[] }[]>(() => {\n const groups = new Map<SearchCategory, SearchesCardData[]>();\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n const arr = groups.get(cat);\n if (arr) arr.push(card);\n else groups.set(cat, [card]);\n }\n }\n return Array.from(groups, ([category, group]) => ({\n category,\n cards: group,\n }));\n }, [cards]);\n\n const categoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const card of cards) {\n const cats = (card.entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [cards]);\n\n // Stable counts based on the baseline (no category / column / global filter\n // applied).\n const baselineCardCount = baselineTableData.length;\n const baselineCategoryCounts = useMemo<Partial<Record<SearchCategory, number>>>(() => {\n const counts: Partial<Record<SearchCategory, number>> = {};\n for (const entry of baselineTableData) {\n const cats = (entry.categories ?? []) as SearchCategory[];\n for (const cat of cats) {\n counts[cat] = (counts[cat] ?? 0) + 1;\n }\n }\n return counts;\n }, [baselineTableData]);\n\n return {\n table,\n cards,\n cardsByCategory,\n categoryCounts,\n baselineCardCount,\n baselineCategoryCounts,\n\n category,\n setCategory: handleCategoryChange,\n globalFilterInput,\n setGlobalFilterInput,\n\n addColumnFilter,\n removeColumnFilter,\n resetFilters,\n getColumnFilterValue,\n\n sortedOutputFieldEntries: aggregates.sortedOutputFieldEntries,\n sortedTagEntries: aggregates.sortedTagEntries,\n sortedProviderEntries: aggregates.sortedProviderEntries,\n\n searchIdsByOutputField: aggregates.searchIdsByOutputField,\n searchIdsByProvider: aggregates.searchIdsByProvider,\n searchIdsByTag: aggregates.searchIdsByTag,\n };\n}\n\nexport type UseSearchesCatalogTableReturn = ReturnType<typeof useSearchesCatalogTable>;\n"],"mappings":"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"}
package/dist/index.d.mts CHANGED
@@ -93,13 +93,14 @@ import { SearchCatalogCardContext, SearchCatalogCardContextValue, useSearchCatal
93
93
  import { SearchCatalogContext, SearchCatalogContextValue, useSearchCatalogContext } from "./context/search-catalog-context.mjs";
94
94
  import { SearchesCatalogCardContext, SearchesCatalogCardContextValue, useSearchesCatalogCard } from "./context/searches-catalog-card-context.mjs";
95
95
  import { SearchesCatalogContext, SearchesCatalogContextValue, useSearchesCatalogContext } from "./context/searches-catalog-context.mjs";
96
+ import { CatalogFilterMeta, CatalogSearchFeatures, catalogSearchFilter, catalogSearchSort, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon } from "./utils/catalog-helpers.mjs";
97
+ import { CatalogTableFeatures, catalogTableFeatures, createCatalogColumnHelper, useCatalogTable } from "./hooks/catalog-table.mjs";
96
98
  import { useFieldError } from "./hooks/use-field-error.mjs";
97
99
  import { UsePipeFormOptions, usePipeForm } from "./hooks/use-pipe-form.mjs";
98
100
  import { UsePlaybookFormOptions, usePlaybookForm } from "./hooks/use-playbook-form.mjs";
99
101
  import { UseSearchFormOptions, useSearchForm } from "./hooks/use-search-form.mjs";
100
102
  import { UseSheetEffectFormOptions, useSheetEffectForm } from "./hooks/use-sheet-effect-form.mjs";
101
103
  import { UseStreamFormOptions, useStreamForm } from "./hooks/use-stream-form.mjs";
102
- import { fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon } from "./utils/catalog-helpers.mjs";
103
104
  import { EmojiGlyph } from "./widgets/emoji-glyph.mjs";
104
105
  import { FieldTypeBadge } from "./widgets/field-type-badge.mjs";
105
106
  import { IconGlyph } from "./widgets/icon-glyph.mjs";
@@ -108,4 +109,4 @@ import { PricingBadge } from "./widgets/pricing-badge.mjs";
108
109
  import { ProviderLogo } from "./widgets/provider-logo.mjs";
109
110
  import { WidgetStrip } from "./widgets/widget-strip.mjs";
110
111
  import { WidgetView } from "./widgets/widget-view.mjs";
111
- export { Alert, AlertDescription, type AlertProps, AlertTitle, type AlertVariant, type AnyFieldProps as AnyFieldHandle, AvatarGroup, type AvatarGroupProps, type AvatarGroupState, CatalogCard, CatalogCardBadge, type CatalogCardBadgeProps, CatalogCardBadges, type CatalogCardBadgesProps, CatalogCardDescription, type CatalogCardDescriptionProps, CatalogCardHeader, type CatalogCardHeaderProps, type CatalogCardProps, CatalogCardTitle, type CatalogCardTitleProps, CatalogCategorySection, type CatalogCategorySectionProps, type CatalogClassNames, type CatalogComponentOverrides, type CatalogConfig, CatalogCopyId, type CatalogCopyIdProps, CatalogCreditBadge, type CatalogCreditBadgeProps, CatalogDocsBadge, type CatalogDocsBadgeProps, CatalogFieldBadge, type CatalogFieldBadgeProps, type CatalogFieldBadgeState, CatalogProvider, CatalogProviderAvatars, type CatalogProviderAvatarsProps, type CatalogProviderProps, CatalogRoot, type CostMode, type EffectCardData, EffectCatalog, EffectCatalogCard, EffectCatalogCardContext, type EffectCatalogCardContextValue, type EffectCatalogCardProps, type EffectCatalogCardState, EffectCatalogCategoryFilter, type EffectCatalogCategoryFilterProps, type EffectCatalogCategoryFilterState, EffectCatalogContext, type EffectCatalogContextValue, EffectCatalogEmpty, type EffectCatalogEmptyProps, type EffectCatalogEmptyState, type EffectCatalogInstanceProps, EffectCatalogList, type EffectCatalogListProps, type EffectCatalogListState, type EffectCatalogProps, EffectCatalogSearchFilter, type EffectCatalogSearchFilterProps, type EffectCatalogSearchFilterState, type EffectCatalogZeroConfigProps, EmojiGlyph, type FieldAdapterMap, type GeneratedFieldProps as FieldHandle, type FieldKind, type FieldMeta, FieldRenderer, FieldTypeBadge, type FormClassNames, type FormComponents, type FormConfig, type FormErrorEntry, type FormErrors, type FormFieldState, type FormHandle, FormProvider, type FormResetFieldOptions, type FormResetOptions, FormRoot, type FormSetValueOptions, type FormStateSnapshot, type GroupMap, type GroupOverride, IconGlyph, type InputFieldEntries, LogoUrl, type OutputFieldEntries, type PathMap, type PathOverride, type ActiveFilter as PipeActiveFilter, type PipeCardData, PipeCatalog, PipeCatalogActiveFilters, type PipeCatalogActiveFiltersProps, type PipeCatalogActiveFiltersState, PipeCatalogCard, PipeCatalogCardContext, type PipeCatalogCardContextValue, type PipeCatalogCardProps, PipeCatalogCategoryFilter, type PipeCatalogCategoryFilterProps, type PipeCatalogCategoryFilterState, PipeCatalogColumnFilter, type PipeCatalogColumnFilterProps, PipeCatalogColumnFilters, type PipeCatalogColumnFiltersProps, PipeCatalogContext, type PipeCatalogContextValue, PipeCatalogEmpty, type PipeCatalogEmptyProps, type PipeCatalogEmptyState, PipeCatalogInputFieldFilter, type PipeCatalogInputFieldFilterProps, type PipeCatalogInstanceProps, PipeCatalogList, type PipeCatalogListProps, type PipeCatalogListState, PipeCatalogOutputFieldFilter, type PipeCatalogOutputFieldFilterProps, type PipeCatalogProps, PipeCatalogProviderFilter, type PipeCatalogProviderFilterProps, PipeCatalogSearchFilter, type PipeCatalogSearchFilterProps, type PipeCatalogSearchFilterState, PipeCatalogTagFilter, type PipeCatalogTagFilterProps, type PipeCatalogZeroConfigProps, type PipeColumnFilterId, type ColumnFilterState as PipeColumnFilterState, PipeForm, PipeFormContent, PipeFormContext, PipeFormErrors, PipeFormField, PipeFormFooter, PipeFormGroup, PipeFormHeader, type PipeFormInstanceProps, type PipeFormProps, PipeFormSection, PipeFormSubmitButton, PipeFormTitle, type PipeFormZeroConfigProps, PricingBadge, ProviderLogo, type ActiveFilter$1 as SearchActiveFilter, type SearchCardData, SearchCatalog, SearchCatalogActiveFilters, type SearchCatalogActiveFiltersProps, type SearchCatalogActiveFiltersState, SearchCatalogCard, SearchCatalogCardContext, type SearchCatalogCardContextValue, type SearchCatalogCardProps, SearchCatalogCategoryFilter, type SearchCatalogCategoryFilterProps, type SearchCatalogCategoryFilterState, SearchCatalogColumnFilter, type SearchCatalogColumnFilterProps, SearchCatalogColumnFilters, type SearchCatalogColumnFiltersProps, SearchCatalogContext, type SearchCatalogContextValue, SearchCatalogEmpty, type SearchCatalogEmptyProps, type SearchCatalogEmptyState, type SearchCatalogInstanceProps, SearchCatalogList, type SearchCatalogListProps, type SearchCatalogListState, SearchCatalogOutputFieldFilter, type SearchCatalogOutputFieldFilterProps, type SearchCatalogProps, SearchCatalogProviderFilter, type SearchCatalogProviderFilterProps, SearchCatalogSearchFilter, type SearchCatalogSearchFilterProps, type SearchCatalogSearchFilterState, SearchCatalogTagFilter, type SearchCatalogTagFilterProps, type SearchCatalogZeroConfigProps, type SearchColumnFilterId, type ColumnFilterState$1 as SearchColumnFilterState, SearchForm, SearchFormContent, SearchFormContext, SearchFormErrors, SearchFormField, SearchFormFooter, SearchFormGroup, SearchFormHeader, type SearchFormInstanceProps, type SearchFormProps, SearchFormSection, SearchFormSubmitButton, SearchFormTitle, type SearchFormZeroConfigProps, type SearchOutputFieldEntries, type ActiveFilter$2 as SearchesActiveFilter, type SearchesCardData, SearchesCatalog, SearchesCatalogActiveFilters, type SearchesCatalogActiveFiltersProps, type SearchesCatalogActiveFiltersState, SearchesCatalogCard, SearchesCatalogCardContext, type SearchesCatalogCardContextValue, type SearchesCatalogCardProps, SearchesCatalogCategoryFilter, type SearchesCatalogCategoryFilterProps, type SearchesCatalogCategoryFilterState, SearchesCatalogColumnFilter, type SearchesCatalogColumnFilterProps, SearchesCatalogColumnFilters, type SearchesCatalogColumnFiltersProps, SearchesCatalogContext, type SearchesCatalogContextValue, SearchesCatalogEmpty, type SearchesCatalogEmptyProps, type SearchesCatalogEmptyState, type SearchesCatalogInstanceProps, SearchesCatalogList, type SearchesCatalogListProps, type SearchesCatalogListState, SearchesCatalogOutputFieldFilter, type SearchesCatalogOutputFieldFilterProps, type SearchesCatalogProps, SearchesCatalogProviderFilter, type SearchesCatalogProviderFilterProps, SearchesCatalogSearchFilter, type SearchesCatalogSearchFilterProps, type SearchesCatalogSearchFilterState, SearchesCatalogTagFilter, type SearchesCatalogTagFilterProps, type SearchesCatalogZeroConfigProps, type SearchesColumnFilterId, type ColumnFilterState$2 as SearchesColumnFilterState, type SearchesOutputFieldEntries, type SectionMap, type SectionOverride, type UseEffectCatalogTableReturn, type UsePipeCatalogTableReturn, type UsePipeFormOptions, type UsePlaybookFormOptions, type UseSearchCatalogTableReturn, type UseSearchFormOptions, type UseSearchesCatalogTableReturn, type UseSheetEffectFormOptions, type UseStreamFormOptions, WidgetStrip, WidgetView, alertVariants, defaultAdapters, fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon, useCatalogConfig, useEffectCatalogCard, useEffectCatalogContext, useEffectCatalogTable, useFieldError, useFormAlert, useFormConfig, usePipeCatalogCard, usePipeCatalogContext, usePipeCatalogTable, usePipeForm, usePipeFormContext, usePlaybookForm, usePortalContainer, useSearchCatalogCard, useSearchCatalogContext, useSearchCatalogTable, useSearchForm, useSearchFormContext, useSearchesCatalogCard, useSearchesCatalogContext, useSearchesCatalogTable, useSheetEffectForm, useStreamForm };
112
+ export { Alert, AlertDescription, type AlertProps, AlertTitle, type AlertVariant, type AnyFieldProps as AnyFieldHandle, AvatarGroup, type AvatarGroupProps, type AvatarGroupState, CatalogCard, CatalogCardBadge, type CatalogCardBadgeProps, CatalogCardBadges, type CatalogCardBadgesProps, CatalogCardDescription, type CatalogCardDescriptionProps, CatalogCardHeader, type CatalogCardHeaderProps, type CatalogCardProps, CatalogCardTitle, type CatalogCardTitleProps, CatalogCategorySection, type CatalogCategorySectionProps, type CatalogClassNames, type CatalogComponentOverrides, type CatalogConfig, CatalogCopyId, type CatalogCopyIdProps, CatalogCreditBadge, type CatalogCreditBadgeProps, CatalogDocsBadge, type CatalogDocsBadgeProps, CatalogFieldBadge, type CatalogFieldBadgeProps, type CatalogFieldBadgeState, type CatalogFilterMeta, CatalogProvider, CatalogProviderAvatars, type CatalogProviderAvatarsProps, type CatalogProviderProps, CatalogRoot, type CatalogSearchFeatures, type CatalogTableFeatures, type CostMode, type EffectCardData, EffectCatalog, EffectCatalogCard, EffectCatalogCardContext, type EffectCatalogCardContextValue, type EffectCatalogCardProps, type EffectCatalogCardState, EffectCatalogCategoryFilter, type EffectCatalogCategoryFilterProps, type EffectCatalogCategoryFilterState, EffectCatalogContext, type EffectCatalogContextValue, EffectCatalogEmpty, type EffectCatalogEmptyProps, type EffectCatalogEmptyState, type EffectCatalogInstanceProps, EffectCatalogList, type EffectCatalogListProps, type EffectCatalogListState, type EffectCatalogProps, EffectCatalogSearchFilter, type EffectCatalogSearchFilterProps, type EffectCatalogSearchFilterState, type EffectCatalogZeroConfigProps, EmojiGlyph, type FieldAdapterMap, type GeneratedFieldProps as FieldHandle, type FieldKind, type FieldMeta, FieldRenderer, FieldTypeBadge, type FormClassNames, type FormComponents, type FormConfig, type FormErrorEntry, type FormErrors, type FormFieldState, type FormHandle, FormProvider, type FormResetFieldOptions, type FormResetOptions, FormRoot, type FormSetValueOptions, type FormStateSnapshot, type GroupMap, type GroupOverride, IconGlyph, type InputFieldEntries, LogoUrl, type OutputFieldEntries, type PathMap, type PathOverride, type ActiveFilter as PipeActiveFilter, type PipeCardData, PipeCatalog, PipeCatalogActiveFilters, type PipeCatalogActiveFiltersProps, type PipeCatalogActiveFiltersState, PipeCatalogCard, PipeCatalogCardContext, type PipeCatalogCardContextValue, type PipeCatalogCardProps, PipeCatalogCategoryFilter, type PipeCatalogCategoryFilterProps, type PipeCatalogCategoryFilterState, PipeCatalogColumnFilter, type PipeCatalogColumnFilterProps, PipeCatalogColumnFilters, type PipeCatalogColumnFiltersProps, PipeCatalogContext, type PipeCatalogContextValue, PipeCatalogEmpty, type PipeCatalogEmptyProps, type PipeCatalogEmptyState, PipeCatalogInputFieldFilter, type PipeCatalogInputFieldFilterProps, type PipeCatalogInstanceProps, PipeCatalogList, type PipeCatalogListProps, type PipeCatalogListState, PipeCatalogOutputFieldFilter, type PipeCatalogOutputFieldFilterProps, type PipeCatalogProps, PipeCatalogProviderFilter, type PipeCatalogProviderFilterProps, PipeCatalogSearchFilter, type PipeCatalogSearchFilterProps, type PipeCatalogSearchFilterState, PipeCatalogTagFilter, type PipeCatalogTagFilterProps, type PipeCatalogZeroConfigProps, type PipeColumnFilterId, type ColumnFilterState as PipeColumnFilterState, PipeForm, PipeFormContent, PipeFormContext, PipeFormErrors, PipeFormField, PipeFormFooter, PipeFormGroup, PipeFormHeader, type PipeFormInstanceProps, type PipeFormProps, PipeFormSection, PipeFormSubmitButton, PipeFormTitle, type PipeFormZeroConfigProps, PricingBadge, ProviderLogo, type ActiveFilter$1 as SearchActiveFilter, type SearchCardData, SearchCatalog, SearchCatalogActiveFilters, type SearchCatalogActiveFiltersProps, type SearchCatalogActiveFiltersState, SearchCatalogCard, SearchCatalogCardContext, type SearchCatalogCardContextValue, type SearchCatalogCardProps, SearchCatalogCategoryFilter, type SearchCatalogCategoryFilterProps, type SearchCatalogCategoryFilterState, SearchCatalogColumnFilter, type SearchCatalogColumnFilterProps, SearchCatalogColumnFilters, type SearchCatalogColumnFiltersProps, SearchCatalogContext, type SearchCatalogContextValue, SearchCatalogEmpty, type SearchCatalogEmptyProps, type SearchCatalogEmptyState, type SearchCatalogInstanceProps, SearchCatalogList, type SearchCatalogListProps, type SearchCatalogListState, SearchCatalogOutputFieldFilter, type SearchCatalogOutputFieldFilterProps, type SearchCatalogProps, SearchCatalogProviderFilter, type SearchCatalogProviderFilterProps, SearchCatalogSearchFilter, type SearchCatalogSearchFilterProps, type SearchCatalogSearchFilterState, SearchCatalogTagFilter, type SearchCatalogTagFilterProps, type SearchCatalogZeroConfigProps, type SearchColumnFilterId, type ColumnFilterState$1 as SearchColumnFilterState, SearchForm, SearchFormContent, SearchFormContext, SearchFormErrors, SearchFormField, SearchFormFooter, SearchFormGroup, SearchFormHeader, type SearchFormInstanceProps, type SearchFormProps, SearchFormSection, SearchFormSubmitButton, SearchFormTitle, type SearchFormZeroConfigProps, type SearchOutputFieldEntries, type ActiveFilter$2 as SearchesActiveFilter, type SearchesCardData, SearchesCatalog, SearchesCatalogActiveFilters, type SearchesCatalogActiveFiltersProps, type SearchesCatalogActiveFiltersState, SearchesCatalogCard, SearchesCatalogCardContext, type SearchesCatalogCardContextValue, type SearchesCatalogCardProps, SearchesCatalogCategoryFilter, type SearchesCatalogCategoryFilterProps, type SearchesCatalogCategoryFilterState, SearchesCatalogColumnFilter, type SearchesCatalogColumnFilterProps, SearchesCatalogColumnFilters, type SearchesCatalogColumnFiltersProps, SearchesCatalogContext, type SearchesCatalogContextValue, SearchesCatalogEmpty, type SearchesCatalogEmptyProps, type SearchesCatalogEmptyState, type SearchesCatalogInstanceProps, SearchesCatalogList, type SearchesCatalogListProps, type SearchesCatalogListState, SearchesCatalogOutputFieldFilter, type SearchesCatalogOutputFieldFilterProps, type SearchesCatalogProps, SearchesCatalogProviderFilter, type SearchesCatalogProviderFilterProps, SearchesCatalogSearchFilter, type SearchesCatalogSearchFilterProps, type SearchesCatalogSearchFilterState, SearchesCatalogTagFilter, type SearchesCatalogTagFilterProps, type SearchesCatalogZeroConfigProps, type SearchesColumnFilterId, type ColumnFilterState$2 as SearchesColumnFilterState, type SearchesOutputFieldEntries, type SectionMap, type SectionOverride, type UseEffectCatalogTableReturn, type UsePipeCatalogTableReturn, type UsePipeFormOptions, type UsePlaybookFormOptions, type UseSearchCatalogTableReturn, type UseSearchFormOptions, type UseSearchesCatalogTableReturn, type UseSheetEffectFormOptions, type UseStreamFormOptions, WidgetStrip, WidgetView, alertVariants, catalogSearchFilter, catalogSearchSort, catalogTableFeatures, createCatalogColumnHelper, defaultAdapters, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon, useCatalogConfig, useCatalogTable, useEffectCatalogCard, useEffectCatalogContext, useEffectCatalogTable, useFieldError, useFormAlert, useFormConfig, usePipeCatalogCard, usePipeCatalogContext, usePipeCatalogTable, usePipeForm, usePipeFormContext, usePlaybookForm, usePortalContainer, useSearchCatalogCard, useSearchCatalogContext, useSearchCatalogTable, useSearchForm, useSearchFormContext, useSearchesCatalogCard, useSearchesCatalogContext, useSearchesCatalogTable, useSheetEffectForm, useStreamForm };
package/dist/index.mjs CHANGED
@@ -13,7 +13,8 @@ import { EffectCatalogCard } from "./components/compound/effect-catalog/card.mjs
13
13
  import { EffectCatalogCategoryFilter } from "./components/compound/effect-catalog/category-filter.mjs";
14
14
  import { EffectCatalogEmpty } from "./components/compound/effect-catalog/empty.mjs";
15
15
  import { EffectCatalogList } from "./components/compound/effect-catalog/list.mjs";
16
- import { fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon } from "./utils/catalog-helpers.mjs";
16
+ import { catalogSearchFilter, catalogSearchSort, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon } from "./utils/catalog-helpers.mjs";
17
+ import { catalogTableFeatures, createCatalogColumnHelper, useCatalogTable } from "./hooks/catalog-table.mjs";
17
18
  import { useEffectCatalogTable } from "./hooks/use-effect-catalog-table.mjs";
18
19
  import { EffectCatalogSearchFilter } from "./components/compound/effect-catalog/search-filter.mjs";
19
20
  import { EffectCatalog } from "./components/compound/effect-catalog/root.mjs";
@@ -103,4 +104,4 @@ import { usePlaybookForm } from "./hooks/use-playbook-form.mjs";
103
104
  import { useSheetEffectForm } from "./hooks/use-sheet-effect-form.mjs";
104
105
  import { useStreamForm } from "./hooks/use-stream-form.mjs";
105
106
 
106
- export { Alert, AlertDescription, AlertTitle, AvatarGroup, CatalogCard, CatalogCardBadge, CatalogCardBadges, CatalogCardDescription, CatalogCardHeader, CatalogCardTitle, CatalogCategorySection, CatalogCopyId, CatalogCreditBadge, CatalogDocsBadge, CatalogFieldBadge, CatalogProvider, CatalogProviderAvatars, CatalogRoot, EffectCatalog, EffectCatalogCard, EffectCatalogCardContext, EffectCatalogCategoryFilter, EffectCatalogContext, EffectCatalogEmpty, EffectCatalogList, EffectCatalogSearchFilter, EmojiGlyph, FieldRenderer, FieldTypeBadge, FormProvider, FormRoot, IconGlyph, LogoUrl, PipeCatalog, PipeCatalogActiveFilters, PipeCatalogCard, PipeCatalogCardContext, PipeCatalogCategoryFilter, PipeCatalogColumnFilter, PipeCatalogColumnFilters, PipeCatalogContext, PipeCatalogEmpty, PipeCatalogInputFieldFilter, PipeCatalogList, PipeCatalogOutputFieldFilter, PipeCatalogProviderFilter, PipeCatalogSearchFilter, PipeCatalogTagFilter, PipeForm, PipeFormContent, PipeFormContext, PipeFormErrors, PipeFormField, PipeFormFooter, PipeFormGroup, PipeFormHeader, PipeFormSection, PipeFormSubmitButton, PipeFormTitle, PricingBadge, ProviderLogo, SearchCatalog, SearchCatalogActiveFilters, SearchCatalogCard, SearchCatalogCardContext, SearchCatalogCategoryFilter, SearchCatalogColumnFilter, SearchCatalogColumnFilters, SearchCatalogContext, SearchCatalogEmpty, SearchCatalogList, SearchCatalogOutputFieldFilter, SearchCatalogProviderFilter, SearchCatalogSearchFilter, SearchCatalogTagFilter, SearchForm, SearchFormContent, SearchFormContext, SearchFormErrors, SearchFormField, SearchFormFooter, SearchFormGroup, SearchFormHeader, SearchFormSection, SearchFormSubmitButton, SearchFormTitle, SearchesCatalog, SearchesCatalogActiveFilters, SearchesCatalogCard, SearchesCatalogCardContext, SearchesCatalogCategoryFilter, SearchesCatalogColumnFilter, SearchesCatalogColumnFilters, SearchesCatalogContext, SearchesCatalogEmpty, SearchesCatalogList, SearchesCatalogOutputFieldFilter, SearchesCatalogProviderFilter, SearchesCatalogSearchFilter, SearchesCatalogTagFilter, WidgetStrip, WidgetView, alertVariants, defaultAdapters, fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon, useCatalogConfig, useEffectCatalogCard, useEffectCatalogContext, useEffectCatalogTable, useFieldError, useFormAlert, useFormConfig, usePipeCatalogCard, usePipeCatalogContext, usePipeCatalogTable, usePipeForm, usePipeFormContext, usePlaybookForm, usePortalContainer, useSearchCatalogCard, useSearchCatalogContext, useSearchCatalogTable, useSearchForm, useSearchFormContext, useSearchesCatalogCard, useSearchesCatalogContext, useSearchesCatalogTable, useSheetEffectForm, useStreamForm };
107
+ export { Alert, AlertDescription, AlertTitle, AvatarGroup, CatalogCard, CatalogCardBadge, CatalogCardBadges, CatalogCardDescription, CatalogCardHeader, CatalogCardTitle, CatalogCategorySection, CatalogCopyId, CatalogCreditBadge, CatalogDocsBadge, CatalogFieldBadge, CatalogProvider, CatalogProviderAvatars, CatalogRoot, EffectCatalog, EffectCatalogCard, EffectCatalogCardContext, EffectCatalogCategoryFilter, EffectCatalogContext, EffectCatalogEmpty, EffectCatalogList, EffectCatalogSearchFilter, EmojiGlyph, FieldRenderer, FieldTypeBadge, FormProvider, FormRoot, IconGlyph, LogoUrl, PipeCatalog, PipeCatalogActiveFilters, PipeCatalogCard, PipeCatalogCardContext, PipeCatalogCategoryFilter, PipeCatalogColumnFilter, PipeCatalogColumnFilters, PipeCatalogContext, PipeCatalogEmpty, PipeCatalogInputFieldFilter, PipeCatalogList, PipeCatalogOutputFieldFilter, PipeCatalogProviderFilter, PipeCatalogSearchFilter, PipeCatalogTagFilter, PipeForm, PipeFormContent, PipeFormContext, PipeFormErrors, PipeFormField, PipeFormFooter, PipeFormGroup, PipeFormHeader, PipeFormSection, PipeFormSubmitButton, PipeFormTitle, PricingBadge, ProviderLogo, SearchCatalog, SearchCatalogActiveFilters, SearchCatalogCard, SearchCatalogCardContext, SearchCatalogCategoryFilter, SearchCatalogColumnFilter, SearchCatalogColumnFilters, SearchCatalogContext, SearchCatalogEmpty, SearchCatalogList, SearchCatalogOutputFieldFilter, SearchCatalogProviderFilter, SearchCatalogSearchFilter, SearchCatalogTagFilter, SearchForm, SearchFormContent, SearchFormContext, SearchFormErrors, SearchFormField, SearchFormFooter, SearchFormGroup, SearchFormHeader, SearchFormSection, SearchFormSubmitButton, SearchFormTitle, SearchesCatalog, SearchesCatalogActiveFilters, SearchesCatalogCard, SearchesCatalogCardContext, SearchesCatalogCategoryFilter, SearchesCatalogColumnFilter, SearchesCatalogColumnFilters, SearchesCatalogContext, SearchesCatalogEmpty, SearchesCatalogList, SearchesCatalogOutputFieldFilter, SearchesCatalogProviderFilter, SearchesCatalogSearchFilter, SearchesCatalogTagFilter, WidgetStrip, WidgetView, alertVariants, catalogSearchFilter, catalogSearchSort, catalogTableFeatures, createCatalogColumnHelper, defaultAdapters, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon, useCatalogConfig, useCatalogTable, useEffectCatalogCard, useEffectCatalogContext, useEffectCatalogTable, useFieldError, useFormAlert, useFormConfig, usePipeCatalogCard, usePipeCatalogContext, usePipeCatalogTable, usePipeForm, usePipeFormContext, usePlaybookForm, usePortalContainer, useSearchCatalogCard, useSearchCatalogContext, useSearchCatalogTable, useSearchForm, useSearchFormContext, useSearchesCatalogCard, useSearchesCatalogContext, useSearchesCatalogTable, useSheetEffectForm, useStreamForm };
@@ -1,12 +1,29 @@
1
1
  import * as _$react from "react";
2
- import { RecordFieldStatus, RecordFieldType } from "@pipe0/base";
2
+ import { ComponentType } from "react";
3
+ import { RecordFieldFormat, RecordFieldStatus, RecordFieldType } from "@pipe0/base";
3
4
  import * as _$lucide_react0 from "lucide-react";
4
- import { FilterFn } from "@tanstack/react-table";
5
+ import { FilterFn, RowData, SortFn, TableFeatures } from "@tanstack/react-table";
6
+ import { RankingInfo } from "@tanstack/match-sorter-utils";
5
7
 
6
8
  //#region src/utils/catalog-helpers.d.ts
7
9
  declare function getFieldTypeIcon(fieldType: RecordFieldType): _$react.ForwardRefExoticComponent<Omit<_$lucide_react0.LucideProps, "ref"> & _$react.RefAttributes<SVGSVGElement>>;
10
+ /**
11
+ * Column icon: the format is the expressive signal (an email column looks
12
+ * different from a date column), the type is the fallback for untyped fields.
13
+ */
14
+ declare function getFieldFormatIcon(format: RecordFieldFormat, fieldType: RecordFieldType): ComponentType | _$react.ForwardRefExoticComponent<Omit<_$lucide_react0.LucideProps, "ref"> & _$react.RefAttributes<SVGSVGElement>>;
8
15
  declare function getFieldStatusIcon(fieldStatus: RecordFieldStatus): _$react.ForwardRefExoticComponent<Omit<_$lucide_react0.LucideProps, "ref"> & _$react.RefAttributes<SVGSVGElement>>;
9
- declare const fuzzyFilter: FilterFn<any>;
16
+ /** Filter meta the catalog filter fns attach to rows, read back by the sort fns. */
17
+ interface CatalogFilterMeta {
18
+ itemRank?: RankingInfo;
19
+ searchScore?: number;
20
+ }
21
+ type CatalogSearchFeatures = TableFeatures & {
22
+ filterMeta: CatalogFilterMeta;
23
+ };
24
+ declare const fuzzyFilter: FilterFn<CatalogSearchFeatures, RowData>;
25
+ declare const catalogSearchFilter: FilterFn<CatalogSearchFeatures, RowData>;
26
+ declare const catalogSearchSort: SortFn<CatalogSearchFeatures, RowData>;
10
27
  //#endregion
11
- export { fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon };
28
+ export { CatalogFilterMeta, CatalogSearchFeatures, catalogSearchFilter, catalogSearchSort, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon };
12
29
  //# sourceMappingURL=catalog-helpers.d.mts.map
@@ -1 +1 @@
1
- {"version":3,"file":"catalog-helpers.d.mts","names":[],"sources":["../../src/utils/catalog-helpers.tsx"],"mappings":";;;;;;iBAqCgB,gBAAA,CAAiB,SAAA,EAAW,eAAA,GAAe,OAAA,CAAA,yBAAA,CAAA,IAAA,CAAA,eAAA,CAAA,WAAA,WAAA,OAAA,CAAA,aAAA,CAAA,aAAA;AAAA,iBAI3C,kBAAA,CAAmB,WAAA,EAAa,iBAAA,GAAiB,OAAA,CAAA,yBAAA,CAAA,IAAA,CAAA,eAAA,CAAA,WAAA,WAAA,OAAA,CAAA,aAAA,CAAA,aAAA;AAAA,cAIpD,WAAA,EAAa,QAAA"}
1
+ {"version":3,"file":"catalog-helpers.d.mts","names":[],"sources":["../../src/utils/catalog-helpers.tsx"],"mappings":";;;;;;;;iBAqDgB,gBAAA,CAAiB,SAAA,EAAW,eAAA,GAAe,OAAA,CAAA,yBAAA,CAAA,IAAA,CAAA,eAAA,CAAA,WAAA,WAAA,OAAA,CAAA,aAAA,CAAA,aAAA;;;;AAA3D;iBA+BgB,kBAAA,CAAmB,MAAA,EAAQ,iBAAA,EAAmB,SAAA,EAAW,eAAA,GAAe,aAAA,GAAA,OAAA,CAAA,yBAAA,CAAA,IAAA,CAAA,eAAA,CAAA,WAAA,WAAA,OAAA,CAAA,aAAA,CAAA,aAAA;AAAA,iBAIxE,kBAAA,CAAmB,WAAA,EAAa,iBAAA,GAAiB,OAAA,CAAA,yBAAA,CAAA,IAAA,CAAA,eAAA,CAAA,WAAA,WAAA,OAAA,CAAA,aAAA,CAAA,aAAA;;UAKhD,iBAAA;EACf,QAAA,GAAW,WAAA;EACX,WAAA;AAAA;AAAA,KAKU,qBAAA,GAAwB,aAAA;EAAkB,UAAA,EAAY,iBAAA;AAAA;AAAA,cAErD,WAAA,EAAa,QAAA,CAAS,qBAAA,EAAuB,OAAA;AAAA,cAc7C,mBAAA,EAAqB,QAAA,CAAS,qBAAA,EAAuB,OAAA;AAAA,cAcrD,iBAAA,EAAmB,MAAA,CAAO,qBAAA,EAAuB,OAAA"}
@@ -1,5 +1,5 @@
1
1
  import { scoreCatalogSearch } from "@pipe0/base";
2
- import { BookDashed, Bookmark, Braces, CheckCheck, Hash, HelpCircle, Loader, Pause, ToggleRight, TriangleDashed, Type, X } from "lucide-react";
2
+ import { AtSign, BookDashed, Bookmark, Braces, Calendar, CalendarClock, CheckCheck, Coins, Contact, Globe, Hash, HelpCircle, Loader, MapPin, Pause, Percent, Phone, TextAlignStart, ToggleRight, TriangleDashed, Type, X } from "lucide-react";
3
3
  import { rankItem } from "@tanstack/match-sorter-utils";
4
4
 
5
5
  //#region src/utils/catalog-helpers.tsx
@@ -22,17 +22,46 @@ const FieldTypeIconMap = {
22
22
  function getFieldTypeIcon(fieldType) {
23
23
  return FieldTypeIconMap[fieldType];
24
24
  }
25
+ const FieldFormatIconMap = {
26
+ email: AtSign,
27
+ url: Globe,
28
+ website_url: Globe,
29
+ domain: Globe,
30
+ profile_url: Contact,
31
+ phone: Phone,
32
+ date: Calendar,
33
+ datetime: CalendarClock,
34
+ address_line_1: MapPin,
35
+ zip_code: Hash,
36
+ currency: Coins,
37
+ percent: Percent,
38
+ markdown: TextAlignStart,
39
+ long_text: TextAlignStart,
40
+ text: Type,
41
+ int: Hash,
42
+ decimal: Hash,
43
+ json_object: Braces,
44
+ json_list: Braces,
45
+ json_list_string: Braces
46
+ };
47
+ /**
48
+ * Column icon: the format is the expressive signal (an email column looks
49
+ * different from a date column), the type is the fallback for untyped fields.
50
+ */
51
+ function getFieldFormatIcon(format, fieldType) {
52
+ return (format ? FieldFormatIconMap[format] : void 0) ?? getFieldTypeIcon(fieldType);
53
+ }
25
54
  function getFieldStatusIcon(fieldStatus) {
26
55
  return fieldStatusIconMap[fieldStatus];
27
56
  }
28
57
  const fuzzyFilter = (row, columnId, value, addMeta) => {
29
58
  const itemRank = rankItem(row.getValue(columnId), value);
30
- addMeta({ itemRank });
59
+ addMeta?.({ itemRank });
31
60
  return itemRank.passed;
32
61
  };
33
62
  const catalogSearchFilter = (row, columnId, value, addMeta) => {
34
63
  const score = scoreCatalogSearch(row.getValue(columnId), String(value ?? ""));
35
- addMeta({ searchScore: score });
64
+ addMeta?.({ searchScore: score });
36
65
  return score > 0;
37
66
  };
38
67
  const catalogSearchSort = (rowA, rowB, columnId) => {
@@ -40,5 +69,5 @@ const catalogSearchSort = (rowA, rowB, columnId) => {
40
69
  };
41
70
 
42
71
  //#endregion
43
- export { catalogSearchFilter, catalogSearchSort, fuzzyFilter, getFieldStatusIcon, getFieldTypeIcon };
72
+ export { catalogSearchFilter, catalogSearchSort, fuzzyFilter, getFieldFormatIcon, getFieldStatusIcon, getFieldTypeIcon };
44
73
  //# sourceMappingURL=catalog-helpers.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"catalog-helpers.mjs","names":[],"sources":["../../src/utils/catalog-helpers.tsx"],"sourcesContent":["import { type RecordFieldStatus, type RecordFieldType, scoreCatalogSearch } from \"@pipe0/base\";\nimport { rankItem } from \"@tanstack/match-sorter-utils\";\nimport type { FilterFn, SortingFn } from \"@tanstack/react-table\";\nimport {\n BookDashed,\n Bookmark,\n Braces,\n CheckCheck,\n Hash,\n HelpCircle,\n Loader,\n Pause,\n ToggleRight,\n TriangleDashed,\n Type,\n X,\n} from \"lucide-react\";\nimport type { ComponentType } from \"react\";\n\nconst fieldStatusIconMap = {\n completed: CheckCheck,\n failed: X,\n no_result: BookDashed,\n pending: Bookmark,\n processing: Loader,\n queued: Pause,\n skipped: TriangleDashed,\n} satisfies Record<RecordFieldStatus, ComponentType>;\n\nconst FieldTypeIconMap = {\n boolean: ToggleRight,\n json: Braces,\n number: Hash,\n string: Type,\n unknown: HelpCircle,\n} satisfies Record<RecordFieldType, ComponentType>;\n\nexport function getFieldTypeIcon(fieldType: RecordFieldType) {\n return FieldTypeIconMap[fieldType];\n}\n\nexport function getFieldStatusIcon(fieldStatus: RecordFieldStatus) {\n return fieldStatusIconMap[fieldStatus];\n}\n\nexport const fuzzyFilter: FilterFn<any> = (row, columnId, value, addMeta) => {\n const itemRank = rankItem(row.getValue(columnId), value);\n addMeta({ itemRank });\n return itemRank.passed;\n};\n\n// Global-filter fn for the catalog tables' hidden \"search\" column (its value\n// is a precomputed CatalogSearchTarget). Stashes the score so\n// catalogSearchSort can order rows by relevance while a query is active.\nexport const catalogSearchFilter: FilterFn<any> = (row, columnId, value, addMeta) => {\n const score = scoreCatalogSearch(row.getValue(columnId), String(value ?? \"\"));\n addMeta({ searchScore: score } as any);\n return score > 0;\n};\n\nexport const catalogSearchSort: SortingFn<any> = (rowA, rowB, columnId) => {\n const a = (rowA.columnFiltersMeta[columnId] as any)?.searchScore ?? 0;\n const b = (rowB.columnFiltersMeta[columnId] as any)?.searchScore ?? 0;\n return a - b; // paired with `desc: true` → highest score first\n};\n"],"mappings":";;;;;AAmBA,MAAM,qBAAqB;CACzB,WAAW;CACX,QAAQ;CACR,WAAW;CACX,SAAS;CACT,YAAY;CACZ,QAAQ;CACR,SAAS;CACV;AAED,MAAM,mBAAmB;CACvB,SAAS;CACT,MAAM;CACN,QAAQ;CACR,QAAQ;CACR,SAAS;CACV;AAED,SAAgB,iBAAiB,WAA4B;AAC3D,QAAO,iBAAiB;;AAG1B,SAAgB,mBAAmB,aAAgC;AACjE,QAAO,mBAAmB;;AAG5B,MAAa,eAA8B,KAAK,UAAU,OAAO,YAAY;CAC3E,MAAM,WAAW,SAAS,IAAI,SAAS,SAAS,EAAE,MAAM;AACxD,SAAQ,EAAE,UAAU,CAAC;AACrB,QAAO,SAAS;;AAMlB,MAAa,uBAAsC,KAAK,UAAU,OAAO,YAAY;CACnF,MAAM,QAAQ,mBAAmB,IAAI,SAAS,SAAS,EAAE,OAAO,SAAS,GAAG,CAAC;AAC7E,SAAQ,EAAE,aAAa,OAAO,CAAQ;AACtC,QAAO,QAAQ;;AAGjB,MAAa,qBAAqC,MAAM,MAAM,aAAa;AAGzE,SAFW,KAAK,kBAAkB,WAAmB,eAAe,MACzD,KAAK,kBAAkB,WAAmB,eAAe"}
1
+ {"version":3,"file":"catalog-helpers.mjs","names":[],"sources":["../../src/utils/catalog-helpers.tsx"],"sourcesContent":["import {\n type CatalogSearchTarget,\n type RecordFieldFormat,\n type RecordFieldStatus,\n type RecordFieldType,\n scoreCatalogSearch,\n} from \"@pipe0/base\";\nimport { type RankingInfo, rankItem } from \"@tanstack/match-sorter-utils\";\nimport type { FilterFn, RowData, SortFn, TableFeatures } from \"@tanstack/react-table\";\nimport {\n AtSign,\n BookDashed,\n Bookmark,\n Braces,\n Calendar,\n CalendarClock,\n CheckCheck,\n Coins,\n Contact,\n Globe,\n Hash,\n HelpCircle,\n Loader,\n MapPin,\n Pause,\n Percent,\n Phone,\n TextAlignStart,\n ToggleRight,\n TriangleDashed,\n Type,\n X,\n} from \"lucide-react\";\nimport type { ComponentType } from \"react\";\n\nconst fieldStatusIconMap = {\n completed: CheckCheck,\n failed: X,\n no_result: BookDashed,\n pending: Bookmark,\n processing: Loader,\n queued: Pause,\n skipped: TriangleDashed,\n} satisfies Record<RecordFieldStatus, ComponentType>;\n\nconst FieldTypeIconMap = {\n boolean: ToggleRight,\n json: Braces,\n number: Hash,\n string: Type,\n unknown: HelpCircle,\n} satisfies Record<RecordFieldType, ComponentType>;\n\nexport function getFieldTypeIcon(fieldType: RecordFieldType) {\n return FieldTypeIconMap[fieldType];\n}\n\nconst FieldFormatIconMap: Partial<Record<NonNullable<RecordFieldFormat>, ComponentType>> = {\n email: AtSign,\n url: Globe,\n website_url: Globe,\n domain: Globe,\n profile_url: Contact,\n phone: Phone,\n date: Calendar,\n datetime: CalendarClock,\n address_line_1: MapPin,\n zip_code: Hash,\n currency: Coins,\n percent: Percent,\n markdown: TextAlignStart,\n long_text: TextAlignStart,\n text: Type,\n int: Hash,\n decimal: Hash,\n json_object: Braces,\n json_list: Braces,\n json_list_string: Braces,\n};\n\n/**\n * Column icon: the format is the expressive signal (an email column looks\n * different from a date column), the type is the fallback for untyped fields.\n */\nexport function getFieldFormatIcon(format: RecordFieldFormat, fieldType: RecordFieldType) {\n return (format ? FieldFormatIconMap[format] : undefined) ?? getFieldTypeIcon(fieldType);\n}\n\nexport function getFieldStatusIcon(fieldStatus: RecordFieldStatus) {\n return fieldStatusIconMap[fieldStatus];\n}\n\n/** Filter meta the catalog filter fns attach to rows, read back by the sort fns. */\nexport interface CatalogFilterMeta {\n itemRank?: RankingInfo;\n searchScore?: number;\n}\n\n// Docs idiom (fuzzy-filtering guide): a features type that only carries the\n// meta shape, so these fns are not coupled to one exact features object.\nexport type CatalogSearchFeatures = TableFeatures & { filterMeta: CatalogFilterMeta };\n\nexport const fuzzyFilter: FilterFn<CatalogSearchFeatures, RowData> = (\n row,\n columnId,\n value,\n addMeta,\n) => {\n const itemRank = rankItem(row.getValue(columnId), value);\n addMeta?.({ itemRank });\n return itemRank.passed;\n};\n\n// Global-filter fn for the catalog tables' hidden \"search\" column (its value\n// is a precomputed CatalogSearchTarget). Stashes the score so\n// catalogSearchSort can order rows by relevance while a query is active.\nexport const catalogSearchFilter: FilterFn<CatalogSearchFeatures, RowData> = (\n row,\n columnId,\n value,\n addMeta,\n) => {\n const score = scoreCatalogSearch(\n row.getValue<CatalogSearchTarget>(columnId),\n String(value ?? \"\"),\n );\n addMeta?.({ searchScore: score });\n return score > 0;\n};\n\nexport const catalogSearchSort: SortFn<CatalogSearchFeatures, RowData> = (rowA, rowB, columnId) => {\n const a = rowA.columnFiltersMeta[columnId]?.searchScore ?? 0;\n const b = rowB.columnFiltersMeta[columnId]?.searchScore ?? 0;\n return a - b; // paired with `desc: true` → highest score first\n};\n"],"mappings":";;;;;AAmCA,MAAM,qBAAqB;CACzB,WAAW;CACX,QAAQ;CACR,WAAW;CACX,SAAS;CACT,YAAY;CACZ,QAAQ;CACR,SAAS;CACV;AAED,MAAM,mBAAmB;CACvB,SAAS;CACT,MAAM;CACN,QAAQ;CACR,QAAQ;CACR,SAAS;CACV;AAED,SAAgB,iBAAiB,WAA4B;AAC3D,QAAO,iBAAiB;;AAG1B,MAAM,qBAAqF;CACzF,OAAO;CACP,KAAK;CACL,aAAa;CACb,QAAQ;CACR,aAAa;CACb,OAAO;CACP,MAAM;CACN,UAAU;CACV,gBAAgB;CAChB,UAAU;CACV,UAAU;CACV,SAAS;CACT,UAAU;CACV,WAAW;CACX,MAAM;CACN,KAAK;CACL,SAAS;CACT,aAAa;CACb,WAAW;CACX,kBAAkB;CACnB;;;;;AAMD,SAAgB,mBAAmB,QAA2B,WAA4B;AACxF,SAAQ,SAAS,mBAAmB,UAAU,WAAc,iBAAiB,UAAU;;AAGzF,SAAgB,mBAAmB,aAAgC;AACjE,QAAO,mBAAmB;;AAa5B,MAAa,eACX,KACA,UACA,OACA,YACG;CACH,MAAM,WAAW,SAAS,IAAI,SAAS,SAAS,EAAE,MAAM;AACxD,WAAU,EAAE,UAAU,CAAC;AACvB,QAAO,SAAS;;AAMlB,MAAa,uBACX,KACA,UACA,OACA,YACG;CACH,MAAM,QAAQ,mBACZ,IAAI,SAA8B,SAAS,EAC3C,OAAO,SAAS,GAAG,CACpB;AACD,WAAU,EAAE,aAAa,OAAO,CAAC;AACjC,QAAO,QAAQ;;AAGjB,MAAa,qBAA6D,MAAM,MAAM,aAAa;AAGjG,SAFU,KAAK,kBAAkB,WAAW,eAAe,MACjD,KAAK,kBAAkB,WAAW,eAAe"}