@dbx-tools/search 0.6.108 → 0.6.111

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.
@@ -0,0 +1,79 @@
1
+ /**
2
+ * Adapter from AppKit's native AI Search provider to the dbx-tools extension
3
+ * contract used by federated search and agent tools.
4
+ *
5
+ * @module
6
+ */
7
+ import { ValidationError } from "@databricks/appkit";
8
+ import { search as sharedSearch, } from "@dbx-tools/shared-search";
9
+ import { string } from "@dbx-tools/shared-core";
10
+ import { indexConfigFor } from "./config.js";
11
+ function filters(value) {
12
+ if (!value)
13
+ return undefined;
14
+ const result = {};
15
+ for (const [key, item] of Object.entries(value)) {
16
+ if (typeof item === "string" ||
17
+ typeof item === "number" ||
18
+ typeof item === "boolean" ||
19
+ (Array.isArray(item) &&
20
+ item.every((entry) => typeof entry === "string" || typeof entry === "number"))) {
21
+ result[key] = item;
22
+ continue;
23
+ }
24
+ throw new ValidationError(`AI Search filter "${key}" must be a string, number, boolean, or string/number array`);
25
+ }
26
+ return result;
27
+ }
28
+ function hitId(data, primaryKey, index) {
29
+ const value = data[primaryKey ?? "id"] ?? Object.values(data)[0] ?? index;
30
+ return String(value);
31
+ }
32
+ function aliasFor(index, config) {
33
+ const alias = indexConfigFor(config, index)?.alias ?? string.trimToNull(index);
34
+ if (!alias)
35
+ throw new ValidationError("AI Search requires a configured index alias");
36
+ return alias;
37
+ }
38
+ /** Build a read backend that delegates every Vector Search query to AppKit. */
39
+ export function nativeAiSearchBackend(provider, config) {
40
+ const backend = {
41
+ supportsLifecycle: provider.providerKind !== "lakebase",
42
+ async search(index, query, options = {}) {
43
+ options.signal?.throwIfAborted();
44
+ const known = indexConfigFor(config, index);
45
+ const alias = aliasFor(index, config);
46
+ const resolvedQueryType = sharedSearch.toAiSearchQueryType(options.mode);
47
+ const resolvedFilters = filters(options.filter);
48
+ const response = await provider.query(alias, {
49
+ queryText: query,
50
+ numResults: options.limit ?? config.pageSize,
51
+ ...(options.columns ? { columns: [...options.columns] } : {}),
52
+ ...(resolvedQueryType ? { queryType: resolvedQueryType } : {}),
53
+ ...(resolvedFilters ? { filters: resolvedFilters } : {}),
54
+ });
55
+ options.signal?.throwIfAborted();
56
+ const hits = response.results
57
+ .map((result, resultIndex) => ({
58
+ id: hitId(result.data, known?.primaryKey, resultIndex),
59
+ score: result.score,
60
+ fields: result.data,
61
+ }))
62
+ .filter((hit) => options.scoreThreshold === undefined || hit.score >= options.scoreThreshold);
63
+ return { query, index, hits, count: hits.length };
64
+ },
65
+ };
66
+ const addDocuments = provider.addDocuments?.bind(provider);
67
+ if (!addDocuments)
68
+ return backend;
69
+ return {
70
+ ...backend,
71
+ async addDocuments(index, documents, signal) {
72
+ signal?.throwIfAborted();
73
+ const result = await addDocuments(aliasFor(index, config), documents);
74
+ signal?.throwIfAborted();
75
+ return result;
76
+ },
77
+ };
78
+ }
79
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibmF0aXZlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL25hdGl2ZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7R0FLRztBQUVILE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSxvQkFBb0IsQ0FBQztBQU1yRCxPQUFPLEVBQ0wsTUFBTSxJQUFJLFlBQVksR0FNdkIsTUFBTSwwQkFBMEIsQ0FBQztBQUNsQyxPQUFPLEVBQUUsTUFBTSxFQUFFLE1BQU0sd0JBQXdCLENBQUM7QUFFaEQsT0FBTyxFQUFFLGNBQWMsRUFBNkIsTUFBTSxhQUFhLENBQUM7QUFTeEUsU0FBUyxPQUFPLENBQUMsS0FBdUM7SUFDdEQsSUFBSSxDQUFDLEtBQUs7UUFBRSxPQUFPLFNBQVMsQ0FBQztJQUM3QixNQUFNLE1BQU0sR0FBd0IsRUFBRSxDQUFDO0lBQ3ZDLEtBQUssTUFBTSxDQUFDLEdBQUcsRUFBRSxJQUFJLENBQUMsSUFBSSxNQUFNLENBQUMsT0FBTyxDQUFDLEtBQUssQ0FBQyxFQUFFLENBQUM7UUFDaEQsSUFDRSxPQUFPLElBQUksS0FBSyxRQUFRO1lBQ3hCLE9BQU8sSUFBSSxLQUFLLFFBQVE7WUFDeEIsT0FBTyxJQUFJLEtBQUssU0FBUztZQUN6QixDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDO2dCQUNsQixJQUFJLENBQUMsS0FBSyxDQUFDLENBQUMsS0FBSyxFQUFFLEVBQUUsQ0FBQyxPQUFPLEtBQUssS0FBSyxRQUFRLElBQUksT0FBTyxLQUFLLEtBQUssUUFBUSxDQUFDLENBQUMsRUFDaEYsQ0FBQztZQUNELE1BQU0sQ0FBQyxHQUFHLENBQUMsR0FBRyxJQUFJLENBQUM7WUFDbkIsU0FBUztRQUNYLENBQUM7UUFDRCxNQUFNLElBQUksZUFBZSxDQUN2QixxQkFBcUIsR0FBRyw2REFBNkQsQ0FDdEYsQ0FBQztJQUNKLENBQUM7SUFDRCxPQUFPLE1BQU0sQ0FBQztBQUNoQixDQUFDO0FBRUQsU0FBUyxLQUFL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SSxDQUFDLE1BQU0sRUFBRSxDQUFDO1FBQ3BELENBQUM7S0FDRixDQUFDO0lBQ0YsTUFBTSxZQUFZLEdBQUcsUUFBUSxDQUFDLFlBQVksRUFBRSxJQUFJLENBQUMsUUFBUSxDQUFDLENBQUM7SUFDM0QsSUFBSSxDQUFDLFlBQVk7UUFBRSxPQUFPLE9BQU8sQ0FBQztJQUNsQyxPQUFPO1FBQ0wsR0FBRyxPQUFPO1FBQ1YsS0FBSyxDQUFDLFlBQVksQ0FDaEIsS0FBYSxFQUNiLFNBQTJCLEVBQzNCLE1BQW9CO1lBRXBCLE1BQU0sRUFBRSxjQUFjLEVBQUUsQ0FBQztZQUN6QixNQUFNLE1BQU0sR0FBRyxNQUFNLFlBQVksQ0FBQyxRQUFRLENBQUMsS0FBSyxFQUFFLE1BQU0sQ0FBQyxFQUFFLFNBQVMsQ0FBQyxDQUFDO1lBQ3RFLE1BQU0sRUFBRSxjQUFjLEVBQUUsQ0FBQztZQUN6QixPQUFPLE1BQU0sQ0FBQztRQUNoQixDQUFDO0tBQ0YsQ0FBQztBQUNKLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIEFkYXB0ZXIgZnJvbSBBcHBLaXQncyBuYXRpdmUgQUkgU2VhcmNoIHByb3ZpZGVyIHRvIHRoZSBkYngtdG9vbHMgZXh0ZW5zaW9uXG4gKiBjb250cmFjdCB1c2VkIGJ5IGZlZGVyYXRlZCBzZWFyY2ggYW5kIGFnZW50IHRvb2xzLlxuICpcbiAqIEBtb2R1bGVcbiAqL1xuXG5pbXBvcnQgeyBWYWxpZGF0aW9uRXJyb3IgfSBmcm9tIFwiQGRhdGFicmlja3MvYXBwa2l0XCI7XG5pbXBvcnQgdHlwZSB7XG4gIFNlYXJjaEZpbHRlcnMgYXMgQXBwS2l0U2VhcmNoRmlsdGVycyxcbiAgU2VhcmNoUmVxdWVzdCBhcyBBcHBLaXRTZWFyY2hSZXF1ZXN0LFxuICBTZWFyY2hSZXNwb25zZSBhcyBBcHBLaXRTZWFyY2hSZXNwb25zZSxcbn0gZnJvbSBcIkBkYXRhYnJpY2tzL2FwcGtpdC9iZXRhXCI7XG5pbXBvcnQge1xuICBzZWFyY2ggYXMgc2hhcmVkU2VhcmNoLFxuICB0eXBlIFNlYXJjaERvY3VtZW50LFxuICB0eXBlIFNlYXJjaEhpdCxcbiAgdHlwZSBTZWFyY2hSZXF1ZXN0IGFzIEV4dGVuc2lvblNlYXJjaFJlcXVlc3QsXG4gIHR5cGUgU2VhcmNoUmVzdWx0LFxuICB0eXBlIFVwc2VydFJlc3VsdCxcbn0gZnJvbSBcIkBkYngtdG9vbHMvc2hhcmVkLXNlYXJjaFwiO1xuaW1wb3J0IHsgc3RyaW5nIH0gZnJvbSBcIkBkYngtdG9vbHMvc2hhcmVkLWNvcmVcIjtcbmltcG9ydCB0eXBlIHsgU2VhcmNoT3B0aW9ucywgU2VhcmNoUmVhZEJhY2tlbmQgfSBmcm9tIFwiLi9jbGllbnQudHNcIjtcbmltcG9ydCB7IGluZGV4Q29uZmlnRm9yLCB0eXBlIFJlc29sdmVkU2VhcmNoQ29uZmlnIH0gZnJvbSBcIi4vY29uZmlnLnRzXCI7XG5cbi8qKiBNaW5pbWFsIHF1ZXJ5IHN1cmZhY2UgZXhwb3NlZCBieSBBcHBLaXQncyBuYXRpdmUgYGFpU2VhcmNoYCBwbHVnaW4uICovXG5leHBvcnQgaW50ZXJmYWNlIEFpU2VhcmNoUHJvdmlkZXIge1xuICBwcm92aWRlcktpbmQ/OiBcImxha2ViYXNlXCI7XG4gIHF1ZXJ5KGFsaWFzOiBzdHJpbmcsIHJlcXVlc3Q6IEFwcEtpdFNlYXJjaFJlcXVlc3QpOiBQcm9taXNlPEFwcEtpdFNlYXJjaFJlc3BvbnNlPjtcbiAgYWRkRG9jdW1lbnRzPyhhbGlhczogc3RyaW5nLCBkb2N1bWVudHM6IFNlYXJjaERvY3VtZW50W10pOiBQcm9taXNlPFVwc2VydFJlc3VsdD47XG59XG5cbmZ1bmN0aW9uIGZpbHRlcnModmFsdWU6IEV4dGVuc2lvblNlYXJjaFJlcXVlc3RbXCJmaWx0ZXJcIl0pOiBBcHBLaXRTZWFyY2hGaWx0ZXJzIHwgdW5kZWZpbmVkIHtcbiAgaWYgKCF2YWx1ZSkgcmV0dXJuIHVuZGVmaW5lZDtcbiAgY29uc3QgcmVzdWx0OiBBcHBLaXRTZWFyY2hGaWx0ZXJzID0ge307XG4gIGZvciAoY29uc3QgW2tleSwgaXRlbV0gb2YgT2JqZWN0LmVudHJpZXModmFsdWUpKSB7XG4gICAgaWYgKFxuICAgICAgdHlwZW9mIGl0ZW0gPT09IFwic3RyaW5nXCIgfHxcbiAgICAgIHR5cGVvZiBpdGVtID09PSBcIm51bWJlclwiIHx8XG4gICAgICB0eXBlb2YgaXRlbSA9PT0gXCJib29sZWFuXCIgfHxcbiAgICAgIChBcnJheS5pc0FycmF5KGl0ZW0pICYmXG4gICAgICAgIGl0ZW0uZXZlcnkoKGVudHJ5KSA9PiB0eXBlb2YgZW50cnkgPT09IFwic3RyaW5nXCIgfHwgdHlwZW9mIGVudHJ5ID09PSBcIm51bWJlclwiKSlcbiAgICApIHtcbiAgICAgIHJlc3VsdFtrZXldID0gaXRlbTtcbiAgICAgIGNvbnRpbnVlO1xuICAgIH1cbiAgICB0aHJvdyBuZXcgVmFsaWRhdGlvbkVycm9yKFxuICAgICAgYEFJIFNlYXJjaCBmaWx0ZXIgXCIke2tleX1cIiBtdXN0IGJlIGEgc3RyaW5nLCBudW1iZXIsIGJvb2xlYW4sIG9yIHN0cmluZy9udW1iZXIgYXJyYXlgLFxuICAgICk7XG4gIH1cbiAgcmV0dXJuIHJlc3VsdDtcbn1cblxuZnVuY3Rpb24gaGl0SWQoXG4gIGRhdGE6IFJlY29yZDxzdHJpbmcsIHVua25vd24+LFxuICBwcmltYXJ5S2V5OiBzdHJpbmcgfCB1bmRlZmluZWQsXG4gIGluZGV4OiBudW1iZXIsXG4pOiBzdHJpbmcge1xuICBjb25zdCB2YWx1ZSA9IGRhdGFbcHJpbWFyeUtleSA/PyBcImlkXCJdID8/IE9iamVjdC52YWx1ZXMoZGF0YSlbMF0gPz8gaW5kZXg7XG4gIHJldHVybiBTdHJpbmcodmFsdWUpO1xufVxuXG5mdW5jdGlvbiBhbGlhc0ZvcihpbmRleDogc3RyaW5nLCBjb25maWc6IFJlc29sdmVkU2VhcmNoQ29uZmlnKTogc3RyaW5nIHtcbiAgY29uc3QgYWxpYXMgPSBpbmRleENvbmZpZ0Zvcihjb25maWcsIGluZGV4KT8uYWxpYXMgPz8gc3RyaW5nLnRyaW1Ub051bGwoaW5kZXgpO1xuICBpZiAoIWFsaWFzKSB0aHJvdyBuZXcgVmFsaWRhdGlvbkVycm9yKFwiQUkgU2VhcmNoIHJlcXVpcmVzIGEgY29uZmlndXJlZCBpbmRleCBhbGlhc1wiKTtcbiAgcmV0dXJuIGFsaWFzO1xufVxuXG4vKiogQnVpbGQgYSByZWFkIGJhY2tlbmQgdGhhdCBkZWxlZ2F0ZXMgZXZlcnkgVmVjdG9yIFNlYXJjaCBxdWVyeSB0byBBcHBLaXQuICovXG5leHBvcnQgZnVuY3Rpb24gbmF0aXZlQWlTZWFyY2hCYWNrZW5kKFxuICBwcm92aWRlcjogQWlTZWFyY2hQcm92aWRlcixcbiAgY29uZmlnOiBSZXNvbHZlZFNlYXJjaENvbmZpZyxcbik6IFNlYXJjaFJlYWRCYWNrZW5kIHtcbiAgY29uc3QgYmFja2VuZDogU2VhcmNoUmVhZEJhY2tlbmQgPSB7XG4gICAgc3VwcG9ydHNMaWZlY3ljbGU6IHByb3ZpZGVyLnByb3ZpZGVyS2luZCAhPT0gXCJsYWtlYmFzZVwiLFxuICAgIGFzeW5jIHNlYXJjaChpbmRleDogc3RyaW5nLCBxdWVyeTogc3RyaW5nLCBvcHRpb25zOiBTZWFyY2hPcHRpb25zID0ge30pOiBQcm9taXNlPFNlYXJjaFJlc3VsdD4ge1xuICAgICAgb3B0aW9ucy5zaWduYWw/LnRocm93SWZBYm9ydGVkKCk7XG4gICAgICBjb25zdCBrbm93biA9IGluZGV4Q29uZmlnRm9yKGNvbmZpZywgaW5kZXgpO1xuICAgICAgY29uc3QgYWxpYXMgPSBhbGlhc0ZvcihpbmRleCwgY29uZmlnKTtcbiAgICAgIGNvbnN0IHJlc29sdmVkUXVlcnlUeXBlID0gc2hhcmVkU2VhcmNoLnRvQWlTZWFyY2hRdWVyeVR5cGUob3B0aW9ucy5tb2RlKTtcbiAgICAgIGNvbnN0IHJlc29sdmVkRmlsdGVycyA9IGZpbHRlcnMob3B0aW9ucy5maWx0ZXIpO1xuICAgICAgY29uc3QgcmVzcG9uc2UgPSBhd2FpdCBwcm92aWRlci5xdWVyeShhbGlhcywge1xuICAgICAgICBxdWVyeVRleHQ6IHF1ZXJ5LFxuICAgICAgICBudW1SZXN1bHRzOiBvcHRpb25zLmxpbWl0ID8/IGNvbmZpZy5wYWdlU2l6ZSxcbiAgICAgICAgLi4uKG9wdGlvbnMuY29sdW1ucyA/IHsgY29sdW1uczogWy4uLm9wdGlvbnMuY29sdW1uc10gfSA6IHt9KSxcbiAgICAgICAgLi4uKHJlc29sdmVkUXVlcnlUeXBlID8geyBxdWVyeVR5cGU6IHJlc29sdmVkUXVlcnlUeXBlIH0gOiB7fSksXG4gICAgICAgIC4uLihyZXNvbHZlZEZpbHRlcnMgPyB7IGZpbHRlcnM6IHJlc29sdmVkRmlsdGVycyB9IDoge30pLFxuICAgICAgfSk7XG4gICAgICBvcHRpb25zLnNpZ25hbD8udGhyb3dJZkFib3J0ZWQoKTtcbiAgICAgIGNvbnN0IGhpdHM6IFNlYXJjaEhpdFtdID0gcmVzcG9uc2UucmVzdWx0c1xuICAgICAgICAubWFwKChyZXN1bHQsIHJlc3VsdEluZGV4KSA9PiAoe1xuICAgICAgICAgIGlkOiBoaXRJZChyZXN1bHQuZGF0YSwga25vd24/LnByaW1hcnlLZXksIHJlc3VsdEluZGV4KSxcbiAgICAgICAgICBzY29yZTogcmVzdWx0LnNjb3JlLFxuICAgICAgICAgIGZpZWxkczogcmVzdWx0LmRhdGEsXG4gICAgICAgIH0pKVxuICAgICAgICAuZmlsdGVyKFxuICAgICAgICAgIChoaXQpID0+IG9wdGlvbnMuc2NvcmVUaHJlc2hvbGQgPT09IHVuZGVmaW5lZCB8fCBoaXQuc2NvcmUgPj0gb3B0aW9ucy5zY29yZVRocmVzaG9sZCxcbiAgICAgICAgKTtcbiAgICAgIHJldHVybiB7IHF1ZXJ5LCBpbmRleCwgaGl0cywgY291bnQ6IGhpdHMubGVuZ3RoIH07XG4gICAgfSxcbiAgfTtcbiAgY29uc3QgYWRkRG9jdW1lbnRzID0gcHJvdmlkZXIuYWRkRG9jdW1lbnRzPy5iaW5kKHByb3ZpZGVyKTtcbiAgaWYgKCFhZGREb2N1bWVudHMpIHJldHVybiBiYWNrZW5kO1xuICByZXR1cm4ge1xuICAgIC4uLmJhY2tlbmQsXG4gICAgYXN5bmMgYWRkRG9jdW1lbnRzKFxuICAgICAgaW5kZXg6IHN0cmluZyxcbiAgICAgIGRvY3VtZW50czogU2VhcmNoRG9jdW1lbnRbXSxcbiAgICAgIHNpZ25hbD86IEFib3J0U2lnbmFsLFxuICAgICk6IFByb21pc2U8VXBzZXJ0UmVzdWx0PiB7XG4gICAgICBzaWduYWw/LnRocm93SWZBYm9ydGVkKCk7XG4gICAgICBjb25zdCByZXN1bHQgPSBhd2FpdCBhZGREb2N1bWVudHMoYWxpYXNGb3IoaW5kZXgsIGNvbmZpZyksIGRvY3VtZW50cyk7XG4gICAgICBzaWduYWw/LnRocm93SWZBYm9ydGVkKCk7XG4gICAgICByZXR1cm4gcmVzdWx0O1xuICAgIH0sXG4gIH07XG59XG4iXX0=
@@ -1,51 +1,55 @@
1
1
  /**
2
- * AppKit plugin (registered name: `search`) that turns a Databricks AI
3
- * Search (Vector Search) index into a batteries-included search surface. It is
4
- * the "shortcut" half of this package: register it with nothing but an index
5
- * name and you get, all at once -
2
+ * AppKit extension plugin (registered name: `search`) around a sibling
3
+ * `aiSearch` provider. Native AppKit owns Vector Search query execution; this
4
+ * plugin adds the surfaces that remain useful across native and Lakebase
5
+ * providers:
6
6
  *
7
7
  * - a `search` / `universal_search` / (opt-in) `add_documents` tool set for
8
8
  * both Mastra and AppKit agents (autocomplete is a small-`limit` search);
9
- * - HTTP routes under `/api/search` a browser search box calls directly
9
+ * - compatibility and extension routes under `/api/search`
10
10
  * (`POST /` search, `POST /universal` federated, `GET /indexes` catalogue,
11
11
  * and `POST /documents` when writes are enabled);
12
12
  * - a `clientConfig()` payload so a UI knows the indexes, default, and page
13
13
  * size at boot with no round-trip;
14
14
  * - `exports()` so app code can `appkit.search.search(...)` directly.
15
15
  *
16
- * Everything runs under the caller's OBO identity (routes wrap in `asUser`),
17
- * so Unity Catalog ACLs on the index apply. Registering the plugin resolves
18
- * and logs the effective config (default index, known indexes, page size,
19
- * mode) so a misconfiguration shows up in the boot log rather than on the
20
- * first search.
16
+ * Vector Search reads delegate to the registered native AppKit `aiSearch`
17
+ * plugin, preserving its OBO, caching, reranking, and response handling. The
18
+ * alternative `lakebaseAiSearch` provider supplies the same query contract
19
+ * over PostgreSQL full-text search.
21
20
  *
22
21
  * @module
23
22
  */
