@dxos/plugin-thread 0.6.14-main.2b6a0f3 → 0.6.14-main.69511f5

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 (44) hide show
  1. package/dist/lib/browser/{ThreadArticle-43QSPQ2B.mjs → ThreadArticle-2Y7UWZLA.mjs} +2 -2
  2. package/dist/lib/browser/{ThreadMain-VXHMJDQC.mjs → ThreadMain-VK5UEBQ7.mjs} +2 -2
  3. package/dist/lib/browser/{chunk-TDPY6D4W.mjs → chunk-LHT42MTJ.mjs} +1 -1
  4. package/dist/lib/browser/{chunk-JFQZ5W2I.mjs → chunk-WKCIKGGW.mjs} +1 -1
  5. package/dist/lib/browser/{chunk-JFQZ5W2I.mjs.map → chunk-WKCIKGGW.mjs.map} +1 -1
  6. package/dist/lib/browser/index.mjs +32 -11
  7. package/dist/lib/browser/index.mjs.map +3 -3
  8. package/dist/lib/browser/meta.json +1 -1
  9. package/dist/lib/browser/types.mjs +1 -1
  10. package/dist/lib/node/{ThreadArticle-ILLKCW6I.cjs → ThreadArticle-CIYBYISR.cjs} +6 -6
  11. package/dist/lib/node/{ThreadMain-7UVE5D34.cjs → ThreadMain-V6KBUQLH.cjs} +6 -6
  12. package/dist/lib/node/{chunk-FOZUQZF4.cjs → chunk-A2IORKQK.cjs} +4 -4
  13. package/dist/lib/node/{chunk-FOZUQZF4.cjs.map → chunk-A2IORKQK.cjs.map} +1 -1
  14. package/dist/lib/node/{chunk-QVOXOTRV.cjs → chunk-HWN7Q5XK.cjs} +4 -4
  15. package/dist/lib/node/index.cjs +57 -36
  16. package/dist/lib/node/index.cjs.map +3 -3
  17. package/dist/lib/node/meta.json +1 -1
  18. package/dist/lib/node/types.cjs +2 -2
  19. package/dist/lib/node/types.cjs.map +1 -1
  20. package/dist/lib/node-esm/{ThreadArticle-MN2KCRY4.mjs → ThreadArticle-PXO4ZJFU.mjs} +2 -2
  21. package/dist/lib/node-esm/{ThreadMain-VKPAHZK7.mjs → ThreadMain-U7R24CN3.mjs} +2 -2
  22. package/dist/lib/node-esm/{chunk-ZXIPFXSA.mjs → chunk-KWNXG6FG.mjs} +1 -1
  23. package/dist/lib/node-esm/{chunk-ZXIPFXSA.mjs.map → chunk-KWNXG6FG.mjs.map} +1 -1
  24. package/dist/lib/node-esm/{chunk-5XQXCOZP.mjs → chunk-SXXOBRAX.mjs} +1 -1
  25. package/dist/lib/node-esm/index.mjs +32 -11
  26. package/dist/lib/node-esm/index.mjs.map +3 -3
  27. package/dist/lib/node-esm/meta.json +1 -1
  28. package/dist/lib/node-esm/types.mjs +1 -1
  29. package/dist/types/src/ThreadPlugin.d.ts.map +1 -1
  30. package/dist/types/src/types.d.ts +1 -1
  31. package/dist/types/src/types.d.ts.map +1 -1
  32. package/package.json +35 -44
  33. package/src/ThreadPlugin.tsx +24 -5
  34. package/src/components/ThreadSettings.tsx +3 -3
  35. package/src/types.ts +1 -1
  36. /package/dist/lib/browser/{ThreadArticle-43QSPQ2B.mjs.map → ThreadArticle-2Y7UWZLA.mjs.map} +0 -0
  37. /package/dist/lib/browser/{ThreadMain-VXHMJDQC.mjs.map → ThreadMain-VK5UEBQ7.mjs.map} +0 -0
  38. /package/dist/lib/browser/{chunk-TDPY6D4W.mjs.map → chunk-LHT42MTJ.mjs.map} +0 -0
  39. /package/dist/lib/node/{ThreadArticle-ILLKCW6I.cjs.map → ThreadArticle-CIYBYISR.cjs.map} +0 -0
  40. /package/dist/lib/node/{ThreadMain-7UVE5D34.cjs.map → ThreadMain-V6KBUQLH.cjs.map} +0 -0
  41. /package/dist/lib/node/{chunk-QVOXOTRV.cjs.map → chunk-HWN7Q5XK.cjs.map} +0 -0
  42. /package/dist/lib/node-esm/{ThreadArticle-MN2KCRY4.mjs.map → ThreadArticle-PXO4ZJFU.mjs.map} +0 -0
  43. /package/dist/lib/node-esm/{ThreadMain-VKPAHZK7.mjs.map → ThreadMain-U7R24CN3.mjs.map} +0 -0
  44. /package/dist/lib/node-esm/{chunk-5XQXCOZP.mjs.map → chunk-SXXOBRAX.mjs.map} +0 -0
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  ChatContainer
3
- } from "./chunk-TDPY6D4W.mjs";
3
+ } from "./chunk-LHT42MTJ.mjs";
4
4
  import "./chunk-5G3KL6TC.mjs";
5
5
 
6
6
  // packages/plugins/plugin-thread/src/components/ThreadArticle.tsx
@@ -15,4 +15,4 @@ var ThreadArticle_default = ThreadArticle;
15
15
  export {
16
16
  ThreadArticle_default as default
17
17
  };
18
- //# sourceMappingURL=ThreadArticle-43QSPQ2B.mjs.map
18
+ //# sourceMappingURL=ThreadArticle-2Y7UWZLA.mjs.map
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  ChatContainer
3
- } from "./chunk-TDPY6D4W.mjs";
3
+ } from "./chunk-LHT42MTJ.mjs";
4
4
  import "./chunk-5G3KL6TC.mjs";
5
5
 
6
6
  // packages/plugins/plugin-thread/src/components/ThreadMain.tsx
@@ -23,4 +23,4 @@ var ThreadMain_default = ThreadMain;
23
23
  export {
24
24
  ThreadMain_default as default
25
25
  };
26
- //# sourceMappingURL=ThreadMain-VXHMJDQC.mjs.map
26
+ //# sourceMappingURL=ThreadMain-VK5UEBQ7.mjs.map
@@ -407,4 +407,4 @@ export {
407
407
  ChatHeading,
408
408
  ChatContainer
409
409
  };
410
- //# sourceMappingURL=chunk-TDPY6D4W.mjs.map
410
+ //# sourceMappingURL=chunk-LHT42MTJ.mjs.map
@@ -17,4 +17,4 @@ var ThreadAction;
17
17
  export {
18
18
  ThreadAction
19
19
  };
20
- //# sourceMappingURL=chunk-JFQZ5W2I.mjs.map
20
+ //# sourceMappingURL=chunk-WKCIKGGW.mjs.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/types.ts"],
4
- "sourcesContent": ["//\n// Copyright 2023 DXOS.org\n//\n\nimport type {\n GraphBuilderProvides,\n IntentResolverProvides,\n MetadataRecordsProvides,\n SettingsProvides,\n SurfaceProvides,\n TranslationsProvides,\n} from '@dxos/app-framework';\nimport { type SchemaProvides } from '@dxos/plugin-client';\nimport { type MarkdownExtensionProvides } from '@dxos/plugin-markdown';\nimport { type ThreadType } from '@dxos/plugin-space/types';\n\nimport { THREAD_PLUGIN } from './meta';\n\nconst THREAD_ACTION = `${THREAD_PLUGIN}/action`;\nexport enum ThreadAction {\n CREATE = `${THREAD_ACTION}/create`,\n SELECT = `${THREAD_ACTION}/select`,\n DELETE = `${THREAD_ACTION}/delete`,\n ON_MESSAGE_ADD = `${THREAD_ACTION}/on-message-add`,\n DELETE_MESSAGE = `${THREAD_ACTION}/delete-message`,\n TOGGLE_RESOLVED = `${THREAD_ACTION}/toggle-resolved`,\n}\n\n// TODO(Zan): Move this to the plugin-space plugin or another common location when we implement threads in sheets.\nexport type ThreadProvides<T> = {\n thread: {\n predicate: (obj: any) => obj is T;\n createSort: (obj: T) => (anchorA: string | undefined, anchorB: string | undefined) => number;\n };\n};\n\nexport type ThreadPluginProvides = SurfaceProvides &\n IntentResolverProvides &\n GraphBuilderProvides &\n MetadataRecordsProvides &\n SettingsProvides &\n TranslationsProvides &\n SchemaProvides &\n MarkdownExtensionProvides;\n\nexport type ThreadSettingsProps = { standalone?: boolean };\n\nexport interface ThreadModel {\n root: ThreadType;\n}\n\nexport type ThreadState = {\n /** In-memory draft threads. */\n drafts: Record<string, ThreadType[]>;\n current?: string | undefined;\n};\n"],
4
+ "sourcesContent": ["//\n// Copyright 2023 DXOS.org\n//\n\nimport type {\n GraphBuilderProvides,\n IntentResolverProvides,\n MetadataRecordsProvides,\n SettingsProvides,\n SurfaceProvides,\n TranslationsProvides,\n} from '@dxos/app-framework';\nimport { type SchemaProvides } from '@dxos/plugin-client';\nimport { type MarkdownExtensionProvides } from '@dxos/plugin-markdown';\nimport { type ThreadType } from '@dxos/plugin-space/types';\n\nimport { THREAD_PLUGIN } from './meta';\n\nconst THREAD_ACTION = `${THREAD_PLUGIN}/action`;\nexport enum ThreadAction {\n CREATE = `${THREAD_ACTION}/create`,\n SELECT = `${THREAD_ACTION}/select`,\n DELETE = `${THREAD_ACTION}/delete`,\n ON_MESSAGE_ADD = `${THREAD_ACTION}/on-message-add`,\n DELETE_MESSAGE = `${THREAD_ACTION}/delete-message`,\n TOGGLE_RESOLVED = `${THREAD_ACTION}/toggle-resolved`,\n}\n\n// TODO(Zan): Move this to the plugin-space plugin or another common location when we implement threads in sheets.\nexport type ThreadProvides<T> = {\n thread: {\n predicate: (obj: any) => obj is T;\n createSort: (obj: T) => (anchorA: string | undefined, anchorB: string | undefined) => number;\n };\n};\n\nexport type ThreadPluginProvides = SurfaceProvides &\n IntentResolverProvides &\n GraphBuilderProvides &\n MetadataRecordsProvides &\n SettingsProvides<ThreadSettingsProps> &\n TranslationsProvides &\n SchemaProvides &\n MarkdownExtensionProvides;\n\nexport type ThreadSettingsProps = { standalone?: boolean };\n\nexport interface ThreadModel {\n root: ThreadType;\n}\n\nexport type ThreadState = {\n /** In-memory draft threads. */\n drafts: Record<string, ThreadType[]>;\n current?: string | undefined;\n};\n"],
5
5
  "mappings": ";;;;;AAkBA,IAAMA,gBAAgB,GAAGC,aAAAA;;UACbC,eAAAA;0CACD,GAAGF,aAAAA,SAAsB,IAAA;0CACzB,GAAGA,aAAAA,SAAsB,IAAA;0CACzB,GAAGA,aAAAA,SAAsB,IAAA;kDACjB,GAAGA,aAAAA,iBAA8B,IAAA;kDACjC,GAAGA,aAAAA,iBAA8B,IAAA;mDAChC,GAAGA,aAAAA,kBAA+B,IAAA;GAN1CE,iBAAAA,eAAAA,CAAAA,EAAAA;",
6
6
  "names": ["THREAD_ACTION", "THREAD_PLUGIN", "ThreadAction"]
