@dxos/plugin-navtree 0.8.4-main.1da679c → 0.8.4-main.21d9917

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 (178) hide show
  1. package/dist/lib/browser/app-graph-builder-RSMA6I22.mjs +43 -0
  2. package/dist/lib/browser/app-graph-builder-RSMA6I22.mjs.map +7 -0
  3. package/dist/lib/browser/chunk-6YPQ625I.mjs +1293 -0
  4. package/dist/lib/browser/chunk-6YPQ625I.mjs.map +7 -0
  5. package/dist/lib/browser/chunk-AGQDZBPL.mjs +23 -0
  6. package/dist/lib/browser/chunk-AGQDZBPL.mjs.map +7 -0
  7. package/dist/lib/browser/chunk-YKTYPINZ.mjs +19 -0
  8. package/dist/lib/browser/chunk-YKTYPINZ.mjs.map +7 -0
  9. package/dist/lib/browser/index.mjs +82 -93
  10. package/dist/lib/browser/index.mjs.map +4 -4
  11. package/dist/lib/browser/{keyboard-R2APW7UM.mjs → keyboard-32EH3N4K.mjs} +20 -19
  12. package/dist/lib/browser/keyboard-32EH3N4K.mjs.map +7 -0
  13. package/dist/lib/browser/meta.json +1 -1
  14. package/dist/lib/browser/operation-resolver-IB75DC5O.mjs +52 -0
  15. package/dist/lib/browser/operation-resolver-IB75DC5O.mjs.map +7 -0
  16. package/dist/lib/browser/react-surface-F6CVMS3Y.mjs +58 -0
  17. package/dist/lib/browser/react-surface-F6CVMS3Y.mjs.map +7 -0
  18. package/dist/lib/browser/state-EVYQOUI3.mjs +120 -0
  19. package/dist/lib/browser/state-EVYQOUI3.mjs.map +7 -0
  20. package/dist/types/src/NavTreePlugin.d.ts +2 -1
  21. package/dist/types/src/NavTreePlugin.d.ts.map +1 -1
  22. package/dist/types/src/capabilities/app-graph-builder/app-graph-builder.d.ts +6 -0
  23. package/dist/types/src/capabilities/app-graph-builder/app-graph-builder.d.ts.map +1 -0
  24. package/dist/types/src/capabilities/app-graph-builder/index.d.ts +3 -0
  25. package/dist/types/src/capabilities/app-graph-builder/index.d.ts.map +1 -0
  26. package/dist/types/src/capabilities/index.d.ts +5 -105
  27. package/dist/types/src/capabilities/index.d.ts.map +1 -1
  28. package/dist/types/src/capabilities/keyboard/index.d.ts +3 -0
  29. package/dist/types/src/capabilities/keyboard/index.d.ts.map +1 -0
  30. package/dist/types/src/capabilities/keyboard/keyboard.d.ts +5 -0
  31. package/dist/types/src/capabilities/keyboard/keyboard.d.ts.map +1 -0
  32. package/dist/types/src/capabilities/operation-resolver/index.d.ts +3 -0
  33. package/dist/types/src/capabilities/operation-resolver/index.d.ts.map +1 -0
  34. package/dist/types/src/capabilities/operation-resolver/operation-resolver.d.ts +5 -0
  35. package/dist/types/src/capabilities/operation-resolver/operation-resolver.d.ts.map +1 -0
  36. package/dist/types/src/capabilities/react-surface/index.d.ts +3 -0
  37. package/dist/types/src/capabilities/react-surface/index.d.ts.map +1 -0
  38. package/dist/types/src/capabilities/react-surface/react-surface.d.ts +5 -0
  39. package/dist/types/src/capabilities/react-surface/react-surface.d.ts.map +1 -0
  40. package/dist/types/src/capabilities/state/index.d.ts +3 -0
  41. package/dist/types/src/capabilities/state/index.d.ts.map +1 -0
  42. package/dist/types/src/capabilities/state/state.d.ts +6 -0
  43. package/dist/types/src/capabilities/state/state.d.ts.map +1 -0
  44. package/dist/types/src/components/CommandsDialog/CommandsDialog.d.ts +3 -2
  45. package/dist/types/src/components/CommandsDialog/CommandsDialog.d.ts.map +1 -1
  46. package/dist/types/src/components/CommandsDialog/CommandsTrigger.d.ts.map +1 -1
  47. package/dist/types/src/components/NavTree/NavTree.d.ts +30 -1
  48. package/dist/types/src/components/NavTree/NavTree.d.ts.map +1 -1
  49. package/dist/types/src/components/NavTree/NavTree.stories.d.ts +5 -3
  50. package/dist/types/src/components/NavTree/NavTree.stories.d.ts.map +1 -1
  51. package/dist/types/src/components/NavTreeContainer.d.ts +8 -1
  52. package/dist/types/src/components/NavTreeContainer.d.ts.map +1 -1
  53. package/dist/types/src/components/NavTreeDocumentTitle.d.ts +1 -1
  54. package/dist/types/src/components/NavTreeDocumentTitle.d.ts.map +1 -1
  55. package/dist/types/src/components/NavTreeItem/NavTreeItemAction.d.ts +6 -6
  56. package/dist/types/src/components/NavTreeItem/NavTreeItemAction.d.ts.map +1 -1
  57. package/dist/types/src/components/NavTreeItem/NavTreeItemAction.stories.d.ts +3 -3
  58. package/dist/types/src/components/NavTreeItem/NavTreeItemAction.stories.d.ts.map +1 -1
  59. package/dist/types/src/components/NavTreeItem/NavTreeItemColumns.d.ts +1 -1
  60. package/dist/types/src/components/NavTreeItem/NavTreeItemColumns.d.ts.map +1 -1
  61. package/dist/types/src/components/Sidebar/L0Menu.d.ts +6 -4
  62. package/dist/types/src/components/Sidebar/L0Menu.d.ts.map +1 -1
  63. package/dist/types/src/components/Sidebar/L1Panel.d.ts +1 -1
  64. package/dist/types/src/components/Sidebar/L1Panel.d.ts.map +1 -1
  65. package/dist/types/src/components/Sidebar/L1Tabs.d.ts +2 -2
  66. package/dist/types/src/components/Sidebar/L1Tabs.d.ts.map +1 -1
  67. package/dist/types/src/components/UserAccountAvatar/UserAccountAvatar.d.ts.map +1 -1
  68. package/dist/types/src/components/UserAccountAvatar/UserAccountAvatar.stories.d.ts +1 -2
  69. package/dist/types/src/components/UserAccountAvatar/UserAccountAvatar.stories.d.ts.map +1 -1
  70. package/dist/types/src/components/index.d.ts.map +1 -1
  71. package/dist/types/src/components/types.d.ts +7 -7
  72. package/dist/types/src/components/types.d.ts.map +1 -1
  73. package/dist/types/src/experimental/Tree.d.ts +1 -2
  74. package/dist/types/src/experimental/Tree.d.ts.map +1 -1
  75. package/dist/types/src/experimental/Tree.stories.d.ts +2 -3
  76. package/dist/types/src/experimental/Tree.stories.d.ts.map +1 -1
  77. package/dist/types/src/hooks.d.ts +32 -1
  78. package/dist/types/src/hooks.d.ts.map +1 -1
  79. package/dist/types/src/index.d.ts +1 -2
  80. package/dist/types/src/index.d.ts.map +1 -1
  81. package/dist/types/src/meta.d.ts +3 -4
  82. package/dist/types/src/meta.d.ts.map +1 -1
  83. package/dist/types/src/testing/app-graph-builder.d.ts +2 -3
  84. package/dist/types/src/testing/app-graph-builder.d.ts.map +1 -1
  85. package/dist/types/src/testing/generator.d.ts +5 -6
  86. package/dist/types/src/testing/generator.d.ts.map +1 -1
  87. package/dist/types/src/testing/update-state.d.ts +2 -2
  88. package/dist/types/src/testing/update-state.d.ts.map +1 -1
  89. package/dist/types/src/types/capabilities.d.ts +16 -0
  90. package/dist/types/src/types/capabilities.d.ts.map +1 -0
  91. package/dist/types/src/types/events.d.ts +5 -0
  92. package/dist/types/src/types/events.d.ts.map +1 -0
  93. package/dist/types/src/types/index.d.ts +4 -0
  94. package/dist/types/src/types/index.d.ts.map +1 -0
  95. package/dist/types/src/{types.d.ts → types/schema.d.ts} +10 -9
  96. package/dist/types/src/types/schema.d.ts.map +1 -0
  97. package/dist/types/src/util.d.ts +7 -7
  98. package/dist/types/src/util.d.ts.map +1 -1
  99. package/dist/types/tsconfig.tsbuildinfo +1 -1
  100. package/package.json +54 -53
  101. package/src/NavTreePlugin.tsx +65 -83
  102. package/src/capabilities/app-graph-builder/app-graph-builder.ts +41 -0
  103. package/src/capabilities/app-graph-builder/index.ts +7 -0
  104. package/src/capabilities/index.ts +5 -9
  105. package/src/capabilities/keyboard/index.ts +7 -0
  106. package/src/capabilities/keyboard/keyboard.ts +65 -0
  107. package/src/capabilities/operation-resolver/index.ts +7 -0
  108. package/src/capabilities/operation-resolver/operation-resolver.ts +41 -0
  109. package/src/capabilities/react-surface/index.ts +7 -0
  110. package/src/capabilities/react-surface/react-surface.tsx +54 -0
  111. package/src/capabilities/state/index.ts +7 -0
  112. package/src/capabilities/state/state.ts +121 -0
  113. package/src/components/CommandsDialog/CommandsDialog.tsx +109 -98
  114. package/src/components/CommandsDialog/CommandsTrigger.tsx +6 -15
  115. package/src/components/NavTree/NavTree.stories.tsx +93 -88
  116. package/src/components/NavTree/NavTree.tsx +9 -15
  117. package/src/components/NavTreeContainer.tsx +254 -256
  118. package/src/components/NavTreeDocumentTitle.tsx +5 -4
  119. package/src/components/NavTreeItem/NavTreeItemAction.stories.tsx +18 -10
  120. package/src/components/NavTreeItem/NavTreeItemAction.tsx +23 -16
  121. package/src/components/NavTreeItem/NavTreeItemColumns.tsx +32 -26
  122. package/src/components/Sidebar/L0Menu.tsx +112 -137
  123. package/src/components/Sidebar/L1Panel.tsx +16 -17
  124. package/src/components/Sidebar/L1Tabs.tsx +6 -31
  125. package/src/components/UserAccountAvatar/UserAccountAvatar.stories.tsx +3 -4
  126. package/src/components/UserAccountAvatar/UserAccountAvatar.tsx +20 -12
  127. package/src/components/index.ts +1 -0
  128. package/src/components/types.ts +7 -7
  129. package/src/experimental/Tree.stories.tsx +26 -30
  130. package/src/experimental/Tree.tsx +7 -24
  131. package/src/hooks.ts +54 -2
  132. package/src/index.ts +1 -2
  133. package/src/meta.ts +11 -8
  134. package/src/testing/app-graph-builder.ts +159 -234
  135. package/src/testing/generator.ts +20 -18
  136. package/src/testing/update-state.ts +6 -6
  137. package/src/types/capabilities.ts +21 -0
  138. package/src/types/events.ts +11 -0
  139. package/src/types/index.ts +7 -0
  140. package/src/{types.ts → types/schema.ts} +9 -8
  141. package/src/util.ts +13 -16
  142. package/dist/lib/browser/app-graph-builder-DU57YHO5.mjs +0 -45
  143. package/dist/lib/browser/app-graph-builder-DU57YHO5.mjs.map +0 -7
  144. package/dist/lib/browser/chunk-EMIN6D7Q.mjs +0 -1469
  145. package/dist/lib/browser/chunk-EMIN6D7Q.mjs.map +0 -7
  146. package/dist/lib/browser/chunk-ERDGQTH5.mjs +0 -16
  147. package/dist/lib/browser/chunk-ERDGQTH5.mjs.map +0 -7
  148. package/dist/lib/browser/chunk-WCARAZ7J.mjs +0 -15
  149. package/dist/lib/browser/chunk-WCARAZ7J.mjs.map +0 -7
  150. package/dist/lib/browser/intent-resolver-RPZ5O7AJ.mjs +0 -47
  151. package/dist/lib/browser/intent-resolver-RPZ5O7AJ.mjs.map +0 -7
  152. package/dist/lib/browser/keyboard-R2APW7UM.mjs.map +0 -7
  153. package/dist/lib/browser/react-surface-DF7FNA34.mjs +0 -51
  154. package/dist/lib/browser/react-surface-DF7FNA34.mjs.map +0 -7
  155. package/dist/lib/browser/state-W5JDWIJL.mjs +0 -117
  156. package/dist/lib/browser/state-W5JDWIJL.mjs.map +0 -7
  157. package/dist/types/src/capabilities/app-graph-builder.d.ts +0 -4
  158. package/dist/types/src/capabilities/app-graph-builder.d.ts.map +0 -1
  159. package/dist/types/src/capabilities/capabilities.d.ts +0 -21
  160. package/dist/types/src/capabilities/capabilities.d.ts.map +0 -1
  161. package/dist/types/src/capabilities/intent-resolver.d.ts +0 -4
  162. package/dist/types/src/capabilities/intent-resolver.d.ts.map +0 -1
  163. package/dist/types/src/capabilities/keyboard.d.ts +0 -4
  164. package/dist/types/src/capabilities/keyboard.d.ts.map +0 -1
  165. package/dist/types/src/capabilities/react-surface.d.ts +0 -4
  166. package/dist/types/src/capabilities/react-surface.d.ts.map +0 -1
  167. package/dist/types/src/capabilities/state.d.ts +0 -20
  168. package/dist/types/src/capabilities/state.d.ts.map +0 -1
  169. package/dist/types/src/events.d.ts +0 -4
  170. package/dist/types/src/events.d.ts.map +0 -1
  171. package/dist/types/src/types.d.ts.map +0 -1
  172. package/src/capabilities/app-graph-builder.ts +0 -52
  173. package/src/capabilities/capabilities.ts +0 -20
  174. package/src/capabilities/intent-resolver.ts +0 -37
  175. package/src/capabilities/keyboard.ts +0 -59
  176. package/src/capabilities/react-surface.tsx +0 -45
  177. package/src/capabilities/state.ts +0 -105
  178. package/src/events.ts +0 -11