24
- import { Plugin, ResourceType, type IAppRouter, type ResourceRequirement } from "@databricks/appkit";
23
+ import { Plugin, type IAppRouter } from "@databricks/appkit";
25
24
  import { type AgentToolDefinition, type ToolProvider } from "@databricks/appkit/beta";
26
25
  import { search as sharedSearch } from "@dbx-tools/shared-search";
27
26
  import { type SearchPluginConfig } from "./config.ts";
28
27
  /**
29
- * AppKit plugin exposing AI Search as a search box, an agent tool set, and a
30
- * direct API.
28
+ * AppKit extension plugin for agent tools, federated search, and optional
29
+ * Vector Search lifecycle operations. Register `aiSearch()` or
30
+ * `lakebaseAiSearch()` before this plugin.
31
31
  *
32
32
  * @example
33
33
  * ```ts
34
34
  * import { createApp, server } from "@databricks/appkit";
35
+ * import { aiSearch } from "@databricks/appkit/beta";
35
36
  * import { plugin as searchPlugin } from "@dbx-tools/search";
36
37
  *
37
38
  * await createApp({
38
39
  * plugins: [
39
40
  * server(),
40
- * // zero-config: reads DATABRICKS_VECTOR_SEARCH_INDEX
41
- * searchPlugin.search(),
42
- * // or go deeper:
43
- * // searchPlugin.search({
44
- * // index: "main.support.docs",
45
- * // indexes: ["main.support.docs", "main.catalog.products"],
46
- * // columns: ["title", "url", "body"],
47
- * // mode: "hybrid",
48
- * // }),
41
+ * aiSearch({
42
+ * indexes: {
43
+ * docs: {
44
+ * indexName: "main.support.docs",
45
+ * columns: ["id", "title", "body"],
46
+ * },
47
+ * },
48
+ * }),
49
+ * searchPlugin.search({
50
+ * index: "main.support.docs",
51
+ * indexes: [{ name: "main.support.docs", alias: "docs" }],
52
+ * }),
49
53
  * ],
50
54
  * });
51
55
  * ```
@@ -58,24 +62,7 @@ export declare class SearchPlugin extends Plugin<SearchPluginConfig> implements
58
62
  stability: "beta";
59
63
  resources: {
60
64
  required: never[];
61
- optional: {
62
- type: ResourceType.VECTOR_SEARCH_INDEX;
63
- alias: string;
64
- resourceKey: string;
65
- description: string;
66
- permission: "SELECT";
67
- fields: {
68
- name: {
69
- env: string;
70
- description: string;
71
- discovery: {
72
- type: "cli";
73
- cliCommand: string;
74
- selectField: string;
75
- };
76
- };
77
- };
78
- }[];
65
+ optional: never[];
79
66
  };
80
67
  config: {
81
68
  schema: import("json-schema").JSONSchema7;
@@ -83,11 +70,6 @@ export declare class SearchPlugin extends Plugin<SearchPluginConfig> implements
83
70
  };
84
71
  /** The base path AppKit mounts this plugin's routes under. */
