@dxos/plugin-search 0.7.5-main.9d26e3a → 0.7.5-main.9d2a38b
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.
- package/dist/lib/browser/app-graph-builder-4C2ZPCED.mjs +41 -0
- package/dist/lib/browser/app-graph-builder-4C2ZPCED.mjs.map +7 -0
- package/dist/lib/browser/{chunk-4L4PWJYC.mjs → chunk-B532NWHM.mjs} +3 -3
- package/dist/lib/browser/chunk-B532NWHM.mjs.map +7 -0
- package/dist/lib/browser/chunk-GGOOQO2C.mjs +133 -0
- package/dist/lib/browser/chunk-GGOOQO2C.mjs.map +7 -0
- package/dist/lib/browser/chunk-Z745WIBH.mjs +21 -0
- package/dist/lib/browser/chunk-Z745WIBH.mjs.map +7 -0
- package/dist/lib/browser/index.mjs +67 -557
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/intent-resolver-XUWUYVFT.mjs +19 -0
- package/dist/lib/browser/intent-resolver-XUWUYVFT.mjs.map +7 -0
- package/dist/lib/browser/meta.json +1 -1
- package/dist/lib/browser/react-context-IIHWUFU6.mjs +18 -0
- package/dist/lib/browser/react-context-IIHWUFU6.mjs.map +7 -0
- package/dist/lib/browser/react-surface-242JU6MW.mjs +360 -0
- package/dist/lib/browser/react-surface-242JU6MW.mjs.map +7 -0
- package/dist/types/src/SearchPlugin.d.ts +1 -3
- package/dist/types/src/SearchPlugin.d.ts.map +1 -1
- package/dist/types/src/capabilities/app-graph-builder.d.ts +181 -0
- package/dist/types/src/capabilities/app-graph-builder.d.ts.map +1 -0
- package/dist/types/src/capabilities/index.d.ts +185 -0
- package/dist/types/src/capabilities/index.d.ts.map +1 -0
- package/dist/types/src/capabilities/intent-resolver.d.ts +4 -0
- package/dist/types/src/capabilities/intent-resolver.d.ts.map +1 -0
- package/dist/types/src/capabilities/react-context.d.ts +8 -0
- package/dist/types/src/capabilities/react-context.d.ts.map +1 -0
- package/dist/types/src/capabilities/react-surface.d.ts +4 -0
- package/dist/types/src/capabilities/react-surface.d.ts.map +1 -0
- package/dist/types/src/components/SearchDialog.d.ts.map +1 -1
- package/dist/types/src/index.d.ts +1 -2
- package/dist/types/src/index.d.ts.map +1 -1
- package/dist/types/src/meta.d.ts +1 -2
- package/dist/types/src/meta.d.ts.map +1 -1
- package/dist/types/src/types.d.ts +0 -2
- package/dist/types/src/types.d.ts.map +1 -1
- package/dist/types/tsconfig.tsbuildinfo +1 -1
- package/package.json +20 -27
- package/src/SearchPlugin.tsx +40 -91
- package/src/capabilities/app-graph-builder.ts +36 -0
- package/src/capabilities/index.ts +10 -0
- package/src/capabilities/intent-resolver.ts +15 -0
- package/src/capabilities/react-context.tsx +16 -0
- package/src/capabilities/react-surface.tsx +30 -0
- package/src/components/SearchDialog.tsx +6 -8
- package/src/index.ts +1 -4
- package/src/meta.ts +1 -1
- package/src/search-sync.ts +1 -1
- package/src/search.ts +1 -1
- package/src/types.tsx +0 -13
- package/dist/lib/browser/chunk-4L4PWJYC.mjs.map +0 -7
- package/dist/lib/browser/meta.mjs +0 -11
- package/dist/lib/browser/meta.mjs.map +0 -7
|
@@ -1,459 +1,27 @@
|
|
|
1
|
+
import {
|
|
2
|
+
SearchContextProvider,
|
|
3
|
+
filterObjectsSync,
|
|
4
|
+
mapObjectToTextFields,
|
|
5
|
+
queryStringToMatch,
|
|
6
|
+
useGlobalFilteredObjects,
|
|
7
|
+
useGlobalSearch,
|
|
8
|
+
useGlobalSearchResults
|
|
9
|
+
} from "./chunk-GGOOQO2C.mjs";
|
|
1
10
|
import {
|
|
2
11
|
SEARCH_PLUGIN,
|
|
3
12
|
SEARCH_RESULT,
|
|
4
|
-
|
|
5
|
-
} from "./chunk-
|
|
13
|
+
meta
|
|
14
|
+
} from "./chunk-B532NWHM.mjs";
|
|
6
15
|
|
|
7
16
|
// packages/plugins/experimental/plugin-search/src/SearchPlugin.tsx
|
|
8
|
-
import
|
|
9
|
-
import { resolvePlugin, parseIntentPlugin, parseGraphPlugin as parseGraphPlugin2, parseNavigationPlugin as parseNavigationPlugin2, LayoutAction as LayoutAction2, firstIdInPart, createSurface, createResolver, createIntent as createIntent2 } from "@dxos/app-framework";
|
|
10
|
-
import { createExtension } from "@dxos/plugin-graph";
|
|
11
|
-
import { getActiveSpace } from "@dxos/plugin-space";
|
|
17
|
+
import { contributes, Events, defineModule, definePlugin, Capabilities, oneOf } from "@dxos/app-framework";
|
|
12
18
|
|
|
13
|
-
// packages/plugins/experimental/plugin-search/src/
|
|
14
|
-
import {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
var
|
|
19
|
-
const inputRef = useRef(null);
|
|
20
|
-
const [text, setText] = useState(value);
|
|
21
|
-
useEffect(() => {
|
|
22
|
-
setText(value);
|
|
23
|
-
}, [
|
|
24
|
-
value
|
|
25
|
-
]);
|
|
26
|
-
const handleChange = (text2) => {
|
|
27
|
-
setText(text2);
|
|
28
|
-
onChange?.(text2);
|
|
29
|
-
};
|
|
30
|
-
const handleReset = () => {
|
|
31
|
-
handleChange(void 0);
|
|
32
|
-
inputRef.current?.focus();
|
|
33
|
-
};
|
|
34
|
-
return /* @__PURE__ */ React.createElement("div", {
|
|
35
|
-
className: "flex w-full items-center pli-1 pbs-1"
|
|
36
|
-
}, /* @__PURE__ */ React.createElement(Input.Root, null, /* @__PURE__ */ React.createElement(Input.TextInput, {
|
|
37
|
-
ref: inputRef,
|
|
38
|
-
placeholder,
|
|
39
|
-
variant,
|
|
40
|
-
value: text ?? "",
|
|
41
|
-
classNames: mx("pl-3 pr-10", classes?.input),
|
|
42
|
-
onChange: ({ target }) => handleChange(target.value),
|
|
43
|
-
onKeyDown: ({ key }) => key === "Escape" && handleReset()
|
|
44
|
-
}), /* @__PURE__ */ React.createElement("div", {
|
|
45
|
-
role: "button",
|
|
46
|
-
className: "-ml-7 p-0 cursor-pointer",
|
|
47
|
-
onClick: handleReset
|
|
48
|
-
}, /* @__PURE__ */ React.createElement(MagnifyingGlass, {
|
|
49
|
-
className: getSize(5)
|
|
50
|
-
}))));
|
|
51
|
-
};
|
|
52
|
-
|
|
53
|
-
// packages/plugins/experimental/plugin-search/src/components/SearchMain.tsx
|
|
54
|
-
import React4, { useState as useState3 } from "react";
|
|
55
|
-
import { useClient } from "@dxos/react-client";
|
|
56
|
-
import { Filter, useQuery } from "@dxos/react-client/echo";
|
|
57
|
-
import { useTranslation } from "@dxos/react-ui";
|
|
58
|
-
import { groupSurface, mx as mx3 } from "@dxos/react-ui-theme";
|
|
59
|
-
|
|
60
|
-
// packages/plugins/experimental/plugin-search/src/components/SearchResults/SearchResults.tsx
|
|
61
|
-
import { Buildings, Folders, User } from "@phosphor-icons/react";
|
|
62
|
-
import React2, { forwardRef } from "react";
|
|
63
|
-
import { ScrollArea } from "@dxos/react-ui";
|
|
64
|
-
import { Card } from "@dxos/react-ui-card";
|
|
65
|
-
import { Mosaic } from "@dxos/react-ui-mosaic";
|
|
66
|
-
import { ghostHover, mx as mx2 } from "@dxos/react-ui-theme";
|
|
67
|
-
var styles = {
|
|
68
|
-
selected: "!bg-primary-100 !dark:bg-primary-900"
|
|
69
|
-
};
|
|
70
|
-
var getIcon = (type) => {
|
|
71
|
-
const iconMap = {
|
|
72
|
-
user: User,
|
|
73
|
-
organization: Buildings,
|
|
74
|
-
project: Folders
|
|
75
|
-
};
|
|
76
|
-
return iconMap[type];
|
|
77
|
-
};
|
|
78
|
-
var Snippet = ({ text, match }) => {
|
|
79
|
-
let content = /* @__PURE__ */ React2.createElement(React2.Fragment, null, text);
|
|
80
|
-
if (match) {
|
|
81
|
-
const result = text.match(match);
|
|
82
|
-
if (result?.index !== void 0) {
|
|
83
|
-
const maxOffset = 16;
|
|
84
|
-
let before = text.slice(0, result.index);
|
|
85
|
-
if (before.length > maxOffset) {
|
|
86
|
-
const idx = before.indexOf(" ", result.index - maxOffset);
|
|
87
|
-
before = "\u2026 " + before.slice(idx);
|
|
88
|
-
}
|
|
89
|
-
const after = text.slice(result.index + result[0].length);
|
|
90
|
-
content = /* @__PURE__ */ React2.createElement(React2.Fragment, null, before, /* @__PURE__ */ React2.createElement("span", {
|
|
91
|
-
className: "text-blue-500"
|
|
92
|
-
}, result[0]), after);
|
|
93
|
-
}
|
|
94
|
-
}
|
|
95
|
-
return /* @__PURE__ */ React2.createElement("span", {
|
|
96
|
-
className: "text-xs mb-1 line-clamp-3 text-neutral-300"
|
|
97
|
-
}, content);
|
|
98
|
-
};
|
|
99
|
-
var SearchItem = /* @__PURE__ */ forwardRef(({ draggableStyle, draggableProps, item, debug = false }, forwardRef3) => {
|
|
100
|
-
const { id, type, label, snippet, match, selected, onSelect } = item;
|
|
101
|
-
const Icon2 = type ? getIcon(type) : void 0;
|
|
102
|
-
return /* @__PURE__ */ React2.createElement(Card.Root, {
|
|
103
|
-
ref: forwardRef3,
|
|
104
|
-
style: draggableStyle,
|
|
105
|
-
classNames: mx2("mx-2 mt-2 cursor-pointer", ghostHover, selected && styles.selected),
|
|
106
|
-
onClick: () => onSelect?.(id)
|
|
107
|
-
}, /* @__PURE__ */ React2.createElement(Card.Header, null, /* @__PURE__ */ React2.createElement(Card.DragHandle, draggableProps), /* @__PURE__ */ React2.createElement(Card.Title, {
|
|
108
|
-
title: label ?? "Untitled"
|
|
109
|
-
}), Icon2 && /* @__PURE__ */ React2.createElement(Card.Endcap, {
|
|
110
|
-
Icon: Icon2
|
|
111
|
-
})), snippet && /* @__PURE__ */ React2.createElement(Card.Body, {
|
|
112
|
-
gutter: true
|
|
113
|
-
}, /* @__PURE__ */ React2.createElement(Snippet, {
|
|
114
|
-
text: snippet,
|
|
115
|
-
match
|
|
116
|
-
})), debug && /* @__PURE__ */ React2.createElement(Card.Body, {
|
|
117
|
-
gutter: true
|
|
118
|
-
}, /* @__PURE__ */ React2.createElement("pre", {
|
|
119
|
-
className: "text-xs whitespace-pre-line"
|
|
120
|
-
}, JSON.stringify(item))));
|
|
121
|
-
});
|
|
122
|
-
var SearchResults = ({ items, selected, onSelect }) => {
|
|
123
|
-
const path = "search";
|
|
124
|
-
return /* @__PURE__ */ React2.createElement(ScrollArea.Root, {
|
|
125
|
-
classNames: "grow"
|
|
126
|
-
}, /* @__PURE__ */ React2.createElement(ScrollArea.Viewport, null, /* @__PURE__ */ React2.createElement(Mosaic.Container, {
|
|
127
|
-
id: path,
|
|
128
|
-
Component: SearchItem
|
|
129
|
-
}, items.map((item) => /* @__PURE__ */ React2.createElement(Mosaic.DraggableTile, {
|
|
130
|
-
key: item.id,
|
|
131
|
-
path,
|
|
132
|
-
type: SEARCH_RESULT,
|
|
133
|
-
item: {
|
|
134
|
-
...item,
|
|
135
|
-
selected: selected === item.id,
|
|
136
|
-
onSelect
|
|
137
|
-
},
|
|
138
|
-
Component: SearchItem
|
|
139
|
-
})))), /* @__PURE__ */ React2.createElement(ScrollArea.Scrollbar, {
|
|
140
|
-
orientation: "vertical"
|
|
141
|
-
}, /* @__PURE__ */ React2.createElement(ScrollArea.Thumb, null)), /* @__PURE__ */ React2.createElement(ScrollArea.Corner, null));
|
|
142
|
-
};
|
|
143
|
-
|
|
144
|
-
// packages/plugins/experimental/plugin-search/src/context.tsx
|
|
145
|
-
import React3, { createContext, useContext, useMemo, useState as useState2 } from "react";
|
|
146
|
-
import { raise } from "@dxos/debug";
|
|
147
|
-
|
|
148
|
-
// packages/plugins/experimental/plugin-search/src/search-sync.ts
|
|
149
|
-
import { AST } from "@dxos/echo-schema";
|
|
150
|
-
import { getSchema } from "@dxos/live-object";
|
|
151
|
-
import { TextType } from "@dxos/plugin-markdown/types";
|
|
152
|
-
var queryStringToMatch = (queryString) => {
|
|
153
|
-
const trimmed = queryString?.trim();
|
|
154
|
-
return trimmed ? new RegExp(trimmed, "i") : void 0;
|
|
155
|
-
};
|
|
156
|
-
var getIcon2 = (schema) => {
|
|
157
|
-
if (!(schema && AST.isTypeLiteral(schema.ast))) {
|
|
158
|
-
return void 0;
|
|
159
|
-
}
|
|
160
|
-
const keys = schema.ast.propertySignatures.map((p) => p.name);
|
|
161
|
-
if (keys.indexOf("email") !== -1) {
|
|
162
|
-
return "user";
|
|
163
|
-
}
|
|
164
|
-
if (keys.indexOf("website") !== -1) {
|
|
165
|
-
return "organization";
|
|
166
|
-
}
|
|
167
|
-
if (keys.indexOf("repo") !== -1) {
|
|
168
|
-
return "project";
|
|
169
|
-
}
|
|
170
|
-
return void 0;
|
|
171
|
-
};
|
|
172
|
-
var filterObjectsSync = (objects, match) => {
|
|
173
|
-
if (!match) {
|
|
174
|
-
return [];
|
|
175
|
-
}
|
|
176
|
-
return objects.reduce((results, object) => {
|
|
177
|
-
if (object instanceof TextType) {
|
|
178
|
-
return results;
|
|
179
|
-
}
|
|
180
|
-
const fields = mapObjectToTextFields(object);
|
|
181
|
-
Object.entries(fields).some(([, value]) => {
|
|
182
|
-
const result = value.match(match);
|
|
183
|
-
if (result) {
|
|
184
|
-
const label = getStringProperty(object, [
|
|
185
|
-
"label",
|
|
186
|
-
"name",
|
|
187
|
-
"title"
|
|
188
|
-
]);
|
|
189
|
-
results.push({
|
|
190
|
-
id: object.id,
|
|
191
|
-
type: getIcon2(getSchema(object)),
|
|
192
|
-
label,
|
|
193
|
-
match,
|
|
194
|
-
// TODO(burdon): Truncate.
|
|
195
|
-
// TODO(burdon): Issue with sketch documents.
|
|
196
|
-
snippet: value !== label ? value : fields.content ?? fields.description ?? void 0,
|
|
197
|
-
object
|
|
198
|
-
});
|
|
199
|
-
return true;
|
|
200
|
-
}
|
|
201
|
-
return false;
|
|
202
|
-
});
|
|
203
|
-
return results;
|
|
204
|
-
}, []);
|
|
205
|
-
};
|
|
206
|
-
var getStringProperty = (object, keys) => {
|
|
207
|
-
let label;
|
|
208
|
-
keys.some((key) => {
|
|
209
|
-
const value = object[key];
|
|
210
|
-
if (typeof value === "string") {
|
|
211
|
-
label = value;
|
|
212
|
-
return true;
|
|
213
|
-
}
|
|
214
|
-
return false;
|
|
215
|
-
});
|
|
216
|
-
return label;
|
|
217
|
-
};
|
|
218
|
-
var getKeys = (object) => {
|
|
219
|
-
try {
|
|
220
|
-
const obj = JSON.parse(JSON.stringify(object));
|
|
221
|
-
return Object.keys(obj).filter((key) => key !== "id" && key !== "identityKey" && key[0] !== "_" && key[0] !== "@");
|
|
222
|
-
} catch (err) {
|
|
223
|
-
return [];
|
|
224
|
-
}
|
|
225
|
-
};
|
|
226
|
-
var mapObjectToTextFields = (object) => {
|
|
227
|
-
return getKeys(object).reduce((fields, key) => {
|
|
228
|
-
const value = object[key];
|
|
229
|
-
if (typeof value === "string" || value instanceof TextType) {
|
|
230
|
-
try {
|
|
231
|
-
fields[key] = String(value);
|
|
232
|
-
} catch (err) {
|
|
233
|
-
}
|
|
234
|
-
}
|
|
235
|
-
return fields;
|
|
236
|
-
}, {});
|
|
237
|
-
};
|
|
238
|
-
|
|
239
|
-
// packages/plugins/experimental/plugin-search/src/context.tsx
|
|
240
|
-
var SearchContext = /* @__PURE__ */ createContext({});
|
|
241
|
-
var SearchContextProvider = ({ children }) => {
|
|
242
|
-
const [match, setMatch] = useState2();
|
|
243
|
-
const handleMatch = (text) => setMatch(queryStringToMatch(text));
|
|
244
|
-
return /* @__PURE__ */ React3.createElement(SearchContext.Provider, {
|
|
245
|
-
value: {
|
|
246
|
-
match,
|
|
247
|
-
setMatch: handleMatch
|
|
248
|
-
}
|
|
249
|
-
}, children);
|
|
250
|
-
};
|
|
251
|
-
var useGlobalSearch = () => {
|
|
252
|
-
return useContext(SearchContext) ?? raise(new Error("Missing SearchContext."));
|
|
253
|
-
};
|
|
254
|
-
var useGlobalSearchResults = (objects) => {
|
|
255
|
-
const { match } = useGlobalSearch();
|
|
256
|
-
return objects && match ? filterObjectsSync(objects, match) : [];
|
|
257
|
-
};
|
|
258
|
-
var useGlobalFilteredObjects = (objects) => {
|
|
259
|
-
const { match } = useGlobalSearch();
|
|
260
|
-
if (!match || !objects) {
|
|
261
|
-
return objects ?? [];
|
|
262
|
-
}
|
|
263
|
-
return useMemo(() => filterObjectsSync(objects, match).map((result) => result.object), [
|
|
264
|
-
objects,
|
|
265
|
-
match
|
|
266
|
-
]);
|
|
267
|
-
};
|
|
268
|
-
|
|
269
|
-
// packages/plugins/experimental/plugin-search/src/components/SearchMain.tsx
|
|
270
|
-
var SearchMain = ({ space }) => {
|
|
271
|
-
const { t } = useTranslation(SEARCH_PLUGIN);
|
|
272
|
-
const client = useClient();
|
|
273
|
-
const { setMatch } = useGlobalSearch();
|
|
274
|
-
const allSpaces = false;
|
|
275
|
-
const objects = useQuery(allSpaces ? client.spaces : space, Filter.all());
|
|
276
|
-
const results = useGlobalSearchResults(objects);
|
|
277
|
-
const [selected, setSelected] = useState3();
|
|
278
|
-
const handleSelect = (id) => {
|
|
279
|
-
setSelected((selected2) => selected2 === id ? void 0 : id);
|
|
280
|
-
};
|
|
281
|
-
return /* @__PURE__ */ React4.createElement("div", {
|
|
282
|
-
className: "flex flex-col grow h-full"
|
|
283
|
-
}, /* @__PURE__ */ React4.createElement(Searchbar, {
|
|
284
|
-
placeholder: t("search placeholder"),
|
|
285
|
-
onChange: setMatch
|
|
286
|
-
}), results.length > 0 && /* @__PURE__ */ React4.createElement("div", {
|
|
287
|
-
className: "absolute top-[--topbar-size] bottom-0 z-[1]"
|
|
288
|
-
}, /* @__PURE__ */ React4.createElement("div", {
|
|
289
|
-
className: mx3("flex flex-col h-full overflow-hidden", groupSurface)
|
|
290
|
-
}, /* @__PURE__ */ React4.createElement(SearchResults, {
|
|
291
|
-
items: results,
|
|
292
|
-
selected,
|
|
293
|
-
onSelect: handleSelect
|
|
294
|
-
}))));
|
|
295
|
-
};
|
|
296
|
-
|
|
297
|
-
// packages/plugins/experimental/plugin-search/src/components/SearchDialog.tsx
|
|
298
|
-
import React5, { forwardRef as forwardRef2, useCallback, useState as useState5 } from "react";
|
|
299
|
-
import { useResolvePlugin, parseNavigationPlugin, parseGraphPlugin, NavigationAction, LayoutAction, isLayoutParts, useIntentDispatcher, createIntent } from "@dxos/app-framework";
|
|
300
|
-
import { useClient as useClient2 } from "@dxos/react-client";
|
|
301
|
-
import { Filter as Filter2, fullyQualifiedId, useQuery as useQuery2 } from "@dxos/react-client/echo";
|
|
302
|
-
import { Button, Dialog, Icon, toLocalizedString, useTranslation as useTranslation2 } from "@dxos/react-ui";
|
|
303
|
-
import { SearchList } from "@dxos/react-ui-searchlist";
|
|
304
|
-
import { descriptionText, mx as mx4 } from "@dxos/react-ui-theme";
|
|
305
|
-
|
|
306
|
-
// packages/plugins/experimental/plugin-search/src/search.ts
|
|
307
|
-
import { yieldOrContinue } from "main-thread-scheduling";
|
|
308
|
-
import { useEffect as useEffect2, useState as useState4 } from "react";
|
|
309
|
-
import { TextType as TextType2 } from "@dxos/plugin-markdown/types";
|
|
310
|
-
var filterObjects = async (objects, match) => {
|
|
311
|
-
const result = /* @__PURE__ */ new Map();
|
|
312
|
-
if (!match) {
|
|
313
|
-
return result;
|
|
314
|
-
}
|
|
315
|
-
await Promise.all(objects.filter((object) => !(object instanceof TextType2)).map(async (object) => {
|
|
316
|
-
await yieldOrContinue("interactive");
|
|
317
|
-
const fields = mapObjectToTextFields(object);
|
|
318
|
-
Object.entries(fields).filter(([_, value]) => value.match(match)).forEach(([key, value]) => {
|
|
319
|
-
if (!result.has(object)) {
|
|
320
|
-
result.set(object, []);
|
|
321
|
-
}
|
|
322
|
-
result.set(object, [
|
|
323
|
-
...result.get(object),
|
|
324
|
-
[
|
|
325
|
-
key,
|
|
326
|
-
value
|
|
327
|
-
]
|
|
328
|
-
]);
|
|
329
|
-
});
|
|
330
|
-
}));
|
|
331
|
-
return result;
|
|
332
|
-
};
|
|
333
|
-
var useSearchResults = (queryString, objects, delay = 400) => {
|
|
334
|
-
const [results, setResults] = useState4(/* @__PURE__ */ new Map());
|
|
335
|
-
const [pending, setPending] = useState4(false);
|
|
336
|
-
useEffect2(() => {
|
|
337
|
-
setPending(!!(objects && queryString));
|
|
338
|
-
const timeoutId = setTimeout(async () => {
|
|
339
|
-
const nextResults = objects && queryString ? await filterObjects(objects, queryStringToMatch(queryString)) : /* @__PURE__ */ new Map();
|
|
340
|
-
setResults(nextResults);
|
|
341
|
-
setPending(false);
|
|
342
|
-
}, delay);
|
|
343
|
-
return () => clearTimeout(timeoutId);
|
|
344
|
-
}, [
|
|
345
|
-
queryString,
|
|
346
|
-
objects
|
|
347
|
-
]);
|
|
348
|
-
return [
|
|
349
|
-
pending,
|
|
350
|
-
results
|
|
351
|
-
];
|
|
352
|
-
};
|
|
353
|
-
|
|
354
|
-
// packages/plugins/experimental/plugin-search/src/components/SearchDialog.tsx
|
|
355
|
-
var SEARCH_DIALOG = `${SEARCH_PLUGIN}/SearchDialog`;
|
|
356
|
-
var SearchListResult = /* @__PURE__ */ forwardRef2(({ node, onSelect }, forwardedRef) => {
|
|
357
|
-
const { t } = useTranslation2(SEARCH_PLUGIN);
|
|
358
|
-
const label = toLocalizedString(node?.properties.label ?? "never", t);
|
|
359
|
-
return /* @__PURE__ */ React5.createElement(SearchList.Item, {
|
|
360
|
-
value: label,
|
|
361
|
-
key: node.id,
|
|
362
|
-
classNames: "flex gap-2 items-center pli-2",
|
|
363
|
-
onSelect: () => onSelect?.(node.id),
|
|
364
|
-
ref: forwardedRef
|
|
365
|
-
}, /* @__PURE__ */ React5.createElement(Icon, {
|
|
366
|
-
size: 5,
|
|
367
|
-
icon: node?.properties.icon
|
|
368
|
-
}), /* @__PURE__ */ React5.createElement("span", {
|
|
369
|
-
className: "is-0 grow truncate"
|
|
370
|
-
}, label));
|
|
371
|
-
});
|
|
372
|
-
var SearchDialog = ({ layoutCoordinate }) => {
|
|
373
|
-
const { t } = useTranslation2(SEARCH_PLUGIN);
|
|
374
|
-
const graphPlugin = useResolvePlugin(parseGraphPlugin);
|
|
375
|
-
const graph = graphPlugin?.provides.graph;
|
|
376
|
-
const navigationPlugin = useResolvePlugin(parseNavigationPlugin);
|
|
377
|
-
const providedClosed = navigationPlugin?.provides.location.closed ?? [];
|
|
378
|
-
const closed = (Array.isArray(providedClosed) ? providedClosed : [
|
|
379
|
-
providedClosed
|
|
380
|
-
]).map((id) => graph?.findNode(id)).filter(Boolean);
|
|
381
|
-
const active = navigationPlugin?.provides.location.active;
|
|
382
|
-
const [queryString, setQueryString] = useState5("");
|
|
383
|
-
const client = useClient2();
|
|
384
|
-
const dangerouslyLoadAllObjects = useQuery2(client.spaces, Filter2.all());
|
|
385
|
-
const [pending, results] = useSearchResults(queryString, dangerouslyLoadAllObjects);
|
|
386
|
-
const resultObjects = Array.from(results.keys());
|
|
387
|
-
const { dispatchPromise: dispatch } = useIntentDispatcher();
|
|
388
|
-
const handleSelect = useCallback(async (nodeId) => {
|
|
389
|
-
if (active && isLayoutParts(active)) {
|
|
390
|
-
const index = active?.main?.findIndex((entry) => entry.id === nodeId);
|
|
391
|
-
if (index !== -1) {
|
|
392
|
-
await dispatch(createIntent(LayoutAction.SetLayout, {
|
|
393
|
-
element: "dialog",
|
|
394
|
-
state: false
|
|
395
|
-
}));
|
|
396
|
-
await dispatch(createIntent(LayoutAction.ScrollIntoView, {
|
|
397
|
-
id: nodeId
|
|
398
|
-
}));
|
|
399
|
-
return;
|
|
400
|
-
}
|
|
401
|
-
await dispatch(createIntent(NavigationAction.AddToActive, {
|
|
402
|
-
part: layoutCoordinate.part,
|
|
403
|
-
id: nodeId,
|
|
404
|
-
pivotId: layoutCoordinate.entryId,
|
|
405
|
-
positioning: "end"
|
|
406
|
-
}));
|
|
407
|
-
await dispatch(createIntent(LayoutAction.SetLayout, {
|
|
408
|
-
element: "dialog",
|
|
409
|
-
state: false
|
|
410
|
-
}));
|
|
411
|
-
await dispatch(createIntent(LayoutAction.ScrollIntoView, {
|
|
412
|
-
id: nodeId
|
|
413
|
-
}));
|
|
414
|
-
}
|
|
415
|
-
}, [
|
|
416
|
-
layoutCoordinate,
|
|
417
|
-
dispatch,
|
|
418
|
-
active
|
|
419
|
-
]);
|
|
420
|
-
return /* @__PURE__ */ React5.createElement(Dialog.Content, {
|
|
421
|
-
classNames: [
|
|
422
|
-
"md:max-is-[24rem] overflow-hidden mbs-12"
|
|
423
|
-
]
|
|
424
|
-
}, /* @__PURE__ */ React5.createElement(Dialog.Title, null, t("search dialog title")), /* @__PURE__ */ React5.createElement(SearchList.Root, {
|
|
425
|
-
label: t("search placeholder"),
|
|
426
|
-
classNames: "flex flex-col grow overflow-hidden my-2"
|
|
427
|
-
}, /* @__PURE__ */ React5.createElement(SearchList.Input, {
|
|
428
|
-
value: queryString,
|
|
429
|
-
onValueChange: (nextValue) => {
|
|
430
|
-
setQueryString(nextValue);
|
|
431
|
-
},
|
|
432
|
-
placeholder: t("search placeholder"),
|
|
433
|
-
classNames: "px-1 my-2"
|
|
434
|
-
}), /* @__PURE__ */ React5.createElement(SearchList.Content, {
|
|
435
|
-
classNames: "max-bs-[24rem] overflow-auto"
|
|
436
|
-
}, queryString.length > 0 ? resultObjects.length > 0 ? resultObjects.map((object) => graph?.findNode(fullyQualifiedId(object))).filter(Boolean).map((node) => /* @__PURE__ */ React5.createElement(SearchListResult, {
|
|
437
|
-
key: node.id,
|
|
438
|
-
node,
|
|
439
|
-
onSelect: handleSelect
|
|
440
|
-
})) : /* @__PURE__ */ React5.createElement("p", {
|
|
441
|
-
className: "pli-1"
|
|
442
|
-
}, t(pending ? "pending results message" : "empty results message")) : /* @__PURE__ */ React5.createElement(React5.Fragment, null, closed.length > 0 && /* @__PURE__ */ React5.createElement("h2", {
|
|
443
|
-
className: mx4("mlb-1", descriptionText)
|
|
444
|
-
}, t("recently closed heading")), closed.map((node) => /* @__PURE__ */ React5.createElement(SearchListResult, {
|
|
445
|
-
key: node.id,
|
|
446
|
-
node,
|
|
447
|
-
onSelect: handleSelect
|
|
448
|
-
}))))), /* @__PURE__ */ React5.createElement(Dialog.Close, {
|
|
449
|
-
asChild: true
|
|
450
|
-
}, /* @__PURE__ */ React5.createElement(Button, {
|
|
451
|
-
variant: "primary",
|
|
452
|
-
classNames: "mbs-2"
|
|
453
|
-
}, t("close label", {
|
|
454
|
-
ns: "os"
|
|
455
|
-
}))));
|
|
456
|
-
};
|
|
19
|
+
// packages/plugins/experimental/plugin-search/src/capabilities/index.ts
|
|
20
|
+
import { lazy } from "@dxos/app-framework";
|
|
21
|
+
var AppGraphBuilder = lazy(() => import("./app-graph-builder-4C2ZPCED.mjs"));
|
|
22
|
+
var IntentResolver = lazy(() => import("./intent-resolver-XUWUYVFT.mjs"));
|
|
23
|
+
var ReactContext = lazy(() => import("./react-context-IIHWUFU6.mjs"));
|
|
24
|
+
var ReactSurface = lazy(() => import("./react-surface-242JU6MW.mjs"));
|
|
457
25
|
|
|
458
26
|
// packages/plugins/experimental/plugin-search/src/translations.ts
|
|
459
27
|
var translations_default = [
|
|
@@ -472,123 +40,65 @@ var translations_default = [
|
|
|
472
40
|
}
|
|
473
41
|
];
|
|
474
42
|
|
|
475
|
-
// packages/plugins/experimental/plugin-search/src/types.tsx
|
|
476
|
-
import { S } from "@dxos/echo-schema";
|
|
477
|
-
var SearchAction;
|
|
478
|
-
(function(SearchAction2) {
|
|
479
|
-
const SEARCH_ACTION = `${SEARCH_PLUGIN}/action`;
|
|
480
|
-
class OpenSearch extends S.TaggedClass()(`${SEARCH_ACTION}/open-search`, {
|
|
481
|
-
input: S.Void,
|
|
482
|
-
output: S.Void
|
|
483
|
-
}) {
|
|
484
|
-
}
|
|
485
|
-
SearchAction2.OpenSearch = OpenSearch;
|
|
486
|
-
})(SearchAction || (SearchAction = {}));
|
|
487
|
-
|
|
488
43
|
// packages/plugins/experimental/plugin-search/src/SearchPlugin.tsx
|
|
489
|
-
var SearchPlugin = () =>
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
44
|
+
var SearchPlugin = () => definePlugin(meta, [
|
|
45
|
+
defineModule({
|
|
46
|
+
id: `${meta.id}/module/translations`,
|
|
47
|
+
activatesOn: Events.SetupTranslations,
|
|
48
|
+
activate: () => contributes(Capabilities.Translations, translations_default)
|
|
49
|
+
}),
|
|
50
|
+
defineModule({
|
|
51
|
+
id: `${meta.id}/module/metadata`,
|
|
52
|
+
activatesOn: oneOf(Events.Startup, Events.SetupAppGraph),
|
|
53
|
+
activate: () => contributes(Capabilities.Metadata, {
|
|
54
|
+
id: SEARCH_RESULT,
|
|
494
55
|
metadata: {
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
case "view-object":
|
|
508
|
-
return item;
|
|
509
|
-
}
|
|
510
|
-
}
|
|
56
|
+
parse: (item, type) => {
|
|
57
|
+
switch (type) {
|
|
58
|
+
case "node":
|
|
59
|
+
return {
|
|
60
|
+
id: item.id,
|
|
61
|
+
label: item.label,
|
|
62
|
+
data: item.object
|
|
63
|
+
};
|
|
64
|
+
case "object":
|
|
65
|
+
return item.object;
|
|
66
|
+
case "view-object":
|
|
67
|
+
return item;
|
|
511
68
|
}
|
|
512
69
|
}
|
|
513
|
-
},
|
|
514
|
-
graph: {
|
|
515
|
-
builder: (plugins) => {
|
|
516
|
-
const dispatch = resolvePlugin(plugins, parseIntentPlugin)?.provides.intent.dispatchPromise;
|
|
517
|
-
return createExtension({
|
|
518
|
-
id: SEARCH_PLUGIN,
|
|
519
|
-
filter: (node) => node.id === "root",
|
|
520
|
-
actions: () => [
|
|
521
|
-
{
|
|
522
|
-
id: SearchAction.OpenSearch._tag,
|
|
523
|
-
data: async () => {
|
|
524
|
-
await dispatch?.(createIntent2(SearchAction.OpenSearch));
|
|
525
|
-
},
|
|
526
|
-
properties: {
|
|
527
|
-
label: [
|
|
528
|
-
"search action label",
|
|
529
|
-
{
|
|
530
|
-
ns: SEARCH_PLUGIN
|
|
531
|
-
}
|
|
532
|
-
],
|
|
533
|
-
icon: "ph--magnifying-glass--regular",
|
|
534
|
-
keyBinding: {
|
|
535
|
-
macos: "shift+meta+f",
|
|
536
|
-
windows: "shift+alt+f"
|
|
537
|
-
},
|
|
538
|
-
testId: "searchPlugin.search"
|
|
539
|
-
}
|
|
540
|
-
}
|
|
541
|
-
]
|
|
542
|
-
});
|
|
543
|
-
}
|
|
544
|
-
},
|
|
545
|
-
context: ({ children }) => /* @__PURE__ */ React6.createElement(SearchContextProvider, null, children),
|
|
546
|
-
surface: {
|
|
547
|
-
definitions: ({ plugins }) => {
|
|
548
|
-
const location = resolvePlugin(plugins, parseNavigationPlugin2)?.provides.location;
|
|
549
|
-
const graph = resolvePlugin(plugins, parseGraphPlugin2)?.provides.graph;
|
|
550
|
-
return [
|
|
551
|
-
createSurface({
|
|
552
|
-
id: SEARCH_DIALOG,
|
|
553
|
-
role: "dialog",
|
|
554
|
-
filter: (data) => data.component === SEARCH_DIALOG,
|
|
555
|
-
component: ({ data }) => /* @__PURE__ */ React6.createElement(SearchDialog, data.subject)
|
|
556
|
-
}),
|
|
557
|
-
createSurface({
|
|
558
|
-
id: "search-input",
|
|
559
|
-
role: "search-input",
|
|
560
|
-
component: () => {
|
|
561
|
-
const space = graph && location ? getActiveSpace(graph, firstIdInPart(location.active, "main")) : void 0;
|
|
562
|
-
return space ? /* @__PURE__ */ React6.createElement(SearchMain, {
|
|
563
|
-
space
|
|
564
|
-
}) : null;
|
|
565
|
-
}
|
|
566
|
-
})
|
|
567
|
-
];
|
|
568
|
-
}
|
|
569
|
-
},
|
|
570
|
-
intent: {
|
|
571
|
-
resolvers: () => createResolver(SearchAction.OpenSearch, () => ({
|
|
572
|
-
intents: [
|
|
573
|
-
createIntent2(LayoutAction2.SetLayout, {
|
|
574
|
-
element: "complementary",
|
|
575
|
-
state: true
|
|
576
|
-
})
|
|
577
|
-
]
|
|
578
|
-
}))
|
|
579
70
|
}
|
|
580
|
-
}
|
|
581
|
-
}
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
71
|
+
})
|
|
72
|
+
}),
|
|
73
|
+
defineModule({
|
|
74
|
+
id: `${meta.id}/module/react-context`,
|
|
75
|
+
activatesOn: Events.Startup,
|
|
76
|
+
activate: ReactContext
|
|
77
|
+
}),
|
|
78
|
+
defineModule({
|
|
79
|
+
id: `${meta.id}/module/react-surface`,
|
|
80
|
+
activatesOn: Events.Startup,
|
|
81
|
+
activate: ReactSurface
|
|
82
|
+
}),
|
|
83
|
+
defineModule({
|
|
84
|
+
id: `${meta.id}/module/intent-resolver`,
|
|
85
|
+
activatesOn: Events.SetupIntents,
|
|
86
|
+
activate: IntentResolver
|
|
87
|
+
}),
|
|
88
|
+
defineModule({
|
|
89
|
+
id: `${meta.id}/module/app-graph-builder`,
|
|
90
|
+
activatesOn: Events.SetupAppGraph,
|
|
91
|
+
activate: AppGraphBuilder
|
|
92
|
+
})
|
|
93
|
+
]);
|
|
586
94
|
export {
|
|
95
|
+
SEARCH_PLUGIN,
|
|
96
|
+
SEARCH_RESULT,
|
|
587
97
|
SearchContextProvider,
|
|
588
98
|
SearchPlugin,
|
|
589
|
-
src_default as default,
|
|
590
99
|
filterObjectsSync,
|
|
591
100
|
mapObjectToTextFields,
|
|
101
|
+
meta,
|
|
592
102
|
queryStringToMatch,
|
|
593
103
|
useGlobalFilteredObjects,
|
|
594
104
|
useGlobalSearch,
|