@@ -2,15 +2,15 @@
2
2
  // Copyright 2025 DXOS.org
3
3
  //
4
4
 
5
- import { Rx } from '@effect-rx/rx-react';
6
- import { Option, pipe } from 'effect';
5
+ import { Atom } from '@effect-atom/atom-react';
6
+ import * as Effect from 'effect/Effect';
7
7
 
8
- import { type PluginContext } from '@dxos/app-framework';
8
+ import { type BuilderExtensions } from '@dxos/app-graph';
9
9
  import { log } from '@dxos/log';
10
- import { type BuilderExtensions, ROOT_ID, createExtension } from '@dxos/plugin-graph';
10
+ import { GraphBuilder, NodeMatcher } from '@dxos/plugin-graph';
11
11
  import { faker } from '@dxos/random';
12
12
 
13
- export const storybookGraphBuilders = (context: PluginContext): BuilderExtensions => {
13
+ export const storybookGraphBuilders = (): BuilderExtensions => {
14
14
  const propertiesCache = new Map<string, Record<string, unknown>>();
15
15
  const getProperties = (id: string, defaults: Record<string, unknown>) => {
16
16
  const cached = propertiesCache.get(id);
@@ -22,249 +22,174 @@ export const storybookGraphBuilders = (context: PluginContext): BuilderExtension
22
22
  return defaults;
23
23
  };
24
24
 
25
- return [
26
- // Create app menu actions.
27
- createExtension({
28
- id: 'app-menu',
29
- actions: (node) =>
30
- Rx.make((get) =>
31
- pipe(
32
- get(node),
33
- Option.flatMap((node) => (node.id === ROOT_ID ? Option.some(node) : Option.none())),
34
- Option.map((node) => {
35
- return [
36
- ...Array.from({ length: 5 }, (_, i) => ({
37
- id: `${node.id}/action-${i}`,
38
- data: () => {
39
- log.info('action', { id: node.id, index: i });
40
- },
41
- properties: {
42
- label: `Action ${i}`,
43
- icon: faker.properties.icon(),
44
- disposition: 'menu',
45
- },
46
- })),
47
- ];
48
- }),
49
- Option.getOrElse(() => []),
25
+ return Effect.runSync(
26
+ Effect.all([
27
+ // Create app menu actions.
28
+ GraphBuilder.createExtension({
29
+ id: 'app-menu',
30
+ match: NodeMatcher.whenRoot,
31
+ actions: () =>
32
+ Effect.succeed(
33
+ Array.from({ length: 5 }, (_, i) => ({
34
+ id: `app-menu/action-${i}`,
35
+ data: Effect.fnUntraced(function* () {
36
+ log.info('action', { id: 'app-menu', index: i });
37
+ }),
38
+ properties: {
39
+ label: `Action ${i}`,
40
+ icon: faker.properties.icon(),
41
+ disposition: 'menu',
42
+ },
43
+ })),
50
44
  ),
51
- ),
52
- }),
53
- // Create user account node.
54
- createExtension({
55
- id: 'user-account',
56
- connector: (node) =>
57
- Rx.make((get) =>
58
- pipe(
59
- get(node),
60
- Option.flatMap((node) => (node.id === ROOT_ID ? Option.some(node) : Option.none())),
61
- Option.map(() => {
62
- return [
45
+ }),
46
+ // Create user account node.
47
+ GraphBuilder.createExtension({
48
+ id: 'user-account',
49
+ match: NodeMatcher.whenRoot,
50
+ connector: () =>
51
+ Effect.succeed([
52
+ {
53
+ id: 'user-account',
54
+ type: 'user-account',
55
+ properties: {
56
+ label: 'User profile',
57
+ icon: 'ph--user--regular',
58
+ disposition: 'user-account',
59
+ userId: '1234567890ABCDEF',
60
+ hue: faker.properties.hue(),
61
+ emoji: faker.properties.emoji(),
62
+ status: 'active',
63
+ },
64
+ nodes: [
63
65
  {
64
- id: 'user-account',
65
- type: 'user-account',
66
+ id: 'profile',
67
+ type: 'profile',
66
68
  properties: {
67
- label: 'User Account',
69
+ label: 'Profile',
68
70
  icon: 'ph--user--regular',
69
- disposition: 'user-account',
70
- userId: '1234567890ABCDEF',
71
- hue: faker.properties.hue(),
72
- emoji: faker.properties.emoji(),
73
- status: 'active',
74
71
  },
75
- nodes: [
76
- {
77
- id: 'profile',
78
- type: 'profile',
79
- properties: {
80
- label: 'Profile',
81
- icon: 'ph--user--regular',
82
- },
83
- },
84
- {
85
- id: 'devices',
86
- type: 'devices',
87
- properties: {
88
- label: 'Devices',
89
- icon: 'ph--devices--regular',
90
- },
91
- },
92
- {
93
- id: 'security',
94
- type: 'security',
95
- properties: {
96
- label: 'Security',
97
- icon: 'ph--key--regular',
98
- },
99
- },
100
- ],
101
72
  },
102
- ];
103
- }),
104
- Option.getOrElse(() => []),
105
- ),
106
- ),
107
- }),
108
- // TODO(wittjosiah): This group node probably is unnecessary now with the flat L0 structure.
109
- // Create spaces group node.
110
- createExtension({
111
- id: 'spaces-root',
112
- position: 'hoist',
113
- connector: (node) =>
114
- Rx.make((get) =>
115
- pipe(
116
- get(node),
117
- Option.flatMap((node) => (node.id === ROOT_ID ? Option.some(node) : Option.none())),
118
- Option.map(() => {
119
- return [
120
73
  {
121
- id: 'spaces-root',
122
- type: 'spaces-root',
74
+ id: 'devices',
75
+ type: 'devices',
123
76
  properties: {
124
- label: 'Spaces',
125
- icon: 'ph--planet--regular',
126
- role: 'branch',
127
- disposition: 'collection',
77
+ label: 'Devices',
78
+ icon: 'ph--devices--regular',
128
79
  },
129
80
  },
130
- ];
131
- }),
132
- Option.getOrElse(() => []),
133
- ),
134
- ),
135
- }),
136
- // Create space nodes.
137
- createExtension({
138
- id: 'spaces',
139
- connector: (node) => {
140
- const count = Rx.make((get) => {
141
- let value = 3;
142
- const interval = setInterval(() => {
143
- if (value >= 10) {
144
- clearInterval(interval);
145
- return;
146
- }
81
+ {
82
+ id: 'security',
83
+ type: 'security',
84
+ properties: {
85
+ label: 'Security',
86
+ icon: 'ph--key--regular',
87
+ },
88
+ },
89
+ ],
90
+ },
91
+ ]),
92
+ }),
93
+ // Create space (workspace) nodes directly under root.
94
+ GraphBuilder.createExtension({
95
+ id: 'spaces',
96
+ match: NodeMatcher.whenRoot,
97
+ connector: (_, get) =>
98
+ Effect.sync(() => {
99
+ const count = Atom.make((get) => {
100
+ let value = 3;
101
+ const interval = setInterval(() => {
102
+ if (value >= 10) {
103
+ clearInterval(interval);
104
+ return;
105
+ }
147
106
 
148
- value++;
149
- get.setSelf(value);
150
- }, 5000);
151
- get.addFinalizer(() => clearInterval(interval));
152
- return value;
153
- });
107
+ value++;
108
+ get.setSelf(value);
109
+ }, 5000);
110
+ get.addFinalizer(() => clearInterval(interval));
111
+ return value;
112
+ });
154
113
 
155
- return Rx.make((get) =>
156
- pipe(
157
- get(node),
158
- Option.flatMap((node) => (node.id === 'spaces-root' ? Option.some(node) : Option.none())),
159
- Option.map(() => {
160
- return [
161
- ...Array.from({ length: get(count) }, (_, i) => ({
162
- id: `space-${i}`,
163
- type: 'space',
164
- properties: getProperties(`space-${i}`, {
165
- label: `Space ${i}`,
166
- icon: faker.properties.icon(),
167
- hue: faker.properties.hue(),
168
- }),
169
- })),
170
- ];
171
- }),
172
- Option.getOrElse(() => []),
173
- ),
174
- );
175
- },
176
- }),
177
- // Create space actions.
178
- createExtension({
179
- id: 'space-actions',
180
- actions: (node) =>
181
- Rx.make((get) =>
182
- pipe(
183
- get(node),
184
- Option.flatMap((node) => (node.type === 'space' ? Option.some(node) : Option.none())),
185
- Option.map((node) => {
186
- return [
187
- ...Array.from({ length: 5 }, (_, i) => ({
188
- id: `${node.id}/action-${i}`,
189
- data: () => {
190
- log.info('action', { id: node.id, index: i });
191
- },
192
- properties: getProperties(`${node.id}/action-${i}`, {
193
- label: `Action ${i}`,
194
- icon: faker.properties.icon(),
195
- }),
196
- })),
197
- ];
198
- }),
199
- Option.getOrElse(() => []),
114
+ return Array.from({ length: get(count) }, (_, i) => ({
115
+ id: `space-${i}`,
116
+ type: 'space',
117
+ properties: getProperties(`space-${i}`, {
118
+ label: `Space ${i}`,
119
+ icon: faker.properties.icon(),
120
+ hue: faker.properties.hue(),
121
+ disposition: 'workspace',
122
+ }),
123
+ }));
124
+ }),
125
+ }),
126
+ // Create space actions.
127
+ GraphBuilder.createExtension({
128
+ id: 'space-actions',
129
+ match: NodeMatcher.whenNodeType('space'),
130
+ actions: () =>
131
+ Effect.succeed(
132
+ Array.from({ length: 5 }, (_, i) => ({
133
+ id: `space-actions/action-${i}`,
134
+ data: Effect.fnUntraced(function* () {
135
+ log.info('action', { id: 'space-actions', index: i });
136
+ }),
137
+ properties: getProperties(`space-actions/action-${i}`, {
138
+ label: `Action ${i}`,
139
+ icon: faker.properties.icon(),
140
+ }),
141
+ })),
200
142
  ),
201
- ),
202
- }),
203
- // Create object nodes.
204
- createExtension({
205
- id: 'objects',
206
- connector: (node) => {
207
- const count = Rx.make((get) => {
208
- let value = 3;
209
- const interval = setInterval(() => {
210
- if (value >= 20) {
211
- clearInterval(interval);
212
- return;
213
- }
143
+ }),
144
+ // Create object nodes.
145
+ GraphBuilder.createExtension({
146
+ id: 'objects',
147
+ match: NodeMatcher.whenNodeType('space'),
148
+ connector: (_, get) =>
149
+ Effect.sync(() => {
150
+ const count = Atom.make((get) => {
151
+ let value = 3;
152
+ const interval = setInterval(() => {
153
+ if (value >= 20) {
154
+ clearInterval(interval);
155
+ return;
156
+ }
214
157
 
215
- value++;
216
- get.setSelf(value);
217
- }, 5000);
218
- get.addFinalizer(() => clearInterval(interval));
219
- return value;
220
- });
158
+ value++;
159
+ get.setSelf(value);
160
+ }, 5000);
161
+ get.addFinalizer(() => clearInterval(interval));
162
+ return value;
163
+ });
221
164
 
222
- return Rx.make((get) =>
223
- pipe(
224
- get(node),
225
- Option.flatMap((node) => (node.type === 'space' ? Option.some(node) : Option.none())),
226
- Option.map((node) => {
227
- return [
228
- ...Array.from({ length: get(count) }, (_, i) => ({
229
- id: `${node.id}/object-${i}`,
230
- type: 'object',
231
- properties: getProperties(`${node.id}/object-${i}`, {
232
- label: `Object ${i}`,
233
- icon: faker.properties.icon(),
234
- }),
235
- })),
236
- ];
237
- }),
238
- Option.getOrElse(() => []),
239
- ),
240
- );
241
- },
242
- }),
243
- // Create object actions.
244
- createExtension({
245
- id: 'object-actions',
246
- actions: (node) =>
247
- Rx.make((get) =>
248
- pipe(
249
- get(node),
250
- Option.flatMap((node) => (node.type === 'object' ? Option.some(node) : Option.none())),
251
- Option.map((node) => {
252
- return [
253
- ...Array.from({ length: 5 }, (_, i) => ({
254
- id: `${node.id}/action-${i}`,
255
- data: () => {
256
- log.info('action', { id: node.id, index: i });
257
- },
258
- properties: getProperties(`${node.id}/action-${i}`, {
259
- label: `Action ${i}`,
260
- icon: faker.properties.icon(),
261
- }),
262
- })),
263
- ];
264
- }),
265
- Option.getOrElse(() => []),
165
+ return Array.from({ length: get(count) }, (_, i) => ({
166
+ id: `object-${i}`,
167
+ type: 'object',
168
+ properties: getProperties(`object-${i}`, {
169
+ label: `Object ${i}`,
170
+ icon: faker.properties.icon(),
171
+ }),
172
+ }));
173
+ }),
174
+ }),
175
+ // Create object actions.
176
+ GraphBuilder.createExtension({
177
+ id: 'object-actions',
178
+ match: NodeMatcher.whenNodeType('object'),
179
+ actions: () =>
180
+ Effect.succeed(
181
+ Array.from({ length: 5 }, (_, i) => ({
182
+ id: `object-actions/action-${i}`,
183
+ data: Effect.fnUntraced(function* () {
184
+ log.info('action', { id: 'object-actions', index: i });
185
+ }),
186
+ properties: getProperties(`object-actions/action-${i}`, {
187
+ label: `Action ${i}`,
188
+ icon: faker.properties.icon(),
189
+ }),
190
+ })),
266
191
  ),
267
- ),
268
- }),
269
- ];
192
+ }),
193
+ ]),
194
+ );
270
195
  };
@@ -2,11 +2,11 @@
2
2
  // Copyright 2023 DXOS.org
3
3
  //
4
4
 
5
- import { Schema } from 'effect';
5
+ import * as Schema from 'effect/Schema';
6
6
 
7
- import { type NodeArg } from '@dxos/app-graph';
8
- import { type Live, Obj, Type } from '@dxos/echo';
9
- import { TypedObject } from '@dxos/echo-schema';
7
+ import { type Node } from '@dxos/app-graph';
8
+ import { Obj, Type } from '@dxos/echo';
9
+ import { TestSchema } from '@dxos/echo/testing';
10
10
  import { faker } from '@dxos/random';
11
11
  import { range } from '@dxos/util';
12
12
 
@@ -17,12 +17,12 @@ import { range } from '@dxos/util';
17
17
  export type TestItem = { id: string; type: string } & Record<string, any>;
18
18
 
19
19
  type ObjectDataGenerator = {
20
- createSchema?: () => Schema.Schema.AnyNoContext;
20
+ createSchema?: () => Type.Obj.Any;
21
21
  createData: () => any;
22
22
  };
23
23
 
24
- type ObjectFactory<T extends Live<any>> = {
25
- schema?: Schema.Schema.AnyNoContext; // TODO(burdon): Support both typed and expando schema.
24
+ type ObjectFactory<T> = {
25
+ schema?: Type.Obj.Any; // TODO(burdon): Support both typed and expando schema.
26
26
  createObject: () => T;
27
27
  };
28
28
 
@@ -32,7 +32,7 @@ const createFactory = ({ createSchema, createData }: ObjectDataGenerator) => {
32
32
  const schema = createSchema?.();
33
33
  return {
34
34
  schema,
35
- createObject: () => (schema ? Obj.make(schema, createData()) : Obj.make(Type.Expando, createData())),
35
+ createObject: () => (schema ? Obj.make(schema, createData()) : Obj.make(TestSchema.Expando, createData())),
36
36
  };
37
37
  };
38
38
 
@@ -58,15 +58,17 @@ export const defaultGenerators: { [type: string]: ObjectDataGenerator } = {
58
58
 
59
59
  project: {
60
60
  createSchema: () =>
61
- class ProjectType extends TypedObject({
62
- typename: 'example.com/type/Project',
63
- version: '0.1.0',
64
- })({
61
+ Schema.Struct({
65
62
  title: Schema.String,
66
63
  repo: Schema.String,
67
64
  status: Schema.String,
68
65
  priority: Schema.Number,
69
- }) {},
66
+ }).pipe(
67
+ Type.object({
68
+ typename: 'example.com/type/Project',
69
+ version: '0.1.0',
70
+ }),
71
+ ),
70
72
 
71
73
  createData: () => ({
72
74
  title: faker.commerce.productName(),
@@ -92,7 +94,7 @@ export class TestObjectGenerator {
92
94
  }, {});
93
95
  }
94
96
 
95
- get schema(): Schema.Schema.AnyNoContext[] {
97
+ get schema(): Type.Obj.Any[] {
96
98
  return Object.values(this.factories).map((f) => f.schema!);
97
99
  }
98
100
 
@@ -140,7 +142,7 @@ export const createTree = () => {
140
142
  properties: {
141
143
  label: l0.title,
142
144
  icon: 'ph--horse--regular',
143
- disposition: 'collection',
145
+ disposition: 'workspace',
144
146
  },
145
147
  nodes: [
146
148
  ...[...Array(4)].map(() => {
@@ -173,7 +175,7 @@ export const createTree = () => {
173
175
  },
174
176
  },
175
177
  ],
176
- } satisfies NodeArg<any>;
178
+ } satisfies Node.NodeArg<any>;
177
179
  }),
178
180
  {
179
181
  id: `${faker.string.uuid()}__a1`,
@@ -194,9 +196,9 @@ export const createTree = () => {
194
196
  },
195
197
  },
196
198
  ],
197
- } satisfies NodeArg<any>;
199
+ } satisfies Node.NodeArg<any>;
198
200
  }),
199
- } satisfies NodeArg<any>;
201
+ } satisfies Node.NodeArg<any>;
200
202
 