7
7
  }
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  ThreadAction
3
- } from "./chunk-JFQZ5W2I.mjs";
3
+ } from "./chunk-WKCIKGGW.mjs";
4
4
  import {
5
5
  ChatContainer,
6
6
  ChatHeading,
@@ -10,7 +10,7 @@ import {
10
10
  useAnalyticsCallback,
11
11
  useOnEditAnalytics,
12
12
  useStatus
13
- } from "./chunk-TDPY6D4W.mjs";
13
+ } from "./chunk-LHT42MTJ.mjs";
14
14
  import {
15
15
  THREAD_ITEM,
16
16
  THREAD_PLUGIN,
@@ -28,7 +28,7 @@ import { ObservabilityAction } from "@dxos/plugin-observability/meta";
28
28
  import { SpaceAction } from "@dxos/plugin-space";
29
29
  import { ThreadType as ThreadType2, MessageType as MessageType2, ChannelType } from "@dxos/plugin-space/types";
30
30
  import { create as create2, getTypename } from "@dxos/react-client/echo";
31
- import { getSpace as getSpace3, fullyQualifiedId as fullyQualifiedId5, loadObjectReferences, parseFullyQualifiedId } from "@dxos/react-client/echo";
31
+ import { getSpace as getSpace3, fullyQualifiedId as fullyQualifiedId5, loadObjectReferences, parseId } from "@dxos/react-client/echo";
32
32
  import { translations as threadTranslations } from "@dxos/react-ui-thread";
33
33
 
34
34
  // packages/plugins/plugin-thread/src/components/index.ts
@@ -354,11 +354,11 @@ var ThreadComplementary = ({ role, subject, drafts, current, showResolvedThreads
354
354
 
355
355
  // packages/plugins/plugin-thread/src/components/ThreadSettings.tsx
356
356
  import React4 from "react";
357
- import { SettingsValue } from "@dxos/plugin-settings";
358
357
  import { Input, useTranslation as useTranslation3 } from "@dxos/react-ui";
358
+ import { FormInput } from "@dxos/react-ui-data";
359
359
  var ThreadSettings = ({ settings }) => {
360
360
  const { t } = useTranslation3(THREAD_PLUGIN);
361
- return /* @__PURE__ */ React4.createElement(React4.Fragment, null, /* @__PURE__ */ React4.createElement(SettingsValue, {
361
+ return /* @__PURE__ */ React4.createElement(React4.Fragment, null, /* @__PURE__ */ React4.createElement(FormInput, {
362
362
  label: t("settings standalone label")
363
363
  }, /* @__PURE__ */ React4.createElement(Input.Switch, {
364
364
  checked: settings.standalone,
@@ -367,8 +367,8 @@ var ThreadSettings = ({ settings }) => {
367
367
  };
368
368
 
369
369
  // packages/plugins/plugin-thread/src/components/index.ts
370
- var ThreadMain = lazy(() => import("./ThreadMain-VXHMJDQC.mjs"));
371
- var ThreadArticle = lazy(() => import("./ThreadArticle-43QSPQ2B.mjs"));
370
+ var ThreadMain = lazy(() => import("./ThreadMain-VK5UEBQ7.mjs"));
371
+ var ThreadArticle = lazy(() => import("./ThreadArticle-2Y7UWZLA.mjs"));
372
372
 
373
373
  // packages/plugins/plugin-thread/src/extensions/threads.ts
374
374
  import { EditorView } from "@codemirror/view";
@@ -595,6 +595,8 @@ var ThreadPlugin = () => {
595
595
  if (!client || !dispatch || !metadataResolver) {
596
596
  return [];
597
597
  }
598
+ const type = "orphan-comments-for-subject";
599
+ const icon = "ph--chat-text--regular";
598
600
  return [
599
601
  createExtension({
600
602
  id: `${THREAD_PLUGIN}/comments-for-subject`,
@@ -603,8 +605,27 @@ var ThreadPlugin = () => {
603
605
  return;
604
606
  }
605
607
  const [subjectId] = id.split("~");
606
- const [spaceId, objectId] = parseFullyQualifiedId(subjectId);
608
+ const { spaceId, objectId } = parseId(subjectId);
607
609
  const space = client.spaces.get().find((space2) => space2.id === spaceId);
610
+ if (!objectId) {
611
+ return {
612
+ id,
613
+ type,
614
+ data: null,
615
+ properties: {
616
+ icon,
617
+ label: [
618
+ "unnamed object threads label",
619
+ {
620
+ ns: THREAD_PLUGIN
621
+ }
622
+ ],
623
+ showResolvedThreads: false,
624
+ object: null,
625
+ space
626
+ }
627
+ };
628
+ }
608
629
  const object = toSignal((onChange) => {
609
630
  const timeout = setTimeout(async () => {
610
631
  await space?.db.loadObjectById(objectId);
@@ -625,10 +646,10 @@ var ThreadPlugin = () => {
625
646
  const viewState = getViewState(subjectId);
626
647
  return {
627
648
  id,
628
- type: "orphan-comments-for-subject",
649
+ type,
629
650
  data: null,
630
651
  properties: {
631
- icon: "ph--chat-text--regular",
652
+ icon,
632
653
  label,
633
654
  showResolvedThreads: viewState.showResolvedThreads,
634
655
  object
@@ -797,7 +818,7 @@ var ThreadPlugin = () => {
797
818
  } catch (err) {
798
819
  log.error("Subject does not support threads array", subject?.typename, {
799
820
  F: __dxlog_file,
800
- L: 328,
821
+ L: 347,
801
822
  S: void 0,
802
823
  C: (f, a) => f(...a)
803
824
  });
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/ThreadPlugin.tsx", "../../../src/components/index.ts", "../../../src/components/CommentContainer.tsx", "../../../src/components/CommentsContainer.tsx", "../../../src/components/ThreadComplementary.tsx", "../../../src/components/ThreadSettings.tsx", "../../../src/extensions/threads.ts", "../../../src/translations.ts", "../../../src/index.ts"],
4
- "sourcesContent": ["//\n// Copyright 2023 DXOS.org\n//\n\nimport React from 'react';\n\nimport {\n type IntentPluginProvides,\n type LocationProvides,\n NavigationAction,\n type Plugin,\n type PluginDefinition,\n isLayoutParts,\n parseIntentPlugin,\n parseNavigationPlugin,\n parseMetadataResolverPlugin,\n resolvePlugin,\n LayoutAction,\n} from '@dxos/app-framework';\nimport { type UnsubscribeCallback } from '@dxos/async';\nimport { LocalStorageStore } from '@dxos/local-storage';\nimport { log } from '@dxos/log';\nimport { parseClientPlugin } from '@dxos/plugin-client';\nimport { type ActionGroup, createExtension, isActionGroup, toSignal } from '@dxos/plugin-graph';\nimport { ObservabilityAction } from '@dxos/plugin-observability/meta';\nimport { SpaceAction } from '@dxos/plugin-space';\nimport { ThreadType, MessageType, ChannelType } from '@dxos/plugin-space/types';\nimport { create, type EchoReactiveObject, getTypename } from '@dxos/react-client/echo';\nimport { getSpace, fullyQualifiedId, loadObjectReferences, parseFullyQualifiedId } from '@dxos/react-client/echo';\nimport { translations as threadTranslations } from '@dxos/react-ui-thread';\n\nimport {\n ChatContainer,\n ChatHeading,\n ThreadArticle,\n ThreadComplementary,\n ThreadMain,\n ThreadSettings,\n} from './components';\nimport { threads } from './extensions';\nimport meta, { THREAD_ITEM, THREAD_PLUGIN } from './meta';\nimport translations from './translations';\nimport { ThreadAction, type ThreadPluginProvides, type ThreadSettingsProps, type ThreadState } from './types';\n\ntype SubjectId = string;\n\nconst initialViewState = { showResolvedThreads: false };\n\ntype ViewStore = Record<SubjectId, typeof initialViewState>;\n\n// TODO(Zan): Every instance of `cursor` should be replaced with `anchor`.\n// NOTE(burdon): Review/discuss CursorConverter semantics.\nexport const ThreadPlugin = (): PluginDefinition<ThreadPluginProvides> => {\n const settings = new LocalStorageStore<ThreadSettingsProps>(THREAD_PLUGIN);\n const state = create<ThreadState>({ drafts: {} });\n\n const viewStore = create<ViewStore>({});\n const getViewState = (subjectId: string) => {\n if (!viewStore[subjectId]) {\n viewStore[subjectId] = { ...initialViewState };\n }\n return viewStore[subjectId];\n };\n\n let navigationPlugin: Plugin<LocationProvides> | undefined;\n let intentPlugin: Plugin<IntentPluginProvides> | undefined;\n\n const unsubscribeCallbacks = [] as UnsubscribeCallback[];\n\n return {\n meta,\n ready: async (plugins) => {\n settings.prop({ key: 'standalone', type: LocalStorageStore.bool({ allowUndefined: true }) });\n\n navigationPlugin = resolvePlugin(plugins, parseNavigationPlugin);\n intentPlugin = resolvePlugin(plugins, parseIntentPlugin)!;\n },\n unload: async () => {\n unsubscribeCallbacks.forEach((unsubscribe) => unsubscribe());\n },\n provides: {\n settings: settings.values,\n metadata: {\n records: {\n [ChannelType.typename]: {\n placeholder: ['channel title placeholder', { ns: THREAD_PLUGIN }],\n icon: 'ph--chat--regular',\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (channel: ChannelType) => loadObjectReferences(channel, (channel) => channel.threads),\n },\n [ThreadType.typename]: {\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (thread: ThreadType) => loadObjectReferences(thread, (thread) => thread.messages),\n },\n [MessageType.typename]: {\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (message: MessageType) => [], // loadObjectReferences(message, (message) => [...message.parts, message.context]),\n },\n [THREAD_ITEM]: {\n parse: (item: EchoReactiveObject<any>, type: string) => {\n switch (type) {\n case 'node':\n return { id: item.id, label: item.title, data: item };\n case 'object':\n return item;\n case 'view-object':\n return { id: `${item.id}-view`, object: item };\n }\n },\n },\n },\n },\n translations: [...translations, ...threadTranslations],\n echo: { schema: [ChannelType, ThreadType, MessageType] },\n graph: {\n builder: (plugins) => {\n const client = resolvePlugin(plugins, parseClientPlugin)?.provides.client;\n const dispatch = resolvePlugin(plugins, parseIntentPlugin)?.provides.intent.dispatch;\n const metadataResolver = resolvePlugin(plugins, parseMetadataResolverPlugin)?.provides.metadata.resolver;\n\n if (!client || !dispatch || !metadataResolver) {\n return [];\n }\n\n return [\n createExtension({\n id: `${THREAD_PLUGIN}/comments-for-subject`,\n resolver: ({ id }) => {\n // TODO(Zan): Find util (or make one).\n if (!id.endsWith('~comments')) {\n return;\n }\n\n const [subjectId] = id.split('~');\n const [spaceId, objectId] = parseFullyQualifiedId(subjectId);\n const space = client.spaces.get().find((space) => space.id === spaceId);\n const object = toSignal(\n (onChange) => {\n const timeout = setTimeout(async () => {\n await space?.db.loadObjectById(objectId);\n onChange();\n });\n\n return () => clearTimeout(timeout);\n },\n () => space?.db.getObjectById(objectId),\n subjectId,\n );\n if (!object || !subjectId) {\n return;\n }\n\n const meta = metadataResolver(getTypename(object) ?? '');\n const label = meta.label?.(object) ||\n object.name ||\n meta.placeholder || ['unnamed object threads label', { ns: THREAD_PLUGIN }];\n\n const viewState = getViewState(subjectId);\n\n return {\n id,\n type: 'orphan-comments-for-subject',\n data: null,\n properties: {\n icon: 'ph--chat-text--regular',\n label,\n showResolvedThreads: viewState.showResolvedThreads,\n object,\n },\n };\n },\n actions: ({ node }) => {\n const dataId = node.id.split('~').at(0);\n if (!node.id.endsWith('~comments') || !dataId) {\n return;\n }\n\n const [spaceId, objectId] = dataId.split(':');\n\n const viewState = getViewState(dataId);\n const toggle = () => {\n const newToggleState = !viewState.showResolvedThreads;\n viewState.showResolvedThreads = newToggleState;\n void dispatch({\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.toggle-show-resolved',\n properties: { spaceId, threadId: objectId, showResolved: newToggleState },\n },\n });\n };\n\n return [\n {\n id: `${THREAD_PLUGIN}/toggle-show-resolved/${node.id}`,\n data: toggle,\n properties: {\n label: ['toggle show resolved', { ns: THREAD_PLUGIN }],\n menuItemType: 'toggle',\n isChecked: viewState.showResolvedThreads,\n testId: 'threadPlugin.toggleShowResolved',\n icon: viewState.showResolvedThreads ? 'ph--eye-slash--regular' : 'ph--eye--regular',\n },\n },\n ];\n },\n }),\n createExtension({\n id: ThreadAction.CREATE,\n filter: (node): node is ActionGroup =>\n !!settings.values.standalone && isActionGroup(node) && node.id.startsWith(SpaceAction.ADD_OBJECT),\n actions: ({ node }) => {\n const id = node.id.split('/').at(-1);\n const [spaceId, objectId] = id?.split(':') ?? [];\n const space = client.spaces.get().find((space) => space.id === spaceId);\n const object = objectId && space?.db.getObjectById(objectId);\n const target = objectId ? object : space;\n if (!target) {\n return;\n }\n\n return [\n {\n id: `${THREAD_PLUGIN}/create/${node.id}`,\n data: async () => {\n await dispatch([\n { plugin: THREAD_PLUGIN, action: ThreadAction.CREATE },\n { action: SpaceAction.ADD_OBJECT, data: { target } },\n { action: NavigationAction.OPEN },\n ]);\n },\n properties: {\n label: ['create channel label', { ns: THREAD_PLUGIN }],\n icon: 'ph--chat--regular',\n testId: 'threadPlugin.createObject',\n },\n },\n ];\n },\n }),\n ];\n },\n },\n surface: {\n component: ({ data, role }) => {\n switch (role) {\n case 'main': {\n return data.active instanceof ChannelType && data.active.threads[0] ? (\n <ThreadMain thread={data.active.threads[0]} />\n ) : null;\n }\n\n case 'settings': {\n return data.plugin === meta.id ? <ThreadSettings settings={settings.values} /> : null;\n }\n\n case 'article': {\n const location = navigationPlugin?.provides.location;\n\n if (data.object instanceof ChannelType && data.object.threads[0]) {\n const channel = data.object;\n // TODO(zan): Maybe we should have utility for positional main object ids.\n if (isLayoutParts(location?.active) && location.active.main) {\n const layoutEntries = location.active.main;\n const currentPosition = layoutEntries.findIndex((entry) => channel.id === entry.id);\n if (currentPosition > 0) {\n const objectToTheLeft = layoutEntries[currentPosition - 1];\n const context = getSpace(data.object)?.db.getObjectById(objectToTheLeft.id);\n return <ThreadArticle thread={data.object.threads[0]} context={context} />;\n }\n }\n\n return <ThreadArticle thread={data.object.threads[0]} />;\n }\n\n if (data.subject instanceof ThreadType) {\n return (\n <>\n <ChatHeading attendableId={data.subject.id} />\n <ChatContainer thread={data.subject} />\n </>\n );\n }\n\n break;\n }\n\n case 'complementary--comments': {\n if (\n data.subject &&\n typeof data.subject === 'object' &&\n 'threads' in data.subject &&\n Array.isArray(data.subject.threads)\n ) {\n const { showResolvedThreads } = getViewState(fullyQualifiedId(data.subject));\n\n return (\n <ThreadComplementary\n role={role}\n subject={data.subject}\n drafts={state.drafts[fullyQualifiedId(data.subject)]}\n current={state.current}\n showResolvedThreads={showResolvedThreads}\n />\n );\n }\n\n break;\n }\n }\n\n return null;\n },\n },\n intent: {\n resolver: async (intent) => {\n switch (intent.action) {\n case ThreadAction.CREATE: {\n if (intent.data && intent.data.cursor !== undefined) {\n const { cursor, name, subject } = intent.data;\n\n // Seed the threads array if it does not exist.\n if (subject?.threads === undefined) {\n try {\n // Static schema will throw an error if subject does not support threads array property.\n subject.threads = [];\n } catch (err) {\n log.error('Subject does not support threads array', subject?.typename);\n return;\n }\n }\n\n const subjectId = fullyQualifiedId(subject);\n const thread = create(ThreadType, { name, anchor: cursor, messages: [], status: 'staged' });\n const draft = state.drafts[subjectId];\n if (draft) {\n draft.push(thread);\n } else {\n state.drafts[subjectId] = [thread];\n }\n\n return {\n data: thread,\n intents: [\n [\n {\n action: ThreadAction.SELECT,\n data: { current: fullyQualifiedId(thread) },\n },\n ],\n [\n {\n action: NavigationAction.OPEN,\n data: {\n activeParts: { complementary: 'comments' },\n },\n },\n ],\n [\n {\n action: LayoutAction.SET_LAYOUT,\n data: {\n element: 'complementary',\n state: true,\n },\n },\n ],\n ],\n };\n } else {\n // NOTE: This is the standalone thread creation case.\n return {\n data: create(ChannelType, { threads: [create(ThreadType, { messages: [] })] }),\n };\n }\n }\n\n case ThreadAction.SELECT: {\n state.current = intent.data?.current;\n\n return {\n data: true,\n intents: !intent.data?.skipOpen\n ? [\n [\n {\n action: NavigationAction.OPEN,\n data: {\n activeParts: { complementary: 'comments' },\n },\n },\n ],\n ]\n : [],\n };\n }\n\n case ThreadAction.TOGGLE_RESOLVED: {\n const { thread } = intent.data ?? {};\n if (!(thread instanceof ThreadType)) {\n return;\n }\n\n if (thread.status === 'active' || thread.status === undefined) {\n thread.status = 'resolved';\n } else if (thread.status === 'resolved') {\n thread.status = 'active';\n }\n\n const space = getSpace(thread);\n const spaceId = space?.id;\n\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.toggle-resolved', properties: { threadId: thread.id, spaceId } },\n },\n ],\n ],\n };\n }\n\n case ThreadAction.DELETE: {\n const { subject, thread } = intent.data ?? {};\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject)\n ) {\n return;\n }\n\n const subjectId = fullyQualifiedId(subject);\n const draft = state.drafts[subjectId];\n if (draft) {\n // Check if we're deleting a draft; if so, remove it.\n const index = draft.findIndex((t) => t.id === thread.id);\n if (index !== -1) {\n draft.splice(index, 1);\n return { data: true };\n }\n }\n\n const space = getSpace(thread);\n if (!space || !subject.threads) {\n return;\n }\n\n if (!intent.undo) {\n const index = subject.threads.findIndex((t: any) => t?.id === thread.id);\n const cursor = subject.threads[index]?.anchor;\n if (index !== -1) {\n subject.threads?.splice(index, 1);\n }\n\n space.db.remove(thread);\n\n return {\n undoable: {\n message: translations[0]['en-US'][THREAD_PLUGIN]['thread deleted label'],\n data: { cursor },\n },\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.delete', properties: { threadId: thread.id, spaceId: space.id } },\n },\n ],\n ],\n };\n } else if (intent.undo) {\n // TODO(wittjosiah): SDK should do this automatically.\n const savedThread = space.db.add(thread);\n subject.threads.push(savedThread);\n\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.undo-delete', properties: { threadId: thread.id, spaceId: space.id } },\n },\n ],\n ],\n };\n }\n break;\n }\n\n case ThreadAction.ON_MESSAGE_ADD: {\n const { thread, subject } = intent.data ?? {};\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject && Array.isArray(subject.threads))\n ) {\n return;\n }\n\n const subjectId = fullyQualifiedId(subject);\n const space = getSpace(subject);\n const intents = [];\n const analyticsProperties = { threadId: thread.id, spaceId: space?.id };\n\n if (state.drafts[subjectId]?.find((t) => t === thread)) {\n // Move draft to document.\n thread.status = 'active';\n subject.threads ? subject.threads.push(thread) : (subject.threads = [thread]);\n state.drafts[subjectId] = state.drafts[subjectId]?.filter(({ id }) => id !== thread.id);\n intents.push({\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.thread-created', properties: analyticsProperties },\n });\n }\n\n intents.push({\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message-added',\n properties: { ...analyticsProperties, threadLength: thread.messages.length },\n },\n });\n\n return {\n data: thread,\n intents: [intents],\n };\n }\n\n case ThreadAction.DELETE_MESSAGE: {\n const { subject, thread, messageId } = intent.data ?? {};\n const space = getSpace(subject);\n\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject)\n ) {\n return;\n }\n\n if (!intent.undo) {\n const message = thread.messages.find((m) => m?.id === messageId);\n const messageIndex = thread.messages.findIndex((m) => m?.id === messageId);\n if (messageIndex === -1 || !message) {\n return undefined;\n }\n\n if (messageIndex === 0 && thread.messages.length === 1) {\n // If the message is the only message in the thread, delete the thread.\n return {\n intents: [[{ action: ThreadAction.DELETE, data: { subject, thread } }]],\n };\n } else {\n thread.messages.splice(messageIndex, 1);\n }\n\n return {\n undoable: {\n message: translations[0]['en-US'][THREAD_PLUGIN]['message deleted label'],\n data: { message, messageIndex },\n },\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message.delete',\n properties: { threadId: thread.id, spaceId: space?.id },\n },\n },\n ],\n ],\n };\n } else if (intent.undo) {\n const message = intent.data?.message;\n const messageIndex = intent.data?.messageIndex;\n if (!(message instanceof MessageType) || !(typeof messageIndex === 'number')) {\n return;\n }\n\n thread.messages.splice(messageIndex, 0, message);\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message.undo-delete',\n properties: { threadId: thread.id, spaceId: space?.id },\n },\n },\n ],\n ],\n };\n }\n }\n }\n },\n },\n markdown: {\n extensions: ({ document: doc }) => {\n return threads(state, doc, intentPlugin?.provides.intent.dispatch);\n },\n },\n },\n };\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { lazy } from 'react';\n\nexport const ThreadMain = lazy(() => import('./ThreadMain'));\nexport const ThreadArticle = lazy(() => import('./ThreadArticle'));\n\n// TODO(wittjosiah): Suspense boundary for sidebar?\nexport * from './CommentContainer';\nexport * from './CommentsContainer';\nexport * from './ChatContainer';\nexport * from './MessageContainer';\nexport * from './ThreadComplementary';\nexport * from './ThreadSettings';\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { CheckCircle, X } from '@phosphor-icons/react';\nimport React, { useCallback, useMemo, useRef, useState } from 'react';\n\nimport { create } from '@dxos/echo-schema';\nimport { MessageType } from '@dxos/plugin-space/types';\nimport { fullyQualifiedId, getSpace, useMembers } from '@dxos/react-client/echo';\nimport { useIdentity } from '@dxos/react-client/halo';\nimport { Button, Tag, Tooltip, useThemeContext, useTranslation } from '@dxos/react-ui';\nimport { createBasicExtensions, createThemeExtensions, listener } from '@dxos/react-ui-editor';\nimport {\n getSize,\n hoverableControlItem,\n hoverableControls,\n hoverableFocusedWithinControls,\n mx,\n} from '@dxos/react-ui-theme';\nimport { MessageTextbox, type MessageTextboxProps, Thread, ThreadFooter, ThreadHeading } from '@dxos/react-ui-thread';\nimport { nonNullable } from '@dxos/util';\n\nimport { MessageContainer } from './MessageContainer';\nimport { command } from './command-extension';\nimport { type ThreadContainerProps } from './types';\nimport { useStatus } from '../hooks';\nimport { THREAD_PLUGIN } from '../meta';\nimport { getMessageMetadata } from '../util';\n\nconst sizeClass = getSize(4);\n\nconst ToggleResolvedButton = ({\n isResolved,\n onResolve,\n}: {\n isResolved: boolean | undefined;\n onResolve: () => void;\n}) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const label = t(isResolved ? 'mark as unresolved label' : 'mark as resolved label');\n return (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <Button\n variant='ghost'\n data-testid='thread.toggle-resolved'\n onClick={onResolve}\n classNames={['min-bs-0 p-1', !isResolved && hoverableControlItem]}\n >\n <span className='sr-only'>{label}</span>\n {isResolved ? <CheckCircle className={sizeClass} weight='fill' /> : <CheckCircle className={sizeClass} />}\n </Button>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames={'z-[21]'}>\n {label}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n );\n};\n\nconst DeleteThreadButton = ({ onDelete }: { onDelete: () => void }) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const label = t('delete thread label');\n return (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <Button\n variant='ghost'\n data-testid='thread.delete'\n onClick={onDelete}\n classNames={['min-bs-0 p-1', hoverableControlItem]}\n >\n <span className='sr-only'>{label}</span>\n <X className={sizeClass} />\n </Button>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames='z-[21]'>\n {label}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n );\n};\n\nexport const CommentContainer = ({\n thread,\n detached,\n context,\n current,\n onAttend,\n onThreadDelete,\n onMessageDelete,\n onResolve,\n onComment,\n}: ThreadContainerProps) => {\n const identity = useIdentity()!;\n const space = getSpace(thread);\n const members = useMembers(space?.key);\n const activity = useStatus(space, fullyQualifiedId(thread));\n const { t } = useTranslation(THREAD_PLUGIN);\n const threadScrollRef = useRef<HTMLDivElement | null>(null);\n const { themeMode } = useThemeContext();\n\n const textboxMetadata = getMessageMetadata(fullyQualifiedId(thread), identity);\n // TODO(wittjosiah): This is a hack to reset the editor after a message is sent.\n const [_count, _setCount] = useState(0);\n const rerenderEditor = () => _setCount((count) => count + 1);\n const messageRef = useRef('');\n const extensions = useMemo(\n () => [\n createBasicExtensions({ placeholder: t('message placeholder') }),\n createThemeExtensions({ themeMode }),\n listener({ onChange: (text) => (messageRef.current = text) }),\n command,\n ],\n [_count],\n );\n\n // TODO(thure): Factor out.\n const scrollToEnd = (behavior: ScrollBehavior) =>\n setTimeout(() => threadScrollRef.current?.scrollIntoView({ behavior, block: 'end' }), 10);\n\n const handleCreate: MessageTextboxProps['onSend'] = useCallback(() => {\n if (!messageRef.current) {\n return false;\n }\n\n thread.messages.push(\n create(MessageType, {\n sender: { identityKey: identity.identityKey.toHex() },\n timestamp: new Date().toISOString(),\n text: messageRef.current,\n context,\n }),\n );\n onComment?.(thread);\n\n messageRef.current = '';\n scrollToEnd('instant');\n rerenderEditor();\n\n // TODO(burdon): Scroll to bottom.\n return true;\n }, [thread, identity]);\n\n return (\n <Thread onClickCapture={onAttend} onFocusCapture={onAttend} current={current} id={fullyQualifiedId(thread)}>\n <div\n role='none'\n className={mx(\n 'col-span-2 grid grid-cols-[var(--rail-size)_1fr_min-content]',\n hoverableControls,\n hoverableFocusedWithinControls,\n )}\n >\n {detached ? (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <ThreadHeading detached>{thread.name ?? t('thread title placeholder')}</ThreadHeading>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames='z-[21]' side='top'>\n {t('detached thread label')}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n ) : (\n <ThreadHeading>{thread.name ?? t('thread title placeholder')}</ThreadHeading>\n )}\n <div className='flex flex-row items-center pli-1'>\n {thread.status === 'staged' && <Tag palette='neutral'>{t('draft button')}</Tag>}\n {onResolve && !(thread?.status === 'staged') && (\n <ToggleResolvedButton isResolved={thread?.status === 'resolved'} onResolve={onResolve} />\n )}\n {onThreadDelete && <DeleteThreadButton onDelete={onThreadDelete} />}\n </div>\n </div>\n {thread.messages.filter(nonNullable).map((message) => (\n <MessageContainer\n key={message.id}\n message={message}\n members={members}\n onDelete={(id: string) => onMessageDelete?.(id)}\n />\n ))}\n {/*\n TODO(wittjosiah): Can't autofocus this generally.\n There can be multiple threads with inputs and they can't all be focused.\n Also, it steals focus from documents when first rendered.\n Need to find a way to autofocus in one scenario only: when a new thread is created.\n */}\n <MessageTextbox extensions={extensions} onSend={handleCreate} {...textboxMetadata} />\n <ThreadFooter activity={activity}>{t('activity message')}</ThreadFooter>\n {/* NOTE(thure): This can’t also be the `overflow-anchor` because `ScrollArea` injects an interceding node that contains this necessary ref’d element. */}\n <div role='none' className='bs-px -mbs-px' ref={threadScrollRef} />\n </Thread>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport { ChatText } from '@phosphor-icons/react';\nimport React, { useEffect } from 'react';\n\nimport { type ThreadType } from '@dxos/plugin-space/types';\nimport { fullyQualifiedId } from '@dxos/react-client/echo';\nimport { useTranslation, Trans } from '@dxos/react-ui';\nimport { descriptionText, mx } from '@dxos/react-ui-theme';\n\nimport { CommentContainer } from './CommentContainer';\nimport { type ThreadContainerProps } from './types';\nimport { THREAD_PLUGIN } from '../meta';\n\nexport type ThreadsContainerProps = Omit<\n ThreadContainerProps,\n 'thread' | 'detached' | 'onAttend' | 'onThreadDelete' | 'onMessageDelete' | 'current' | 'autoFocus'\n> & {\n threads: ThreadType[];\n /**\n * Threads that are no longer anchored to a position in the object.\n */\n detached?: string[];\n currentId?: string;\n showResolvedThreads?: boolean;\n onThreadAttend?: (thread: ThreadType) => void;\n onThreadDelete?: (thread: ThreadType) => void;\n onMessageDelete?: (thread: ThreadType, messageId: string) => void;\n onThreadToggleResolved?: (thread: ThreadType) => void;\n onComment?: (thread: ThreadType) => void;\n};\n\n/**\n * Comment threads.\n */\nexport const CommentsContainer = ({\n threads,\n detached = [],\n currentId,\n showResolvedThreads,\n onThreadAttend,\n onThreadDelete,\n onMessageDelete,\n onThreadToggleResolved,\n ...props\n}: ThreadsContainerProps) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const filteredThreads = showResolvedThreads ? threads : threads.filter((thread) => !(thread?.status === 'resolved'));\n\n useEffect(() => {\n if (currentId) {\n document.getElementById(currentId)?.scrollIntoView({ behavior: 'smooth', block: 'end' });\n }\n }, [currentId]);\n\n return (\n <>\n {filteredThreads.length > 0 ? (\n filteredThreads.map((thread) => {\n const threadId = fullyQualifiedId(thread);\n return (\n <CommentContainer\n key={threadId}\n thread={thread}\n current={currentId === threadId}\n detached={detached.includes(threadId)}\n {...(onThreadAttend && { onAttend: () => onThreadAttend(thread) })}\n {...(onThreadDelete && { onThreadDelete: () => onThreadDelete(thread) })}\n {...(onMessageDelete && { onMessageDelete: (messageId: string) => onMessageDelete(thread, messageId) })}\n {...(onThreadToggleResolved && { onResolve: () => onThreadToggleResolved(thread) })}\n {...props}\n />\n );\n })\n ) : (\n <div\n role='alert'\n className={mx(\n descriptionText,\n 'place-self-center border border-dashed border-neutral-400/50 rounded-lg text-center p-4 m-4',\n )}\n >\n <h2 className='mbe-2 font-medium text-baseText'>{t('no comments title')}</h2>\n <p>\n <Trans\n {...{\n t,\n i18nKey: 'no comments message',\n components: {\n commentIcon: <ChatText className='inline-block' />,\n },\n }}\n />\n </p>\n </div>\n )}\n </>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport React, { useEffect, useMemo } from 'react';\n\nimport { LayoutAction, type Plugin, useIntentDispatcher, useResolvePlugins } from '@dxos/app-framework';\nimport { type ThreadType } from '@dxos/plugin-space';\nimport { fullyQualifiedId } from '@dxos/react-client/echo';\nimport { ScrollArea } from '@dxos/react-ui';\nimport { useAttended } from '@dxos/react-ui-attention';\nimport { nonNullable } from '@dxos/util';\n\nimport { CommentsContainer } from '../components';\nimport { THREAD_PLUGIN } from '../meta';\nimport { ThreadAction, type ThreadProvides } from '../types';\n\nconst providesThreadsConfig = (plugin: any): Plugin<ThreadProvides<any>> | undefined =>\n 'thread' in plugin.provides ? (plugin as Plugin<ThreadProvides<any>>) : undefined;\n\nexport const ThreadComplementary = ({\n role,\n subject,\n drafts,\n current,\n showResolvedThreads,\n}: {\n role: string;\n subject: any;\n drafts: ThreadType[] | undefined;\n current?: string;\n showResolvedThreads?: boolean;\n}) => {\n const dispatch = useIntentDispatcher();\n\n const threadsIntegrators = useResolvePlugins(providesThreadsConfig);\n const threadProvides = useMemo(() => threadsIntegrators.map((p) => p.provides.thread), [threadsIntegrators]);\n const createSort = useMemo(\n () => threadProvides.find((p) => p.predicate(subject))?.createSort,\n [threadProvides, subject],\n );\n const sort = useMemo(() => createSort?.(subject), [createSort, subject]);\n\n const threads = useMemo(() => {\n return subject.threads.concat(drafts ?? []).filter(nonNullable) as ThreadType[];\n }, [JSON.stringify(subject.threads), JSON.stringify(drafts)]);\n\n const detachedIds = useMemo(() => {\n return threads.filter(({ anchor }) => !anchor).map((thread) => fullyQualifiedId(thread));\n }, [threads]);\n\n useEffect(() => {\n if (!sort) {\n return;\n }\n threads.sort((a, b) => sort(a?.anchor, b?.anchor));\n }, [sort, threads]);\n\n const attended = useAttended();\n const qualifiedSubjectId = fullyQualifiedId(subject);\n\n return (\n <div role='none' className='contents'>\n <ScrollArea.Root classNames='row-span-2'>\n <ScrollArea.Viewport>\n <CommentsContainer\n threads={threads}\n detached={detachedIds}\n currentId={attended.includes(qualifiedSubjectId) ? current : undefined}\n showResolvedThreads={showResolvedThreads}\n onThreadAttend={(thread) => {\n const threadId = fullyQualifiedId(thread);\n if (current !== threadId) {\n current = threadId;\n\n void dispatch?.([\n {\n action: LayoutAction.SCROLL_INTO_VIEW,\n data: {\n id: fullyQualifiedId(subject),\n thread: threadId,\n cursor: thread.anchor,\n },\n },\n ]);\n }\n }}\n onThreadDelete={(thread) => {\n return dispatch({ plugin: THREAD_PLUGIN, action: ThreadAction.DELETE, data: { subject, thread } });\n }}\n onMessageDelete={(thread, messageId) =>\n dispatch({\n plugin: THREAD_PLUGIN,\n action: ThreadAction.DELETE_MESSAGE,\n data: { subject, thread, messageId },\n })\n }\n onThreadToggleResolved={(thread) =>\n dispatch({ plugin: THREAD_PLUGIN, action: ThreadAction.TOGGLE_RESOLVED, data: { thread } })\n }\n onComment={(thread) => {\n void dispatch({ action: ThreadAction.ON_MESSAGE_ADD, data: { thread, subject } });\n }}\n />\n <div role='none' className='bs-10' />\n <ScrollArea.Scrollbar>\n <ScrollArea.Thumb />\n </ScrollArea.Scrollbar>\n </ScrollArea.Viewport>\n </ScrollArea.Root>\n </div>\n );\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport React from 'react';\n\nimport { SettingsValue } from '@dxos/plugin-settings';\nimport { Input, useTranslation } from '@dxos/react-ui';\n\nimport { THREAD_PLUGIN } from '../meta';\nimport type { ThreadSettingsProps } from '../types';\n\nexport const ThreadSettings = ({ settings }: { settings: ThreadSettingsProps }) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n\n return (\n <>\n <SettingsValue label={t('settings standalone label')}>\n <Input.Switch checked={settings.standalone} onCheckedChange={(checked) => (settings.standalone = !!checked)} />\n </SettingsValue>\n </>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport { type Extension } from '@codemirror/state';\nimport { EditorView } from '@codemirror/view';\nimport { computed, effect } from '@preact/signals-core';\n\nimport { type IntentDispatcher } from '@dxos/app-framework';\nimport { type DocumentType } from '@dxos/plugin-markdown/types';\nimport { ThreadType } from '@dxos/plugin-space/types';\nimport { getSpace, getTextInRange, createDocAccessor, fullyQualifiedId } from '@dxos/react-client/echo';\nimport { comments, createExternalCommentSync } from '@dxos/react-ui-editor';\nimport { nonNullable } from '@dxos/util';\n\nimport { ThreadAction, type ThreadState } from '../types';\n\n// TODO(burdon): Factor out.\nconst getName = (doc: DocumentType, anchor: string): string | undefined => {\n if (doc.content) {\n const [start, end] = anchor.split(':');\n return getTextInRange(createDocAccessor(doc.content, ['content']), start, end);\n }\n};\n\n/**\n * Construct plugins.\n */\nexport const threads = (state: ThreadState, doc?: DocumentType, dispatch?: IntentDispatcher): Extension => {\n const space = doc && getSpace(doc);\n if (!doc || !space || !dispatch) {\n // Include no-op comments extension here to ensure that the facets are always present when they are expected.\n // TODO(wittjosiah): The Editor should only look for these facets when comments are available.\n return [comments()];\n }\n\n // TODO(Zan): When we have the deepsignal specific equivalent of this we should use that instead.\n const threads = computed(() =>\n [...doc.threads.filter(nonNullable), ...(state.drafts[fullyQualifiedId(doc)] ?? [])].filter(\n (thread) => !(thread?.status === 'resolved'),\n ),\n );\n\n return [\n EditorView.updateListener.of((update) => {\n if (update.docChanged) {\n doc.threads.forEach((thread) => {\n if (thread?.anchor) {\n // Only update if the name has changed, otherwise this will cause an infinite loop.\n // Skip if the name is empty; this means comment text was deleted, but thread name should remain.\n const name = getName(doc, thread.anchor);\n if (name && name !== thread.name) {\n thread.name = name;\n }\n }\n });\n }\n }),\n\n createExternalCommentSync(\n fullyQualifiedId(doc),\n (sink) => effect(() => sink()),\n () =>\n threads.value\n .filter((thread) => thread?.anchor)\n .map((thread) => ({ id: fullyQualifiedId(thread), cursor: thread.anchor! })),\n ),\n\n comments({\n id: fullyQualifiedId(doc),\n onCreate: ({ cursor }) => {\n const name = getName(doc, cursor);\n void dispatch({\n action: ThreadAction.CREATE,\n data: {\n cursor,\n name,\n subject: doc,\n },\n });\n },\n onDelete: ({ id }) => {\n const draft = state.drafts[fullyQualifiedId(doc)];\n if (draft) {\n const index = draft.findIndex((thread) => fullyQualifiedId(thread) === id);\n if (index !== -1) {\n draft.splice(index, 1);\n }\n }\n\n const thread = doc.threads.find((thread) => thread?.id === id);\n if (thread) {\n thread.anchor = undefined;\n }\n },\n onUpdate: ({ id, cursor }) => {\n const thread =\n state.drafts[fullyQualifiedId(doc)]?.find((thread) => fullyQualifiedId(thread) === id) ??\n doc.threads.find((thread) => thread?.id === id);\n\n if (thread instanceof ThreadType && thread.anchor) {\n thread.name = getName(doc, thread.anchor);\n thread.anchor = cursor;\n }\n },\n onSelect: ({ selection: { current, closest } }) => {\n void dispatch({\n action: ThreadAction.SELECT,\n data: {\n current: current ?? closest,\n skipOpen: true,\n },\n });\n },\n }),\n ];\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { THREAD_PLUGIN } from './meta';\n\nexport default [\n {\n 'en-US': {\n [THREAD_PLUGIN]: {\n 'plugin name': 'Threads',\n 'channel name placeholder': 'New channel',\n 'channel title label': 'Title',\n 'delete channel label': 'Delete channel',\n 'create channel label': 'Create channel',\n 'message placeholder': 'Reply…',\n 'settings standalone label': 'Enable channel creation (experimental)',\n 'activity message': 'Processing…',\n 'anonymous label': 'Anonymous',\n 'delete message block label': 'Delete message block',\n 'detached thread label': 'Referenced content was removed',\n 'delete thread label': 'Delete thread',\n 'thread deleted label': 'You deleted a thread.',\n 'message deleted label': 'You deleted a message.',\n 'comments heading': 'Comments',\n 'chat heading': 'Chat',\n 'draft button': 'DRAFT',\n 'no comments title': 'No comments (yet)',\n 'no comments message':\n 'To start a comment thread, select a range of text in a document and click the <commentIcon></commentIcon> Create comment button in the toolbar.',\n 'toggle show resolved': 'Show resolved',\n 'unnamed object threads label': 'Threads',\n 'mark as resolved label': 'Mark as resolved',\n 'mark as unresolved label': 'Mark as unresolved',\n 'save message label': 'Save',\n 'edit message label': 'Edit',\n 'delete message label': 'Delete message',\n },\n },\n },\n];\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { ThreadPlugin } from './ThreadPlugin';\n\nexport default ThreadPlugin;\n\nexport * from './hooks';\nexport * from './types';\n\nexport * from './ThreadPlugin';\n"],
5
- "mappings": "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",
6
- "names": ["React", "NavigationAction", "isLayoutParts", "parseIntentPlugin", "parseNavigationPlugin", "parseMetadataResolverPlugin", "resolvePlugin", "LayoutAction", "LocalStorageStore", "log", "parseClientPlugin", "createExtension", "isActionGroup", "toSignal", "ObservabilityAction", "SpaceAction", "ThreadType", "MessageType", "ChannelType", "create", "getTypename", "getSpace", "fullyQualifiedId", "loadObjectReferences", "parseFullyQualifiedId", "translations", "threadTranslations", "lazy", "CheckCircle", "X", "React", "useCallback", "useMemo", "useRef", "useState", "create", "MessageType", "fullyQualifiedId", "getSpace", "useMembers", "useIdentity", "Button", "Tag", "Tooltip", "useThemeContext", "useTranslation", "createBasicExtensions", "createThemeExtensions", "listener", "getSize", "hoverableControlItem", "hoverableControls", "hoverableFocusedWithinControls", "mx", "MessageTextbox", "Thread", "ThreadFooter", "ThreadHeading", "nonNullable", "sizeClass", "getSize", "ToggleResolvedButton", "isResolved", "onResolve", "t", "useTranslation", "THREAD_PLUGIN", "label", "Tooltip", "Root", "Trigger", "asChild", "Button", "variant", "data-testid", "onClick", "classNames", "hoverableControlItem", "span", "className", "CheckCircle", "weight", "Portal", "Content", "Arrow", "DeleteThreadButton", "onDelete", "X", "CommentContainer", "thread", "detached", "context", "current", "onAttend", "onThreadDelete", "onMessageDelete", "onComment", "identity", "useIdentity", "space", "getSpace", "members", "useMembers", "key", "activity", "useStatus", "fullyQualifiedId", "threadScrollRef", "useRef", "themeMode", "useThemeContext", "textboxMetadata", "getMessageMetadata", "_count", "_setCount", "useState", "rerenderEditor", "count", "messageRef", "extensions", "useMemo", "createBasicExtensions", "placeholder", "createThemeExtensions", "listener", "onChange", "text", "command", "scrollToEnd", "behavior", "setTimeout", "scrollIntoView", "block", "handleCreate", "useCallback", "messages", "push", "create", "MessageType", "sender", "identityKey", "toHex", "timestamp", "Date", "toISOString", "Thread", "onClickCapture", "onFocusCapture", "id", "div", "role", "mx", "hoverableControls", "hoverableFocusedWithinControls", "ThreadHeading", "name", "side", "status", "Tag", "palette", "filter", "nonNullable", "map", "message", "MessageContainer", "MessageTextbox", "onSend", "ThreadFooter", "ref", "ChatText", "React", "useEffect", "fullyQualifiedId", "useTranslation", "Trans", "descriptionText", "mx", "CommentsContainer", "threads", "detached", "currentId", "showResolvedThreads", "onThreadAttend", "onThreadDelete", "onMessageDelete", "onThreadToggleResolved", "props", "t", "useTranslation", "THREAD_PLUGIN", "filteredThreads", "filter", "thread", "status", "useEffect", "document", "getElementById", "scrollIntoView", "behavior", "block", "React", "length", "map", "threadId", "fullyQualifiedId", "CommentContainer", "key", "current", "includes", "onAttend", "messageId", "onResolve", "div", "role", "className", "mx", "descriptionText", "h2", "p", "Trans", "i18nKey", "components", "commentIcon", "ChatText", "React", "useEffect", "useMemo", "LayoutAction", "useIntentDispatcher", "useResolvePlugins", "fullyQualifiedId", "ScrollArea", "useAttended", "nonNullable", "providesThreadsConfig", "plugin", "provides", "undefined", "ThreadComplementary", "role", "subject", "drafts", "current", "showResolvedThreads", "dispatch", "useIntentDispatcher", "threadsIntegrators", "useResolvePlugins", "threadProvides", "useMemo", "map", "p", "thread", "createSort", "find", "predicate", "sort", "threads", "concat", "filter", "nonNullable", "JSON", "stringify", "detachedIds", "anchor", "fullyQualifiedId", "useEffect", "a", "b", "attended", "useAttended", "qualifiedSubjectId", "React", "div", "className", "ScrollArea", "Root", "classNames", "Viewport", "CommentsContainer", "detached", "currentId", "includes", "onThreadAttend", "threadId", "action", "LayoutAction", "SCROLL_INTO_VIEW", "data", "id", "cursor", "onThreadDelete", "THREAD_PLUGIN", "ThreadAction", "DELETE", "onMessageDelete", "messageId", "DELETE_MESSAGE", "onThreadToggleResolved", "TOGGLE_RESOLVED", "onComment", "ON_MESSAGE_ADD", "Scrollbar", "Thumb", "React", "SettingsValue", "Input", "useTranslation", "ThreadSettings", "settings", "t", "useTranslation", "THREAD_PLUGIN", "React", "SettingsValue", "label", "Input", "Switch", "checked", "standalone", "onCheckedChange", "ThreadMain", "lazy", "ThreadArticle", "EditorView", "computed", "effect", "ThreadType", "getSpace", "getTextInRange", "createDocAccessor", "fullyQualifiedId", "comments", "createExternalCommentSync", "nonNullable", "getName", "doc", "anchor", "content", "start", "end", "split", "getTextInRange", "createDocAccessor", "threads", "state", "dispatch", "space", "getSpace", "comments", "computed", "filter", "nonNullable", "drafts", "fullyQualifiedId", "thread", "status", "EditorView", "updateListener", "of", "update", "docChanged", "forEach", "name", "createExternalCommentSync", "sink", "effect", "value", "map", "id", "cursor", "onCreate", "action", "ThreadAction", "CREATE", "data", "subject", "onDelete", "draft", "index", "findIndex", "splice", "find", "undefined", "onUpdate", "ThreadType", "onSelect", "selection", "current", "closest", "SELECT", "skipOpen", "THREAD_PLUGIN", "initialViewState", "showResolvedThreads", "ThreadPlugin", "settings", "LocalStorageStore", "THREAD_PLUGIN", "state", "create", "drafts", "viewStore", "getViewState", "subjectId", "navigationPlugin", "intentPlugin", "unsubscribeCallbacks", "meta", "ready", "plugins", "prop", "key", "type", "bool", "allowUndefined", "resolvePlugin", "parseNavigationPlugin", "parseIntentPlugin", "unload", "forEach", "unsubscribe", "provides", "values", "metadata", "records", "ChannelType", "typename", "placeholder", "ns", "icon", "loadReferences", "channel", "loadObjectReferences", "threads", "ThreadType", "thread", "messages", "MessageType", "message", "THREAD_ITEM", "parse", "item", "id", "label", "title", "data", "object", "translations", "threadTranslations", "echo", "schema", "graph", "builder", "client", "parseClientPlugin", "dispatch", "intent", "metadataResolver", "parseMetadataResolverPlugin", "resolver", "createExtension", "endsWith", "split", "spaceId", "objectId", "parseFullyQualifiedId", "space", "spaces", "get", "find", "toSignal", "onChange", "timeout", "setTimeout", "db", "loadObjectById", "clearTimeout", "getObjectById", "getTypename", "name", "viewState", "properties", "actions", "node", "dataId", "at", "toggle", "newToggleState", "action", "ObservabilityAction", "SEND_EVENT", "threadId", "showResolved", "menuItemType", "isChecked", "testId", "ThreadAction", "CREATE", "filter", "standalone", "isActionGroup", "startsWith", "SpaceAction", "ADD_OBJECT", "target", "plugin", "NavigationAction", "OPEN", "surface", "component", "role", "active", "React", "ThreadMain", "ThreadSettings", "location", "isLayoutParts", "main", "layoutEntries", "currentPosition", "findIndex", "entry", "objectToTheLeft", "context", "getSpace", "ThreadArticle", "subject", "ChatHeading", "attendableId", "ChatContainer", "Array", "isArray", "fullyQualifiedId", "ThreadComplementary", "current", "cursor", "undefined", "err", "log", "error", "anchor", "status", "draft", "push", "intents", "SELECT", "activeParts", "complementary", "LayoutAction", "SET_LAYOUT", "element", "skipOpen", "TOGGLE_RESOLVED", "DELETE", "index", "t", "splice", "undo", "remove", "undoable", "savedThread", "add", "ON_MESSAGE_ADD", "analyticsProperties", "threadLength", "length", "DELETE_MESSAGE", "messageId", "m", "messageIndex", "markdown", "extensions", "document", "doc", "ThreadPlugin"]
4
+ "sourcesContent": ["//\n// Copyright 2023 DXOS.org\n//\n\nimport React from 'react';\n\nimport {\n type IntentPluginProvides,\n type LocationProvides,\n NavigationAction,\n type Plugin,\n type PluginDefinition,\n isLayoutParts,\n parseIntentPlugin,\n parseNavigationPlugin,\n parseMetadataResolverPlugin,\n resolvePlugin,\n LayoutAction,\n} from '@dxos/app-framework';\nimport { type UnsubscribeCallback } from '@dxos/async';\nimport { LocalStorageStore } from '@dxos/local-storage';\nimport { log } from '@dxos/log';\nimport { parseClientPlugin } from '@dxos/plugin-client';\nimport { type ActionGroup, createExtension, isActionGroup, toSignal } from '@dxos/plugin-graph';\nimport { ObservabilityAction } from '@dxos/plugin-observability/meta';\nimport { SpaceAction } from '@dxos/plugin-space';\nimport { ThreadType, MessageType, ChannelType } from '@dxos/plugin-space/types';\nimport { create, type EchoReactiveObject, getTypename } from '@dxos/react-client/echo';\nimport { getSpace, fullyQualifiedId, loadObjectReferences, parseId } from '@dxos/react-client/echo';\nimport { translations as threadTranslations } from '@dxos/react-ui-thread';\n\nimport {\n ChatContainer,\n ChatHeading,\n ThreadArticle,\n ThreadComplementary,\n ThreadMain,\n ThreadSettings,\n} from './components';\nimport { threads } from './extensions';\nimport meta, { THREAD_ITEM, THREAD_PLUGIN } from './meta';\nimport translations from './translations';\nimport { ThreadAction, type ThreadPluginProvides, type ThreadSettingsProps, type ThreadState } from './types';\n\ntype SubjectId = string;\n\nconst initialViewState = { showResolvedThreads: false };\n\ntype ViewStore = Record<SubjectId, typeof initialViewState>;\n\n// TODO(Zan): Every instance of `cursor` should be replaced with `anchor`.\n// NOTE(burdon): Review/discuss CursorConverter semantics.\nexport const ThreadPlugin = (): PluginDefinition<ThreadPluginProvides> => {\n const settings = new LocalStorageStore<ThreadSettingsProps>(THREAD_PLUGIN);\n const state = create<ThreadState>({ drafts: {} });\n\n const viewStore = create<ViewStore>({});\n const getViewState = (subjectId: string) => {\n if (!viewStore[subjectId]) {\n viewStore[subjectId] = { ...initialViewState };\n }\n return viewStore[subjectId];\n };\n\n let navigationPlugin: Plugin<LocationProvides> | undefined;\n let intentPlugin: Plugin<IntentPluginProvides> | undefined;\n\n const unsubscribeCallbacks = [] as UnsubscribeCallback[];\n\n return {\n meta,\n ready: async (plugins) => {\n settings.prop({ key: 'standalone', type: LocalStorageStore.bool({ allowUndefined: true }) });\n\n navigationPlugin = resolvePlugin(plugins, parseNavigationPlugin);\n intentPlugin = resolvePlugin(plugins, parseIntentPlugin)!;\n },\n unload: async () => {\n unsubscribeCallbacks.forEach((unsubscribe) => unsubscribe());\n },\n provides: {\n settings: settings.values,\n metadata: {\n records: {\n [ChannelType.typename]: {\n placeholder: ['channel title placeholder', { ns: THREAD_PLUGIN }],\n icon: 'ph--chat--regular',\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (channel: ChannelType) => loadObjectReferences(channel, (channel) => channel.threads),\n },\n [ThreadType.typename]: {\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (thread: ThreadType) => loadObjectReferences(thread, (thread) => thread.messages),\n },\n [MessageType.typename]: {\n // TODO(wittjosiah): Move out of metadata.\n loadReferences: (message: MessageType) => [], // loadObjectReferences(message, (message) => [...message.parts, message.context]),\n },\n [THREAD_ITEM]: {\n parse: (item: EchoReactiveObject<any>, type: string) => {\n switch (type) {\n case 'node':\n return { id: item.id, label: item.title, data: item };\n case 'object':\n return item;\n case 'view-object':\n return { id: `${item.id}-view`, object: item };\n }\n },\n },\n },\n },\n translations: [...translations, ...threadTranslations],\n echo: { schema: [ChannelType, ThreadType, MessageType] },\n graph: {\n builder: (plugins) => {\n const client = resolvePlugin(plugins, parseClientPlugin)?.provides.client;\n const dispatch = resolvePlugin(plugins, parseIntentPlugin)?.provides.intent.dispatch;\n const metadataResolver = resolvePlugin(plugins, parseMetadataResolverPlugin)?.provides.metadata.resolver;\n if (!client || !dispatch || !metadataResolver) {\n return [];\n }\n\n const type = 'orphan-comments-for-subject';\n const icon = 'ph--chat-text--regular';\n\n return [\n createExtension({\n id: `${THREAD_PLUGIN}/comments-for-subject`,\n resolver: ({ id }) => {\n // TODO(Zan): Find util (or make one).\n if (!id.endsWith('~comments')) {\n return;\n }\n\n const [subjectId] = id.split('~');\n const { spaceId, objectId } = parseId(subjectId);\n const space = client.spaces.get().find((space) => space.id === spaceId);\n if (!objectId) {\n // TODO(wittjosiah): Support comments for arbitrary subjects.\n // This is to ensure that the comments panel is not stuck on an old object.\n return {\n id,\n type,\n data: null,\n properties: {\n icon,\n label: ['unnamed object threads label', { ns: THREAD_PLUGIN }],\n showResolvedThreads: false,\n object: null,\n space,\n },\n };\n }\n\n const object = toSignal(\n (onChange) => {\n const timeout = setTimeout(async () => {\n await space?.db.loadObjectById(objectId);\n onChange();\n });\n\n return () => clearTimeout(timeout);\n },\n () => space?.db.getObjectById(objectId),\n subjectId,\n );\n if (!object || !subjectId) {\n return;\n }\n\n const meta = metadataResolver(getTypename(object) ?? '');\n const label = meta.label?.(object) ||\n object.name ||\n meta.placeholder || ['unnamed object threads label', { ns: THREAD_PLUGIN }];\n\n const viewState = getViewState(subjectId);\n\n return {\n id,\n type,\n data: null,\n properties: {\n icon,\n label,\n showResolvedThreads: viewState.showResolvedThreads,\n object,\n },\n };\n },\n actions: ({ node }) => {\n const dataId = node.id.split('~').at(0);\n if (!node.id.endsWith('~comments') || !dataId) {\n return;\n }\n\n const [spaceId, objectId] = dataId.split(':');\n\n const viewState = getViewState(dataId);\n const toggle = () => {\n const newToggleState = !viewState.showResolvedThreads;\n viewState.showResolvedThreads = newToggleState;\n void dispatch({\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.toggle-show-resolved',\n properties: { spaceId, threadId: objectId, showResolved: newToggleState },\n },\n });\n };\n\n return [\n {\n id: `${THREAD_PLUGIN}/toggle-show-resolved/${node.id}`,\n data: toggle,\n properties: {\n label: ['toggle show resolved', { ns: THREAD_PLUGIN }],\n menuItemType: 'toggle',\n isChecked: viewState.showResolvedThreads,\n testId: 'threadPlugin.toggleShowResolved',\n icon: viewState.showResolvedThreads ? 'ph--eye-slash--regular' : 'ph--eye--regular',\n },\n },\n ];\n },\n }),\n createExtension({\n id: ThreadAction.CREATE,\n filter: (node): node is ActionGroup =>\n !!settings.values.standalone && isActionGroup(node) && node.id.startsWith(SpaceAction.ADD_OBJECT),\n actions: ({ node }) => {\n const id = node.id.split('/').at(-1);\n const [spaceId, objectId] = id?.split(':') ?? [];\n const space = client.spaces.get().find((space) => space.id === spaceId);\n const object = objectId && space?.db.getObjectById(objectId);\n const target = objectId ? object : space;\n if (!target) {\n return;\n }\n\n return [\n {\n id: `${THREAD_PLUGIN}/create/${node.id}`,\n data: async () => {\n await dispatch([\n { plugin: THREAD_PLUGIN, action: ThreadAction.CREATE },\n { action: SpaceAction.ADD_OBJECT, data: { target } },\n { action: NavigationAction.OPEN },\n ]);\n },\n properties: {\n label: ['create channel label', { ns: THREAD_PLUGIN }],\n icon: 'ph--chat--regular',\n testId: 'threadPlugin.createObject',\n },\n },\n ];\n },\n }),\n ];\n },\n },\n surface: {\n component: ({ data, role }) => {\n switch (role) {\n case 'main': {\n return data.active instanceof ChannelType && data.active.threads[0] ? (\n <ThreadMain thread={data.active.threads[0]} />\n ) : null;\n }\n\n case 'settings': {\n return data.plugin === meta.id ? <ThreadSettings settings={settings.values} /> : null;\n }\n\n case 'article': {\n const location = navigationPlugin?.provides.location;\n\n if (data.object instanceof ChannelType && data.object.threads[0]) {\n const channel = data.object;\n // TODO(zan): Maybe we should have utility for positional main object ids.\n if (isLayoutParts(location?.active) && location.active.main) {\n const layoutEntries = location.active.main;\n const currentPosition = layoutEntries.findIndex((entry) => channel.id === entry.id);\n if (currentPosition > 0) {\n const objectToTheLeft = layoutEntries[currentPosition - 1];\n const context = getSpace(data.object)?.db.getObjectById(objectToTheLeft.id);\n return <ThreadArticle thread={data.object.threads[0]} context={context} />;\n }\n }\n\n return <ThreadArticle thread={data.object.threads[0]} />;\n }\n\n if (data.subject instanceof ThreadType) {\n return (\n <>\n <ChatHeading attendableId={data.subject.id} />\n <ChatContainer thread={data.subject} />\n </>\n );\n }\n\n break;\n }\n\n case 'complementary--comments': {\n if (\n data.subject &&\n typeof data.subject === 'object' &&\n 'threads' in data.subject &&\n Array.isArray(data.subject.threads)\n ) {\n const { showResolvedThreads } = getViewState(fullyQualifiedId(data.subject));\n\n return (\n <ThreadComplementary\n role={role}\n subject={data.subject}\n drafts={state.drafts[fullyQualifiedId(data.subject)]}\n current={state.current}\n showResolvedThreads={showResolvedThreads}\n />\n );\n }\n\n break;\n }\n }\n\n return null;\n },\n },\n intent: {\n resolver: async (intent) => {\n switch (intent.action) {\n case ThreadAction.CREATE: {\n if (intent.data && intent.data.cursor !== undefined) {\n const { cursor, name, subject } = intent.data;\n\n // Seed the threads array if it does not exist.\n if (subject?.threads === undefined) {\n try {\n // Static schema will throw an error if subject does not support threads array property.\n subject.threads = [];\n } catch (err) {\n log.error('Subject does not support threads array', subject?.typename);\n return;\n }\n }\n\n const subjectId = fullyQualifiedId(subject);\n const thread = create(ThreadType, { name, anchor: cursor, messages: [], status: 'staged' });\n const draft = state.drafts[subjectId];\n if (draft) {\n draft.push(thread);\n } else {\n state.drafts[subjectId] = [thread];\n }\n\n return {\n data: thread,\n intents: [\n [\n {\n action: ThreadAction.SELECT,\n data: { current: fullyQualifiedId(thread) },\n },\n ],\n [\n {\n action: NavigationAction.OPEN,\n data: {\n activeParts: { complementary: 'comments' },\n },\n },\n ],\n [\n {\n action: LayoutAction.SET_LAYOUT,\n data: {\n element: 'complementary',\n state: true,\n },\n },\n ],\n ],\n };\n } else {\n // NOTE: This is the standalone thread creation case.\n return {\n data: create(ChannelType, { threads: [create(ThreadType, { messages: [] })] }),\n };\n }\n }\n\n case ThreadAction.SELECT: {\n state.current = intent.data?.current;\n\n return {\n data: true,\n intents: !intent.data?.skipOpen\n ? [\n [\n {\n action: NavigationAction.OPEN,\n data: {\n activeParts: { complementary: 'comments' },\n },\n },\n ],\n ]\n : [],\n };\n }\n\n case ThreadAction.TOGGLE_RESOLVED: {\n const { thread } = intent.data ?? {};\n if (!(thread instanceof ThreadType)) {\n return;\n }\n\n if (thread.status === 'active' || thread.status === undefined) {\n thread.status = 'resolved';\n } else if (thread.status === 'resolved') {\n thread.status = 'active';\n }\n\n const space = getSpace(thread);\n const spaceId = space?.id;\n\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.toggle-resolved', properties: { threadId: thread.id, spaceId } },\n },\n ],\n ],\n };\n }\n\n case ThreadAction.DELETE: {\n const { subject, thread } = intent.data ?? {};\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject)\n ) {\n return;\n }\n\n const subjectId = fullyQualifiedId(subject);\n const draft = state.drafts[subjectId];\n if (draft) {\n // Check if we're deleting a draft; if so, remove it.\n const index = draft.findIndex((t) => t.id === thread.id);\n if (index !== -1) {\n draft.splice(index, 1);\n return { data: true };\n }\n }\n\n const space = getSpace(thread);\n if (!space || !subject.threads) {\n return;\n }\n\n if (!intent.undo) {\n const index = subject.threads.findIndex((t: any) => t?.id === thread.id);\n const cursor = subject.threads[index]?.anchor;\n if (index !== -1) {\n subject.threads?.splice(index, 1);\n }\n\n space.db.remove(thread);\n\n return {\n undoable: {\n message: translations[0]['en-US'][THREAD_PLUGIN]['thread deleted label'],\n data: { cursor },\n },\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.delete', properties: { threadId: thread.id, spaceId: space.id } },\n },\n ],\n ],\n };\n } else if (intent.undo) {\n // TODO(wittjosiah): SDK should do this automatically.\n const savedThread = space.db.add(thread);\n subject.threads.push(savedThread);\n\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.undo-delete', properties: { threadId: thread.id, spaceId: space.id } },\n },\n ],\n ],\n };\n }\n break;\n }\n\n case ThreadAction.ON_MESSAGE_ADD: {\n const { thread, subject } = intent.data ?? {};\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject && Array.isArray(subject.threads))\n ) {\n return;\n }\n\n const subjectId = fullyQualifiedId(subject);\n const space = getSpace(subject);\n const intents = [];\n const analyticsProperties = { threadId: thread.id, spaceId: space?.id };\n\n if (state.drafts[subjectId]?.find((t) => t === thread)) {\n // Move draft to document.\n thread.status = 'active';\n subject.threads ? subject.threads.push(thread) : (subject.threads = [thread]);\n state.drafts[subjectId] = state.drafts[subjectId]?.filter(({ id }) => id !== thread.id);\n intents.push({\n action: ObservabilityAction.SEND_EVENT,\n data: { name: 'threads.thread-created', properties: analyticsProperties },\n });\n }\n\n intents.push({\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message-added',\n properties: { ...analyticsProperties, threadLength: thread.messages.length },\n },\n });\n\n return {\n data: thread,\n intents: [intents],\n };\n }\n\n case ThreadAction.DELETE_MESSAGE: {\n const { subject, thread, messageId } = intent.data ?? {};\n const space = getSpace(subject);\n\n if (\n !(thread instanceof ThreadType) ||\n !(subject && typeof subject === 'object' && 'threads' in subject)\n ) {\n return;\n }\n\n if (!intent.undo) {\n const message = thread.messages.find((m) => m?.id === messageId);\n const messageIndex = thread.messages.findIndex((m) => m?.id === messageId);\n if (messageIndex === -1 || !message) {\n return undefined;\n }\n\n if (messageIndex === 0 && thread.messages.length === 1) {\n // If the message is the only message in the thread, delete the thread.\n return {\n intents: [[{ action: ThreadAction.DELETE, data: { subject, thread } }]],\n };\n } else {\n thread.messages.splice(messageIndex, 1);\n }\n\n return {\n undoable: {\n message: translations[0]['en-US'][THREAD_PLUGIN]['message deleted label'],\n data: { message, messageIndex },\n },\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message.delete',\n properties: { threadId: thread.id, spaceId: space?.id },\n },\n },\n ],\n ],\n };\n } else if (intent.undo) {\n const message = intent.data?.message;\n const messageIndex = intent.data?.messageIndex;\n if (!(message instanceof MessageType) || !(typeof messageIndex === 'number')) {\n return;\n }\n\n thread.messages.splice(messageIndex, 0, message);\n return {\n data: true,\n intents: [\n [\n {\n action: ObservabilityAction.SEND_EVENT,\n data: {\n name: 'threads.message.undo-delete',\n properties: { threadId: thread.id, spaceId: space?.id },\n },\n },\n ],\n ],\n };\n }\n }\n }\n },\n },\n markdown: {\n extensions: ({ document: doc }) => {\n return threads(state, doc, intentPlugin?.provides.intent.dispatch);\n },\n },\n },\n };\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { lazy } from 'react';\n\nexport const ThreadMain = lazy(() => import('./ThreadMain'));\nexport const ThreadArticle = lazy(() => import('./ThreadArticle'));\n\n// TODO(wittjosiah): Suspense boundary for sidebar?\nexport * from './CommentContainer';\nexport * from './CommentsContainer';\nexport * from './ChatContainer';\nexport * from './MessageContainer';\nexport * from './ThreadComplementary';\nexport * from './ThreadSettings';\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { CheckCircle, X } from '@phosphor-icons/react';\nimport React, { useCallback, useMemo, useRef, useState } from 'react';\n\nimport { create } from '@dxos/echo-schema';\nimport { MessageType } from '@dxos/plugin-space/types';\nimport { fullyQualifiedId, getSpace, useMembers } from '@dxos/react-client/echo';\nimport { useIdentity } from '@dxos/react-client/halo';\nimport { Button, Tag, Tooltip, useThemeContext, useTranslation } from '@dxos/react-ui';\nimport { createBasicExtensions, createThemeExtensions, listener } from '@dxos/react-ui-editor';\nimport {\n getSize,\n hoverableControlItem,\n hoverableControls,\n hoverableFocusedWithinControls,\n mx,\n} from '@dxos/react-ui-theme';\nimport { MessageTextbox, type MessageTextboxProps, Thread, ThreadFooter, ThreadHeading } from '@dxos/react-ui-thread';\nimport { nonNullable } from '@dxos/util';\n\nimport { MessageContainer } from './MessageContainer';\nimport { command } from './command-extension';\nimport { type ThreadContainerProps } from './types';\nimport { useStatus } from '../hooks';\nimport { THREAD_PLUGIN } from '../meta';\nimport { getMessageMetadata } from '../util';\n\nconst sizeClass = getSize(4);\n\nconst ToggleResolvedButton = ({\n isResolved,\n onResolve,\n}: {\n isResolved: boolean | undefined;\n onResolve: () => void;\n}) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const label = t(isResolved ? 'mark as unresolved label' : 'mark as resolved label');\n return (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <Button\n variant='ghost'\n data-testid='thread.toggle-resolved'\n onClick={onResolve}\n classNames={['min-bs-0 p-1', !isResolved && hoverableControlItem]}\n >\n <span className='sr-only'>{label}</span>\n {isResolved ? <CheckCircle className={sizeClass} weight='fill' /> : <CheckCircle className={sizeClass} />}\n </Button>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames={'z-[21]'}>\n {label}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n );\n};\n\nconst DeleteThreadButton = ({ onDelete }: { onDelete: () => void }) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const label = t('delete thread label');\n return (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <Button\n variant='ghost'\n data-testid='thread.delete'\n onClick={onDelete}\n classNames={['min-bs-0 p-1', hoverableControlItem]}\n >\n <span className='sr-only'>{label}</span>\n <X className={sizeClass} />\n </Button>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames='z-[21]'>\n {label}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n );\n};\n\nexport const CommentContainer = ({\n thread,\n detached,\n context,\n current,\n onAttend,\n onThreadDelete,\n onMessageDelete,\n onResolve,\n onComment,\n}: ThreadContainerProps) => {\n const identity = useIdentity()!;\n const space = getSpace(thread);\n const members = useMembers(space?.key);\n const activity = useStatus(space, fullyQualifiedId(thread));\n const { t } = useTranslation(THREAD_PLUGIN);\n const threadScrollRef = useRef<HTMLDivElement | null>(null);\n const { themeMode } = useThemeContext();\n\n const textboxMetadata = getMessageMetadata(fullyQualifiedId(thread), identity);\n // TODO(wittjosiah): This is a hack to reset the editor after a message is sent.\n const [_count, _setCount] = useState(0);\n const rerenderEditor = () => _setCount((count) => count + 1);\n const messageRef = useRef('');\n const extensions = useMemo(\n () => [\n createBasicExtensions({ placeholder: t('message placeholder') }),\n createThemeExtensions({ themeMode }),\n listener({ onChange: (text) => (messageRef.current = text) }),\n command,\n ],\n [_count],\n );\n\n // TODO(thure): Factor out.\n const scrollToEnd = (behavior: ScrollBehavior) =>\n setTimeout(() => threadScrollRef.current?.scrollIntoView({ behavior, block: 'end' }), 10);\n\n const handleCreate: MessageTextboxProps['onSend'] = useCallback(() => {\n if (!messageRef.current) {\n return false;\n }\n\n thread.messages.push(\n create(MessageType, {\n sender: { identityKey: identity.identityKey.toHex() },\n timestamp: new Date().toISOString(),\n text: messageRef.current,\n context,\n }),\n );\n onComment?.(thread);\n\n messageRef.current = '';\n scrollToEnd('instant');\n rerenderEditor();\n\n // TODO(burdon): Scroll to bottom.\n return true;\n }, [thread, identity]);\n\n return (\n <Thread onClickCapture={onAttend} onFocusCapture={onAttend} current={current} id={fullyQualifiedId(thread)}>\n <div\n role='none'\n className={mx(\n 'col-span-2 grid grid-cols-[var(--rail-size)_1fr_min-content]',\n hoverableControls,\n hoverableFocusedWithinControls,\n )}\n >\n {detached ? (\n <Tooltip.Root>\n <Tooltip.Trigger asChild>\n <ThreadHeading detached>{thread.name ?? t('thread title placeholder')}</ThreadHeading>\n </Tooltip.Trigger>\n <Tooltip.Portal>\n <Tooltip.Content classNames='z-[21]' side='top'>\n {t('detached thread label')}\n <Tooltip.Arrow />\n </Tooltip.Content>\n </Tooltip.Portal>\n </Tooltip.Root>\n ) : (\n <ThreadHeading>{thread.name ?? t('thread title placeholder')}</ThreadHeading>\n )}\n <div className='flex flex-row items-center pli-1'>\n {thread.status === 'staged' && <Tag palette='neutral'>{t('draft button')}</Tag>}\n {onResolve && !(thread?.status === 'staged') && (\n <ToggleResolvedButton isResolved={thread?.status === 'resolved'} onResolve={onResolve} />\n )}\n {onThreadDelete && <DeleteThreadButton onDelete={onThreadDelete} />}\n </div>\n </div>\n {thread.messages.filter(nonNullable).map((message) => (\n <MessageContainer\n key={message.id}\n message={message}\n members={members}\n onDelete={(id: string) => onMessageDelete?.(id)}\n />\n ))}\n {/*\n TODO(wittjosiah): Can't autofocus this generally.\n There can be multiple threads with inputs and they can't all be focused.\n Also, it steals focus from documents when first rendered.\n Need to find a way to autofocus in one scenario only: when a new thread is created.\n */}\n <MessageTextbox extensions={extensions} onSend={handleCreate} {...textboxMetadata} />\n <ThreadFooter activity={activity}>{t('activity message')}</ThreadFooter>\n {/* NOTE(thure): This can’t also be the `overflow-anchor` because `ScrollArea` injects an interceding node that contains this necessary ref’d element. */}\n <div role='none' className='bs-px -mbs-px' ref={threadScrollRef} />\n </Thread>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport { ChatText } from '@phosphor-icons/react';\nimport React, { useEffect } from 'react';\n\nimport { type ThreadType } from '@dxos/plugin-space/types';\nimport { fullyQualifiedId } from '@dxos/react-client/echo';\nimport { useTranslation, Trans } from '@dxos/react-ui';\nimport { descriptionText, mx } from '@dxos/react-ui-theme';\n\nimport { CommentContainer } from './CommentContainer';\nimport { type ThreadContainerProps } from './types';\nimport { THREAD_PLUGIN } from '../meta';\n\nexport type ThreadsContainerProps = Omit<\n ThreadContainerProps,\n 'thread' | 'detached' | 'onAttend' | 'onThreadDelete' | 'onMessageDelete' | 'current' | 'autoFocus'\n> & {\n threads: ThreadType[];\n /**\n * Threads that are no longer anchored to a position in the object.\n */\n detached?: string[];\n currentId?: string;\n showResolvedThreads?: boolean;\n onThreadAttend?: (thread: ThreadType) => void;\n onThreadDelete?: (thread: ThreadType) => void;\n onMessageDelete?: (thread: ThreadType, messageId: string) => void;\n onThreadToggleResolved?: (thread: ThreadType) => void;\n onComment?: (thread: ThreadType) => void;\n};\n\n/**\n * Comment threads.\n */\nexport const CommentsContainer = ({\n threads,\n detached = [],\n currentId,\n showResolvedThreads,\n onThreadAttend,\n onThreadDelete,\n onMessageDelete,\n onThreadToggleResolved,\n ...props\n}: ThreadsContainerProps) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n const filteredThreads = showResolvedThreads ? threads : threads.filter((thread) => !(thread?.status === 'resolved'));\n\n useEffect(() => {\n if (currentId) {\n document.getElementById(currentId)?.scrollIntoView({ behavior: 'smooth', block: 'end' });\n }\n }, [currentId]);\n\n return (\n <>\n {filteredThreads.length > 0 ? (\n filteredThreads.map((thread) => {\n const threadId = fullyQualifiedId(thread);\n return (\n <CommentContainer\n key={threadId}\n thread={thread}\n current={currentId === threadId}\n detached={detached.includes(threadId)}\n {...(onThreadAttend && { onAttend: () => onThreadAttend(thread) })}\n {...(onThreadDelete && { onThreadDelete: () => onThreadDelete(thread) })}\n {...(onMessageDelete && { onMessageDelete: (messageId: string) => onMessageDelete(thread, messageId) })}\n {...(onThreadToggleResolved && { onResolve: () => onThreadToggleResolved(thread) })}\n {...props}\n />\n );\n })\n ) : (\n <div\n role='alert'\n className={mx(\n descriptionText,\n 'place-self-center border border-dashed border-neutral-400/50 rounded-lg text-center p-4 m-4',\n )}\n >\n <h2 className='mbe-2 font-medium text-baseText'>{t('no comments title')}</h2>\n <p>\n <Trans\n {...{\n t,\n i18nKey: 'no comments message',\n components: {\n commentIcon: <ChatText className='inline-block' />,\n },\n }}\n />\n </p>\n </div>\n )}\n </>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport React, { useEffect, useMemo } from 'react';\n\nimport { LayoutAction, type Plugin, useIntentDispatcher, useResolvePlugins } from '@dxos/app-framework';\nimport { type ThreadType } from '@dxos/plugin-space';\nimport { fullyQualifiedId } from '@dxos/react-client/echo';\nimport { ScrollArea } from '@dxos/react-ui';\nimport { useAttended } from '@dxos/react-ui-attention';\nimport { nonNullable } from '@dxos/util';\n\nimport { CommentsContainer } from '../components';\nimport { THREAD_PLUGIN } from '../meta';\nimport { ThreadAction, type ThreadProvides } from '../types';\n\nconst providesThreadsConfig = (plugin: any): Plugin<ThreadProvides<any>> | undefined =>\n 'thread' in plugin.provides ? (plugin as Plugin<ThreadProvides<any>>) : undefined;\n\nexport const ThreadComplementary = ({\n role,\n subject,\n drafts,\n current,\n showResolvedThreads,\n}: {\n role: string;\n subject: any;\n drafts: ThreadType[] | undefined;\n current?: string;\n showResolvedThreads?: boolean;\n}) => {\n const dispatch = useIntentDispatcher();\n\n const threadsIntegrators = useResolvePlugins(providesThreadsConfig);\n const threadProvides = useMemo(() => threadsIntegrators.map((p) => p.provides.thread), [threadsIntegrators]);\n const createSort = useMemo(\n () => threadProvides.find((p) => p.predicate(subject))?.createSort,\n [threadProvides, subject],\n );\n const sort = useMemo(() => createSort?.(subject), [createSort, subject]);\n\n const threads = useMemo(() => {\n return subject.threads.concat(drafts ?? []).filter(nonNullable) as ThreadType[];\n }, [JSON.stringify(subject.threads), JSON.stringify(drafts)]);\n\n const detachedIds = useMemo(() => {\n return threads.filter(({ anchor }) => !anchor).map((thread) => fullyQualifiedId(thread));\n }, [threads]);\n\n useEffect(() => {\n if (!sort) {\n return;\n }\n threads.sort((a, b) => sort(a?.anchor, b?.anchor));\n }, [sort, threads]);\n\n const attended = useAttended();\n const qualifiedSubjectId = fullyQualifiedId(subject);\n\n return (\n <div role='none' className='contents'>\n <ScrollArea.Root classNames='row-span-2'>\n <ScrollArea.Viewport>\n <CommentsContainer\n threads={threads}\n detached={detachedIds}\n currentId={attended.includes(qualifiedSubjectId) ? current : undefined}\n showResolvedThreads={showResolvedThreads}\n onThreadAttend={(thread) => {\n const threadId = fullyQualifiedId(thread);\n if (current !== threadId) {\n current = threadId;\n\n void dispatch?.([\n {\n action: LayoutAction.SCROLL_INTO_VIEW,\n data: {\n id: fullyQualifiedId(subject),\n thread: threadId,\n cursor: thread.anchor,\n },\n },\n ]);\n }\n }}\n onThreadDelete={(thread) => {\n return dispatch({ plugin: THREAD_PLUGIN, action: ThreadAction.DELETE, data: { subject, thread } });\n }}\n onMessageDelete={(thread, messageId) =>\n dispatch({\n plugin: THREAD_PLUGIN,\n action: ThreadAction.DELETE_MESSAGE,\n data: { subject, thread, messageId },\n })\n }\n onThreadToggleResolved={(thread) =>\n dispatch({ plugin: THREAD_PLUGIN, action: ThreadAction.TOGGLE_RESOLVED, data: { thread } })\n }\n onComment={(thread) => {\n void dispatch({ action: ThreadAction.ON_MESSAGE_ADD, data: { thread, subject } });\n }}\n />\n <div role='none' className='bs-10' />\n <ScrollArea.Scrollbar>\n <ScrollArea.Thumb />\n </ScrollArea.Scrollbar>\n </ScrollArea.Viewport>\n </ScrollArea.Root>\n </div>\n );\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport React from 'react';\n\nimport { Input, useTranslation } from '@dxos/react-ui';\nimport { FormInput } from '@dxos/react-ui-data';\n\nimport { THREAD_PLUGIN } from '../meta';\nimport type { ThreadSettingsProps } from '../types';\n\nexport const ThreadSettings = ({ settings }: { settings: ThreadSettingsProps }) => {\n const { t } = useTranslation(THREAD_PLUGIN);\n\n return (\n <>\n <FormInput label={t('settings standalone label')}>\n <Input.Switch checked={settings.standalone} onCheckedChange={(checked) => (settings.standalone = !!checked)} />\n </FormInput>\n </>\n );\n};\n", "//\n// Copyright 2024 DXOS.org\n//\n\nimport { type Extension } from '@codemirror/state';\nimport { EditorView } from '@codemirror/view';\nimport { computed, effect } from '@preact/signals-core';\n\nimport { type IntentDispatcher } from '@dxos/app-framework';\nimport { type DocumentType } from '@dxos/plugin-markdown/types';\nimport { ThreadType } from '@dxos/plugin-space/types';\nimport { getSpace, getTextInRange, createDocAccessor, fullyQualifiedId } from '@dxos/react-client/echo';\nimport { comments, createExternalCommentSync } from '@dxos/react-ui-editor';\nimport { nonNullable } from '@dxos/util';\n\nimport { ThreadAction, type ThreadState } from '../types';\n\n// TODO(burdon): Factor out.\nconst getName = (doc: DocumentType, anchor: string): string | undefined => {\n if (doc.content) {\n const [start, end] = anchor.split(':');\n return getTextInRange(createDocAccessor(doc.content, ['content']), start, end);\n }\n};\n\n/**\n * Construct plugins.\n */\nexport const threads = (state: ThreadState, doc?: DocumentType, dispatch?: IntentDispatcher): Extension => {\n const space = doc && getSpace(doc);\n if (!doc || !space || !dispatch) {\n // Include no-op comments extension here to ensure that the facets are always present when they are expected.\n // TODO(wittjosiah): The Editor should only look for these facets when comments are available.\n return [comments()];\n }\n\n // TODO(Zan): When we have the deepsignal specific equivalent of this we should use that instead.\n const threads = computed(() =>\n [...doc.threads.filter(nonNullable), ...(state.drafts[fullyQualifiedId(doc)] ?? [])].filter(\n (thread) => !(thread?.status === 'resolved'),\n ),\n );\n\n return [\n EditorView.updateListener.of((update) => {\n if (update.docChanged) {\n doc.threads.forEach((thread) => {\n if (thread?.anchor) {\n // Only update if the name has changed, otherwise this will cause an infinite loop.\n // Skip if the name is empty; this means comment text was deleted, but thread name should remain.\n const name = getName(doc, thread.anchor);\n if (name && name !== thread.name) {\n thread.name = name;\n }\n }\n });\n }\n }),\n\n createExternalCommentSync(\n fullyQualifiedId(doc),\n (sink) => effect(() => sink()),\n () =>\n threads.value\n .filter((thread) => thread?.anchor)\n .map((thread) => ({ id: fullyQualifiedId(thread), cursor: thread.anchor! })),\n ),\n\n comments({\n id: fullyQualifiedId(doc),\n onCreate: ({ cursor }) => {\n const name = getName(doc, cursor);\n void dispatch({\n action: ThreadAction.CREATE,\n data: {\n cursor,\n name,\n subject: doc,\n },\n });\n },\n onDelete: ({ id }) => {\n const draft = state.drafts[fullyQualifiedId(doc)];\n if (draft) {\n const index = draft.findIndex((thread) => fullyQualifiedId(thread) === id);\n if (index !== -1) {\n draft.splice(index, 1);\n }\n }\n\n const thread = doc.threads.find((thread) => thread?.id === id);\n if (thread) {\n thread.anchor = undefined;\n }\n },\n onUpdate: ({ id, cursor }) => {\n const thread =\n state.drafts[fullyQualifiedId(doc)]?.find((thread) => fullyQualifiedId(thread) === id) ??\n doc.threads.find((thread) => thread?.id === id);\n\n if (thread instanceof ThreadType && thread.anchor) {\n thread.name = getName(doc, thread.anchor);\n thread.anchor = cursor;\n }\n },\n onSelect: ({ selection: { current, closest } }) => {\n void dispatch({\n action: ThreadAction.SELECT,\n data: {\n current: current ?? closest,\n skipOpen: true,\n },\n });\n },\n }),\n ];\n};\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { THREAD_PLUGIN } from './meta';\n\nexport default [\n {\n 'en-US': {\n [THREAD_PLUGIN]: {\n 'plugin name': 'Threads',\n 'channel name placeholder': 'New channel',\n 'channel title label': 'Title',\n 'delete channel label': 'Delete channel',\n 'create channel label': 'Create channel',\n 'message placeholder': 'Reply…',\n 'settings standalone label': 'Enable channel creation (experimental)',\n 'activity message': 'Processing…',\n 'anonymous label': 'Anonymous',\n 'delete message block label': 'Delete message block',\n 'detached thread label': 'Referenced content was removed',\n 'delete thread label': 'Delete thread',\n 'thread deleted label': 'You deleted a thread.',\n 'message deleted label': 'You deleted a message.',\n 'comments heading': 'Comments',\n 'chat heading': 'Chat',\n 'draft button': 'DRAFT',\n 'no comments title': 'No comments (yet)',\n 'no comments message':\n 'To start a comment thread, select a range of text in a document and click the <commentIcon></commentIcon> Create comment button in the toolbar.',\n 'toggle show resolved': 'Show resolved',\n 'unnamed object threads label': 'Threads',\n 'mark as resolved label': 'Mark as resolved',\n 'mark as unresolved label': 'Mark as unresolved',\n 'save message label': 'Save',\n 'edit message label': 'Edit',\n 'delete message label': 'Delete message',\n },\n },\n },\n];\n", "//\n// Copyright 2023 DXOS.org\n//\n\nimport { ThreadPlugin } from './ThreadPlugin';\n\nexport default ThreadPlugin;\n\nexport * from './hooks';\nexport * from './types';\n\nexport * from './ThreadPlugin';\n"],
5
+ "mappings": "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",
6
+ "names": ["React", "NavigationAction", "isLayoutParts", "parseIntentPlugin", "parseNavigationPlugin", "parseMetadataResolverPlugin", "resolvePlugin", "LayoutAction", "LocalStorageStore", "log", "parseClientPlugin", "createExtension", "isActionGroup", "toSignal", "ObservabilityAction", "SpaceAction", "ThreadType", "MessageType", "ChannelType", "create", "getTypename", "getSpace", "fullyQualifiedId", "loadObjectReferences", "parseId", "translations", "threadTranslations", "lazy", "CheckCircle", "X", "React", "useCallback", "useMemo", "useRef", "useState", "create", "MessageType", "fullyQualifiedId", "getSpace", "useMembers", "useIdentity", "Button", "Tag", "Tooltip", "useThemeContext", "useTranslation", "createBasicExtensions", "createThemeExtensions", "listener", "getSize", "hoverableControlItem", "hoverableControls", "hoverableFocusedWithinControls", "mx", "MessageTextbox", "Thread", "ThreadFooter", "ThreadHeading", "nonNullable", "sizeClass", "getSize", "ToggleResolvedButton", "isResolved", "onResolve", "t", "useTranslation", "THREAD_PLUGIN", "label", "Tooltip", "Root", "Trigger", "asChild", "Button", "variant", "data-testid", "onClick", "classNames", "hoverableControlItem", "span", "className", "CheckCircle", "weight", "Portal", "Content", "Arrow", "DeleteThreadButton", "onDelete", "X", "CommentContainer", "thread", "detached", "context", "current", "onAttend", "onThreadDelete", "onMessageDelete", "onComment", "identity", "useIdentity", "space", "getSpace", "members", "useMembers", "key", "activity", "useStatus", "fullyQualifiedId", "threadScrollRef", "useRef", "themeMode", "useThemeContext", "textboxMetadata", "getMessageMetadata", "_count", "_setCount", "useState", "rerenderEditor", "count", "messageRef", "extensions", "useMemo", "createBasicExtensions", "placeholder", "createThemeExtensions", "listener", "onChange", "text", "command", "scrollToEnd", "behavior", "setTimeout", "scrollIntoView", "block", "handleCreate", "useCallback", "messages", "push", "create", "MessageType", "sender", "identityKey", "toHex", "timestamp", "Date", "toISOString", "Thread", "onClickCapture", "onFocusCapture", "id", "div", "role", "mx", "hoverableControls", "hoverableFocusedWithinControls", "ThreadHeading", "name", "side", "status", "Tag", "palette", "filter", "nonNullable", "map", "message", "MessageContainer", "MessageTextbox", "onSend", "ThreadFooter", "ref", "ChatText", "React", "useEffect", "fullyQualifiedId", "useTranslation", "Trans", "descriptionText", "mx", "CommentsContainer", "threads", "detached", "currentId", "showResolvedThreads", "onThreadAttend", "onThreadDelete", "onMessageDelete", "onThreadToggleResolved", "props", "t", "useTranslation", "THREAD_PLUGIN", "filteredThreads", "filter", "thread", "status", "useEffect", "document", "getElementById", "scrollIntoView", "behavior", "block", "React", "length", "map", "threadId", "fullyQualifiedId", "CommentContainer", "key", "current", "includes", "onAttend", "messageId", "onResolve", "div", "role", "className", "mx", "descriptionText", "h2", "p", "Trans", "i18nKey", "components", "commentIcon", "ChatText", "React", "useEffect", "useMemo", "LayoutAction", "useIntentDispatcher", "useResolvePlugins", "fullyQualifiedId", "ScrollArea", "useAttended", "nonNullable", "providesThreadsConfig", "plugin", "provides", "undefined", "ThreadComplementary", "role", "subject", "drafts", "current", "showResolvedThreads", "dispatch", "useIntentDispatcher", "threadsIntegrators", "useResolvePlugins", "threadProvides", "useMemo", "map", "p", "thread", "createSort", "find", "predicate", "sort", "threads", "concat", "filter", "nonNullable", "JSON", "stringify", "detachedIds", "anchor", "fullyQualifiedId", "useEffect", "a", "b", "attended", "useAttended", "qualifiedSubjectId", "React", "div", "className", "ScrollArea", "Root", "classNames", "Viewport", "CommentsContainer", "detached", "currentId", "includes", "onThreadAttend", "threadId", "action", "LayoutAction", "SCROLL_INTO_VIEW", "data", "id", "cursor", "onThreadDelete", "THREAD_PLUGIN", "ThreadAction", "DELETE", "onMessageDelete", "messageId", "DELETE_MESSAGE", "onThreadToggleResolved", "TOGGLE_RESOLVED", "onComment", "ON_MESSAGE_ADD", "Scrollbar", "Thumb", "React", "Input", "useTranslation", "FormInput", "ThreadSettings", "settings", "t", "useTranslation", "THREAD_PLUGIN", "React", "FormInput", "label", "Input", "Switch", "checked", "standalone", "onCheckedChange", "ThreadMain", "lazy", "ThreadArticle", "EditorView", "computed", "effect", "ThreadType", "getSpace", "getTextInRange", "createDocAccessor", "fullyQualifiedId", "comments", "createExternalCommentSync", "nonNullable", "getName", "doc", "anchor", "content", "start", "end", "split", "getTextInRange", "createDocAccessor", "threads", "state", "dispatch", "space", "getSpace", "comments", "computed", "filter", "nonNullable", "drafts", "fullyQualifiedId", "thread", "status", "EditorView", "updateListener", "of", "update", "docChanged", "forEach", "name", "createExternalCommentSync", "sink", "effect", "value", "map", "id", "cursor", "onCreate", "action", "ThreadAction", "CREATE", "data", "subject", "onDelete", "draft", "index", "findIndex", "splice", "find", "undefined", "onUpdate", "ThreadType", "onSelect", "selection", "current", "closest", "SELECT", "skipOpen", "THREAD_PLUGIN", "initialViewState", "showResolvedThreads", "ThreadPlugin", "settings", "LocalStorageStore", "THREAD_PLUGIN", "state", "create", "drafts", "viewStore", "getViewState", "subjectId", "navigationPlugin", "intentPlugin", "unsubscribeCallbacks", "meta", "ready", "plugins", "prop", "key", "type", "bool", "allowUndefined", "resolvePlugin", "parseNavigationPlugin", "parseIntentPlugin", "unload", "forEach", "unsubscribe", "provides", "values", "metadata", "records", "ChannelType", "typename", "placeholder", "ns", "icon", "loadReferences", "channel", "loadObjectReferences", "threads", "ThreadType", "thread", "messages", "MessageType", "message", "THREAD_ITEM", "parse", "item", "id", "label", "title", "data", "object", "translations", "threadTranslations", "echo", "schema", "graph", "builder", "client", "parseClientPlugin", "dispatch", "intent", "metadataResolver", "parseMetadataResolverPlugin", "resolver", "createExtension", "endsWith", "split", "spaceId", "objectId", "parseId", "space", "spaces", "get", "find", "properties", "toSignal", "onChange", "timeout", "setTimeout", "db", "loadObjectById", "clearTimeout", "getObjectById", "getTypename", "name", "viewState", "actions", "node", "dataId", "at", "toggle", "newToggleState", "action", "ObservabilityAction", "SEND_EVENT", "threadId", "showResolved", "menuItemType", "isChecked", "testId", "ThreadAction", "CREATE", "filter", "standalone", "isActionGroup", "startsWith", "SpaceAction", "ADD_OBJECT", "target", "plugin", "NavigationAction", "OPEN", "surface", "component", "role", "active", "React", "ThreadMain", "ThreadSettings", "location", "isLayoutParts", "main", "layoutEntries", "currentPosition", "findIndex", "entry", "objectToTheLeft", "context", "getSpace", "ThreadArticle", "subject", "ChatHeading", "attendableId", "ChatContainer", "Array", "isArray", "fullyQualifiedId", "ThreadComplementary", "current", "cursor", "undefined", "err", "log", "error", "anchor", "status", "draft", "push", "intents", "SELECT", "activeParts", "complementary", "LayoutAction", "SET_LAYOUT", "element", "skipOpen", "TOGGLE_RESOLVED", "DELETE", "index", "t", "splice", "undo", "remove", "undoable", "savedThread", "add", "ON_MESSAGE_ADD", "analyticsProperties", "threadLength", "length", "DELETE_MESSAGE", "messageId", "m", "messageIndex", "markdown", "extensions", "document", "doc", "ThreadPlugin"]
7
7
  }