85
72
  private get basePath();
86
- /**
87
- * Promote the index to a required resource once a deployment pins a default,
88
- * through plugin config or either environment name.
89
- */
90
- static getResourceRequirements(config: SearchPluginConfig): ResourceRequirement[];
91
73
  /**
92
74
  * The tools this plugin offers to an AppKit agent. `search` /
93
75
  * `universal_search` are reads; `add_documents` / `create_index` /
@@ -98,16 +80,8 @@ export declare class SearchPlugin extends Plugin<SearchPluginConfig> implements
98
80
  private get tools();
99
81
  /** Prime the shared runtime from config and log the effective policy at boot. */
100
82
  setup(): Promise<void>;
101
- /**
102
- * Build the Lakebase FALLBACK backend, or return `undefined` when Vector
103
- * Search should be used. Falls back only when there is NO Vector Search
104
- * endpoint configured (plugin config or `SEARCH_ENDPOINT` /
105
- * `DATABRICKS_VECTOR_SEARCH_ENDPOINT`) AND the sibling AppKit `lakebase`
106
- * plugin is registered. The pg pool is built from that plugin's
107
- * service-principal config exactly like `@dbx-tools/appkit-mastra`'s memory
108
- * pool - no auth is re-implemented here.
109
- */
110
- private resolveLakebaseBackend;
83
+ /** Resolve the registered AppKit-compatible AI Search provider. */
84
+ private resolveProviderBackend;
111
85
  /**
112
86
  * Ensure the endpoint + index exist and seed them, honoring `ensureOnSetup`.
113
87
  * Uses boot-time SDK auth (env / config profile) via the client's
@@ -121,10 +95,8 @@ export declare class SearchPlugin extends Plugin<SearchPluginConfig> implements
121
95
  shutdown(): Promise<void>;
122
96
  abortActiveOperations(): void;
123
97
  /**
124
- * Mount the search routes under `/api/search`. Each is wrapped in
125
- * `asUser(req)` so the query runs as the requesting user and the index's
126
- * Unity Catalog ACLs apply. `GET /indexes` needs no user scope - it just
127
- * echoes the configured catalogue.
98
+ * Mount extension routes under `/api/search`. Single-index queries stay on
99
+ * the provider's native `/api/ai-search/:alias/query` surface.
128
100
  */
129
101
  injectRoutes(router: IAppRouter): void;
130
102
  /**