201
203
  return initialContent;
202
204
  };
@@ -4,22 +4,22 @@
4
4
 
5
5
  import { type Instruction } from '@atlaskit/pragmatic-drag-and-drop-hitbox/tree-item';
6
6
 
7
- import { type NodeArg } from '@dxos/app-graph';
7
+ import { type Node } from '@dxos/app-graph';
8
8
  import { log } from '@dxos/log';
9
9
  import { type TreeData } from '@dxos/react-ui-list';
10
10
 
11
- const removeItem = (tree: NodeArg<any>, source: TreeData) => {
11
+ const removeItem = (tree: Node.NodeArg<any>, source: TreeData) => {
12
12
  const parent = getNode(tree, source.path.slice(1, -1));
13
- const index = parent.nodes!.findIndex(({ id }) => id === source.id);
13
+ const index = parent.nodes!.findIndex((node: Node.NodeArg<any>) => node.id === source.id);
14
14
  const item = parent.nodes![index];
15
15
  parent.nodes!.splice(index, 1);
16
16
  return item;
17
17
  };
18
18
 
19
- const getNode = (tree: NodeArg<any>, path: string[]) => {
19
+ const getNode = (tree: Node.NodeArg<any>, path: string[]) => {
20
20
  let node = tree;
21
21
  for (const part of path) {
22
- node = node.nodes!.find(({ id }) => id === part)!;
22
+ node = node.nodes!.find((n: Node.NodeArg<any>) => n.id === part)!;
23
23
  }
24
24
  return node;
25
25
  };
@@ -31,7 +31,7 @@ export const updateState = ({
31
31
  source,
32
32
  target,
33
33
  }: {
34
- state: NodeArg<any>;
34
+ state: Node.NodeArg<any>;
35
35
  instruction: Instruction;
36
36
  source: TreeData;
37
37
  target: TreeData;
@@ -0,0 +1,21 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { type Atom } from '@effect-atom/atom-react';
6
+
7
+ import { Capability } from '@dxos/app-framework';
8
+
9
+ import { meta } from '../meta';
10
+
11
+ export namespace NavTreeCapabilities {
12
+ export type NavTreeItemState = { open: boolean; current: boolean; alternateTree?: boolean };
13
+
14
+ export type NavTreeStateStore = {
15
+ getItem: (path: string[]) => NavTreeItemState;
16
+ getItemAtom: (path: string[]) => Atom.Atom<NavTreeItemState>;
17
+ setItem: (path: string[], key: 'open' | 'current' | 'alternateTree', next: boolean) => void;
18
+ };
19
+
20
+ export const State = Capability.make<NavTreeStateStore>(`${meta.id}/capability/state`);
21
+ }
@@ -0,0 +1,11 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ import { type ActivationEvent, Common } from '@dxos/app-framework';
6
+
7
+ import { meta } from '../meta';
8
+
9
+ export namespace NavTreeEvents {
10
+ export const StateReady: ActivationEvent.ActivationEvent = Common.ActivationEvent.createStateEvent(meta.id);
11
+ }
@@ -0,0 +1,7 @@
1
+ //
2
+ // Copyright 2025 DXOS.org
3
+ //
4
+
5
+ export * from './capabilities';
6
+ export * from './events';
7
+ export * from './schema';
@@ -2,11 +2,11 @@
2
2
  // Copyright 2023 DXOS.org
3
3
  //
4
4
 
5
- import { type Action, type ActionLike, type Node } from '@dxos/app-graph';
5
+ import { type Node } from '@dxos/app-graph';
6
6
  import { type Label } from '@dxos/react-ui';
7
7
  import { type MaybePromise, type Position } from '@dxos/util';
8
8
 
9
- export type NavTreeItemGraphNode = Node<
9
+ export type NavTreeItemGraphNode = Node.Node<
10
10
  any,
11
11
  Partial<
12
12
  NodeProperties & {
@@ -14,7 +14,7 @@ export type NavTreeItemGraphNode = Node<
14
14
  persistenceKey: string;
15
15
  acceptPersistenceClass: Set<string>;
16
16
  acceptPersistenceKey: Set<string>;
17
- onRearrangeChildren: (nextOrder: NavTreeItemGraphNode[]) => MaybePromise<void>;
17
+ onRearrange: (nextOrder: unknown[]) => MaybePromise<void>;
18
18
  onCopy: (activeNode: NavTreeItemGraphNode, index?: number) => MaybePromise<void>;
19
19
  onTransferStart: (activeNode: NavTreeItemGraphNode, index?: number) => MaybePromise<void>;
20
20
  onTransferEnd: (activeNode: NavTreeItemGraphNode, destinationParent: NavTreeItemGraphNode) => MaybePromise<void>;
@@ -23,18 +23,19 @@ export type NavTreeItemGraphNode = Node<
23
23
  >;
24
24
 
25
25
  export type FlattenedActions = {
26
- actions: ActionLike[];
27
- groupedActions: Record<string, Action[]>;
26
+ actions: Node.ActionLike[];
27
+ groupedActions: Record<string, Node.Action[]>;
28
28
  };
29
29
 
30
30
  type SharedProperties = {
31
- label: Label;
32
- icon?: string;
31
+ testId?: string;
33
32
  disabled?: boolean;
34
33
  position?: Position;
35
- testId?: string;
34
+ label: Label;
36
35
  className?: string;
37
36
  headingClassName?: string;
37
+ icon?: string;
38
+ iconHue?: string;
38
39
  };
39
40
 
40
41
  export type NodeProperties = SharedProperties & {