collabmd 0.1.31 → 0.1.33

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 (99) hide show
  1. package/dist/client/assets/{drawio-editor-B4sHHwWJ.js → drawio-editor-BMTwP5mD.js} +1 -1
  2. package/dist/client/assets/drawioEditor-D6clB5OH.js +2 -0
  3. package/dist/client/assets/{editor-session-BKHEYkbY.js → editor-session-Dzy_85Wp.js} +2 -2
  4. package/dist/client/assets/embedded-editor-base-CgEkjNYn.css +1 -0
  5. package/dist/client/assets/{excalidraw-editor-CHbeNZu6.js → excalidraw-editor-CAP9F8CB.js} +3 -3
  6. package/dist/client/assets/{excalidrawEditor-BhaTX2Ko.js → excalidrawEditor-DD4AvzYP.js} +2 -2
  7. package/dist/client/assets/exportDocument-BbkN85c4.css +1 -0
  8. package/dist/client/assets/index-BIt5EZXz.css +1 -0
  9. package/dist/client/assets/{index-kPgEYvEX.js → index-Czg_KL-i.js} +2 -2
  10. package/dist/client/assets/inter-cyrillic-ext-wght-normal-BOeWTOD4.woff2 +0 -0
  11. package/dist/client/assets/inter-cyrillic-wght-normal-DqGufNeO.woff2 +0 -0
  12. package/dist/client/assets/inter-greek-ext-wght-normal-DlzME5K_.woff2 +0 -0
  13. package/dist/client/assets/inter-greek-wght-normal-CkhJZR-_.woff2 +0 -0
  14. package/dist/client/assets/inter-latin-ext-wght-normal-DO1Apj_S.woff2 +0 -0
  15. package/dist/client/assets/inter-latin-wght-normal-Dx4kXJAl.woff2 +0 -0
  16. package/dist/client/assets/inter-vietnamese-wght-normal-CBcvBZtf.woff2 +0 -0
  17. package/dist/client/assets/jetbrains-mono-cyrillic-400-normal-BEIGL1Tu.woff2 +0 -0
  18. package/dist/client/assets/jetbrains-mono-cyrillic-400-normal-ugxPyKxw.woff +0 -0
  19. package/dist/client/assets/jetbrains-mono-greek-400-normal-B9oWc5Lo.woff +0 -0
  20. package/dist/client/assets/jetbrains-mono-greek-400-normal-C190GLew.woff2 +0 -0
  21. package/dist/client/assets/jetbrains-mono-latin-400-normal-6-qcROiO.woff +0 -0
  22. package/dist/client/assets/jetbrains-mono-latin-400-normal-V6pRDFza.woff2 +0 -0
  23. package/dist/client/assets/jetbrains-mono-latin-ext-400-normal-Bc8Ftmh3.woff2 +0 -0
  24. package/dist/client/assets/jetbrains-mono-latin-ext-400-normal-fXTG6kC5.woff +0 -0
  25. package/dist/client/assets/jetbrains-mono-vietnamese-400-normal-CqNFfHCs.woff +0 -0
  26. package/dist/client/assets/main-DeowJOSp.js +1368 -0
  27. package/dist/client/assets/vault-api-client-D7Ck0CvR.css +1 -0
  28. package/dist/client/assets/vault-api-client-p7h7cXKM.js +1 -0
  29. package/dist/client/drawio-editor.html +1 -1
  30. package/dist/client/excalidraw-editor.html +1 -1
  31. package/dist/client/export-document.html +2 -2
  32. package/dist/client/index.html +2 -2
  33. package/package.json +8 -5
  34. package/src/client/app/main-entry.js +2 -0
  35. package/src/client/application/app-shell/git-feature.js +28 -36
  36. package/src/client/application/app-shell/presence-feature.js +3 -1
  37. package/src/client/application/diagram-preview-hydrator.js +24 -15
  38. package/src/client/application/mermaid-preview-hydrator.js +121 -4
  39. package/src/client/application/plantuml-preview-hydrator.js +6 -16
  40. package/src/client/application/preview-renderer.js +11 -2
  41. package/src/client/bootstrap/collabmd-app-shell.js +182 -50
  42. package/src/client/domain/excalidraw-document-switch.js +3 -0
  43. package/src/client/excalidraw-editor.js +187 -84
  44. package/src/client/infrastructure/auth-client.js +4 -4
  45. package/src/client/infrastructure/backlinks-api-client.js +18 -0
  46. package/src/client/infrastructure/comment-thread-store.js +4 -0
  47. package/src/client/infrastructure/editor-session.js +6 -0
  48. package/src/client/infrastructure/editor-view-adapter.js +23 -0
  49. package/src/client/infrastructure/git-api-client.js +134 -0
  50. package/src/client/infrastructure/plantuml-api-client.js +21 -0
  51. package/src/client/infrastructure/vault-api-client.js +115 -0
  52. package/src/client/presentation/backlinks-panel.js +6 -9
  53. package/src/client/presentation/bases-preview-controller.js +1413 -34
  54. package/src/client/presentation/comments-panel.js +50 -5
  55. package/src/client/presentation/excalidraw-embed-controller.js +251 -15
  56. package/src/client/presentation/excalidraw-embed-reconciler.js +0 -1
  57. package/src/client/presentation/file-action-controller.js +97 -0
  58. package/src/client/presentation/file-explorer-controller.js +2 -0
  59. package/src/client/presentation/file-explorer-view.js +368 -0
  60. package/src/client/presentation/file-history-view-controller.js +41 -40
  61. package/src/client/presentation/git-diff-view-controller.js +70 -53
  62. package/src/client/presentation/git-panel-controller.js +12 -30
  63. package/src/client/styles/components/scrollbars.css +5 -0
  64. package/src/client/styles/export-document.css +45 -2
  65. package/src/client/styles/features/auth-gate.css +13 -24
  66. package/src/client/styles/features/comment-card.css +6 -0
  67. package/src/client/styles/features/comments-drawer.css +38 -18
  68. package/src/client/styles/features/diagram-preview.css +33 -0
  69. package/src/client/styles/features/embedded-preview.css +37 -11
  70. package/src/client/styles/features/preview-markdown.css +559 -39
  71. package/src/client/styles/foundation/themes.css +4 -0
  72. package/src/client/styles/foundation/tokens.css +4 -3
  73. package/src/client/styles/layout/sidebar.css +72 -0
  74. package/src/server/auth/auth-common.js +224 -0
  75. package/src/server/auth/auth-constants.js +30 -0
  76. package/src/server/auth/auth-strategies.js +320 -0
  77. package/src/server/auth/create-auth-service.js +24 -545
  78. package/src/server/domain/backlink-index.js +177 -5
  79. package/src/server/domain/bases/base-definition.js +382 -0
  80. package/src/server/domain/bases/base-expression-runtime.js +1196 -0
  81. package/src/server/domain/bases/base-index-snapshot-store.js +565 -0
  82. package/src/server/domain/bases/base-query-metadata.js +242 -0
  83. package/src/server/domain/bases/base-query-results.js +215 -0
  84. package/src/server/domain/bases/base-query-service.js +406 -1992
  85. package/src/server/domain/bases/base-transform.js +116 -0
  86. package/src/server/domain/collaboration/collaboration-room.js +36 -1
  87. package/src/server/domain/collaboration/room-client-state-store.js +1 -0
  88. package/src/server/domain/collaboration/room-persistence-controller.js +1 -1
  89. package/src/server/infrastructure/http/create-vault-api-query-handler.js +161 -1
  90. package/src/server/infrastructure/http/http-response.js +56 -0
  91. package/src/server/infrastructure/persistence/vault-file-store.js +110 -0
  92. package/dist/client/assets/drawioEditor-DGpo2hcx.js +0 -2
  93. package/dist/client/assets/embedded-editor-base-DgmRcsR8.css +0 -1
  94. package/dist/client/assets/exportDocument-DmV7Gngb.css +0 -1
  95. package/dist/client/assets/index-D69HOZHr.css +0 -1
  96. package/dist/client/assets/main-DSxNTtD-.js +0 -1243
  97. package/dist/client/assets/vault-api-client-BzHQseMN.js +0 -1
  98. package/dist/client/assets/vault-api-client-De7kMvrE.css +0 -1
  99. /package/dist/client/assets/{exportDocument-CtZKWE2c.js → exportDocument-Zfwq1XVx.js} +0 -0
@@ -17,7 +17,10 @@ import { BrowserNavigationPort } from '../infrastructure/browser-navigation-port
17
17
  import { BrowserNotificationPort } from '../infrastructure/browser-notification-port.js';
18
18
  import { BrowserPreferencesPort } from '../infrastructure/browser-preferences-port.js';
19
19
  import { AppVersionMonitor } from '../infrastructure/app-version-monitor.js';
20
+ import { backlinksApiClient } from '../infrastructure/backlinks-api-client.js';
21
+ import { gitApiClient } from '../infrastructure/git-api-client.js';
20
22
  import { getRuntimeConfig } from '../infrastructure/runtime-config.js';
23
+ import { plantUmlApiClient } from '../infrastructure/plantuml-api-client.js';
21
24
  import { TabActivityLock } from '../infrastructure/tab-activity-lock.js';
22
25
  import { vaultApiClient } from '../infrastructure/vault-api-client.js';
23
26
  import { WorkspaceSyncClient } from '../infrastructure/workspace-sync-client.js';
@@ -39,58 +42,169 @@ import { VideoEmbedController } from '../presentation/video-embed-controller.js'
39
42
  import { ImageLightboxController } from '../presentation/image-lightbox-controller.js';
40
43
  import { renderAppShell } from '../presentation/app-shell-renderer.js';
41
44
 
42
- const APP_SHELL_FEATURES = Object.freeze({
43
- chat: chatFeature,
44
- comments: commentsFeature,
45
- export: exportFeature,
46
- git: gitFeature,
47
- presence: presenceFeature,
48
- ui: uiFeature,
49
- workspace: workspaceFeature,
50
- });
51
-
52
- function installAppShellFeatures(appShell) {
53
- const featureMethodOwners = {};
54
-
55
- Object.entries(APP_SHELL_FEATURES).forEach(([featureName, feature]) => {
56
- Object.entries(feature).forEach(([methodName, method]) => {
57
- if (typeof method !== 'function') {
58
- return;
59
- }
60
-
61
- if (Object.hasOwn(featureMethodOwners, methodName)) {
62
- throw new Error(
63
- `CollabMdAppShell feature method "${methodName}" is declared by both "${featureMethodOwners[methodName]}" and "${featureName}".`,
64
- );
65
- }
66
-
67
- if (methodName in appShell) {
68
- throw new Error(
69
- `CollabMdAppShell feature method "${methodName}" conflicts with an existing app shell member.`,
70
- );
71
- }
72
-
73
- Object.defineProperty(appShell, methodName, {
74
- configurable: true,
75
- enumerable: false,
76
- value: method.bind(appShell),
77
- writable: false,
78
- });
79
- featureMethodOwners[methodName] = featureName;
80
- });
81
- });
82
-
83
- Object.defineProperty(appShell, 'featureMethodOwners', {
84
- configurable: false,
85
- enumerable: false,
86
- value: Object.freeze(featureMethodOwners),
87
- writable: false,
88
- });
89
- }
90
-
91
45
  export class CollabMdAppShell {
46
+ updateChatMessages(...args) { return chatFeature.updateChatMessages.apply(this, args); }
47
+ toggleChatPanel(...args) { return chatFeature.toggleChatPanel.apply(this, args); }
48
+ openChatPanel(...args) { return chatFeature.openChatPanel.apply(this, args); }
49
+ closeChatPanel(...args) { return chatFeature.closeChatPanel.apply(this, args); }
50
+ handleChatSubmit(...args) { return chatFeature.handleChatSubmit.apply(this, args); }
51
+ renderChat(...args) { return chatFeature.renderChat.apply(this, args); }
52
+ createChatMessageElement(...args) { return chatFeature.createChatMessageElement.apply(this, args); }
53
+ scrollChatToBottom(...args) { return chatFeature.scrollChatToBottom.apply(this, args); }
54
+ formatChatTimestamp(...args) { return chatFeature.formatChatTimestamp.apply(this, args); }
55
+ getChatMessageFileLabel(...args) { return chatFeature.getChatMessageFileLabel.apply(this, args); }
56
+ formatChatToastMessage(...args) { return chatFeature.formatChatToastMessage.apply(this, args); }
57
+ syncChatToggleButton(...args) { return chatFeature.syncChatToggleButton.apply(this, args); }
58
+ syncChatNotificationButton(...args) { return chatFeature.syncChatNotificationButton.apply(this, args); }
59
+ handleChatNotificationToggle(...args) { return chatFeature.handleChatNotificationToggle.apply(this, args); }
60
+ maybeNotifyChatMessage(...args) { return chatFeature.maybeNotifyChatMessage.apply(this, args); }
61
+ maybeShowBrowserChatNotification(...args) { return chatFeature.maybeShowBrowserChatNotification.apply(this, args); }
62
+ getCommentFileKind(...args) { return commentsFeature.getCommentFileKind.apply(this, args); }
63
+ syncCommentChrome(...args) { return commentsFeature.syncCommentChrome.apply(this, args); }
64
+ handleCommentSelectionChange(...args) { return commentsFeature.handleCommentSelectionChange.apply(this, args); }
65
+ handleCommentThreadsChange(...args) { return commentsFeature.handleCommentThreadsChange.apply(this, args); }
66
+ handleCommentEditorContentChange(...args) { return commentsFeature.handleCommentEditorContentChange.apply(this, args); }
67
+ refreshCommentUiLayout(...args) { return commentsFeature.refreshCommentUiLayout.apply(this, args); }
68
+ initializeExportBridge(...args) { return exportFeature.initializeExportBridge.apply(this, args); }
69
+ handleExportRequest(...args) { return exportFeature.handleExportRequest.apply(this, args); }
70
+ formatPullBackupToast(...args) { return gitFeature.formatPullBackupToast.apply(this, args); }
71
+ setGitOperationStatus(...args) { return gitFeature.setGitOperationStatus.apply(this, args); }
72
+ runGitActionWithStatus(...args) { return gitFeature.runGitActionWithStatus.apply(this, args); }
73
+ handleGitDiffSelection(...args) { return gitFeature.handleGitDiffSelection.apply(this, args); }
74
+ handleGitCommitSelection(...args) { return gitFeature.handleGitCommitSelection.apply(this, args); }
75
+ handleGitHistorySelection(...args) { return gitFeature.handleGitHistorySelection.apply(this, args); }
76
+ handleGitFileHistorySelection(...args) { return gitFeature.handleGitFileHistorySelection.apply(this, args); }
77
+ handleGitFilePreviewSelection(...args) { return gitFeature.handleGitFilePreviewSelection.apply(this, args); }
78
+ handleGitRepoChange(...args) { return gitFeature.handleGitRepoChange.apply(this, args); }
79
+ syncFileHistoryButton(...args) { return gitFeature.syncFileHistoryButton.apply(this, args); }
80
+ syncMainChrome(...args) { return gitFeature.syncMainChrome.apply(this, args); }
81
+ showGitDiff(...args) { return gitFeature.showGitDiff.apply(this, args); }
82
+ showGitCommit(...args) { return gitFeature.showGitCommit.apply(this, args); }
83
+ showGitHistory(...args) { return gitFeature.showGitHistory.apply(this, args); }
84
+ showGitFileHistory(...args) { return gitFeature.showGitFileHistory.apply(this, args); }
85
+ showGitFilePreview(...args) { return gitFeature.showGitFilePreview.apply(this, args); }
86
+ postGitAction(...args) { return gitFeature.postGitAction.apply(this, args); }
87
+ refreshWorkspaceAfterGitAction(...args) { return gitFeature.refreshWorkspaceAfterGitAction.apply(this, args); }
88
+ refreshGitAfterAction(...args) { return gitFeature.refreshGitAfterAction.apply(this, args); }
89
+ finalizeGitAction(...args) { return gitFeature.finalizeGitAction.apply(this, args); }
90
+ handleWorkspaceChangeForCurrentFile(...args) { return gitFeature.handleWorkspaceChangeForCurrentFile.apply(this, args); }
91
+ handleIncomingWorkspaceEvent(...args) { return gitFeature.handleIncomingWorkspaceEvent.apply(this, args); }
92
+ stageGitFile(...args) { return gitFeature.stageGitFile.apply(this, args); }
93
+ unstageGitFile(...args) { return gitFeature.unstageGitFile.apply(this, args); }
94
+ pushGitBranch(...args) { return gitFeature.pushGitBranch.apply(this, args); }
95
+ pullGitBranch(...args) { return gitFeature.pullGitBranch.apply(this, args); }
96
+ openGitResetDialog(...args) { return gitFeature.openGitResetDialog.apply(this, args); }
97
+ handleGitResetSubmit(...args) { return gitFeature.handleGitResetSubmit.apply(this, args); }
98
+ openGitCommitDialog(...args) { return gitFeature.openGitCommitDialog.apply(this, args); }
99
+ handleGitCommitSubmit(...args) { return gitFeature.handleGitCommitSubmit.apply(this, args); }
100
+ updateGlobalUsers(...args) { return presenceFeature.updateGlobalUsers.apply(this, args); }
101
+ updateFileAwareness(...args) { return presenceFeature.updateFileAwareness.apply(this, args); }
102
+ renderPresence(...args) { return presenceFeature.renderPresence.apply(this, args); }
103
+ renderAvatars(...args) { return presenceFeature.renderAvatars.apply(this, args); }
104
+ toggleFollowUser(...args) { return presenceFeature.toggleFollowUser.apply(this, args); }
105
+ stopFollowingUser(...args) { return presenceFeature.stopFollowingUser.apply(this, args); }
106
+ syncFollowedUser(...args) { return presenceFeature.syncFollowedUser.apply(this, args); }
107
+ followUserCursor(...args) { return presenceFeature.followUserCursor.apply(this, args); }
108
+ followExcalidrawUser(...args) { return presenceFeature.followExcalidrawUser.apply(this, args); }
109
+ resolveFileClientId(...args) { return presenceFeature.resolveFileClientId.apply(this, args); }
110
+ bindEvents(...args) { return uiFeature.bindEvents.apply(this, args); }
111
+ clearInitialFileBootstrap(...args) { return uiFeature.clearInitialFileBootstrap.apply(this, args); }
112
+ closeToolbarOverflowMenu(...args) { return uiFeature.closeToolbarOverflowMenu.apply(this, args); }
113
+ getStoredLineWrapping(...args) { return uiFeature.getStoredLineWrapping.apply(this, args); }
114
+ handleConnectionChange(...args) { return uiFeature.handleConnectionChange.apply(this, args); }
115
+ handlePreviewContentClick(...args) { return uiFeature.handlePreviewContentClick.apply(this, args); }
116
+ handleThemeChange(...args) { return uiFeature.handleThemeChange.apply(this, args); }
117
+ hideEditorLoading(...args) { return uiFeature.hideEditorLoading.apply(this, args); }
118
+ initialize(...args) { return uiFeature.initialize.apply(this, args); }
119
+ initializeVisualViewportBinding(...args) { return uiFeature.initializeVisualViewportBinding.apply(this, args); }
120
+ initializeVersionMonitoring(...args) { return uiFeature.initializeVersionMonitoring.apply(this, args); }
121
+ promptForVersionReload(...args) { return uiFeature.promptForVersionReload.apply(this, args); }
122
+ scheduleBacklinkRefresh(...args) { return uiFeature.scheduleBacklinkRefresh.apply(this, args); }
123
+ setToolbarOverflowOpen(...args) { return uiFeature.setToolbarOverflowOpen.apply(this, args); }
124
+ showEditorLoadError(...args) { return uiFeature.showEditorLoadError.apply(this, args); }
125
+ showEditorLoading(...args) { return uiFeature.showEditorLoading.apply(this, args); }
126
+ syncVisualViewportBounds(...args) { return uiFeature.syncVisualViewportBounds.apply(this, args); }
127
+ syncToolbarOverflowVisibility(...args) { return uiFeature.syncToolbarOverflowVisibility.apply(this, args); }
128
+ syncWrapToggle(...args) { return uiFeature.syncWrapToggle.apply(this, args); }
129
+ toggleToolbarOverflowMenu(...args) { return uiFeature.toggleToolbarOverflowMenu.apply(this, args); }
130
+ toggleLineWrapping(...args) { return uiFeature.toggleLineWrapping.apply(this, args); }
131
+ applySidebarVisibility(...args) { return uiFeature.applySidebarVisibility.apply(this, args); }
132
+ closeSidebarOnMobile(...args) { return uiFeature.closeSidebarOnMobile.apply(this, args); }
133
+ isMobileViewport(...args) { return uiFeature.isMobileViewport.apply(this, args); }
134
+ restoreSidebarState(...args) { return uiFeature.restoreSidebarState.apply(this, args); }
135
+ setSidebarTab(...args) { return uiFeature.setSidebarTab.apply(this, args); }
136
+ setSidebarVisibility(...args) { return uiFeature.setSidebarVisibility.apply(this, args); }
137
+ toggleSidebar(...args) { return uiFeature.toggleSidebar.apply(this, args); }
138
+ getCurrentUser(...args) { return uiFeature.getCurrentUser.apply(this, args); }
139
+ getCurrentUserName(...args) { return uiFeature.getCurrentUserName.apply(this, args); }
140
+ getStoredUserName(...args) { return uiFeature.getStoredUserName.apply(this, args); }
141
+ handleDisplayNameSubmit(...args) { return uiFeature.handleDisplayNameSubmit.apply(this, args); }
142
+ isIdentityManagedByAuth(...args) { return uiFeature.isIdentityManagedByAuth.apply(this, args); }
143
+ openDisplayNameDialog(...args) { return uiFeature.openDisplayNameDialog.apply(this, args); }
144
+ promptForDisplayNameIfNeeded(...args) { return uiFeature.promptForDisplayNameIfNeeded.apply(this, args); }
145
+ syncCurrentUserName(...args) { return uiFeature.syncCurrentUserName.apply(this, args); }
146
+ syncIdentityManagementUi(...args) { return uiFeature.syncIdentityManagementUi.apply(this, args); }
147
+ applyMarkdownToolbarAction(...args) { return uiFeature.applyMarkdownToolbarAction.apply(this, args); }
148
+ copyCurrentLink(...args) { return uiFeature.copyCurrentLink.apply(this, args); }
149
+ closeMarkdownBlockMenu(...args) { return uiFeature.closeMarkdownBlockMenu.apply(this, args); }
150
+ getActiveMarkdownBlockAction(...args) { return uiFeature.getActiveMarkdownBlockAction.apply(this, args); }
151
+ getMarkdownBlockMenuPopover(...args) { return uiFeature.getMarkdownBlockMenuPopover.apply(this, args); }
152
+ handleEditorImageInsert(...args) { return uiFeature.handleEditorImageInsert.apply(this, args); }
153
+ handleMarkdownToolbarClick(...args) { return uiFeature.handleMarkdownToolbarClick.apply(this, args); }
154
+ handleMarkdownToolbarDocumentPointerDown(...args) { return uiFeature.handleMarkdownToolbarDocumentPointerDown.apply(this, args); }
155
+ handleMarkdownToolbarKeydown(...args) { return uiFeature.handleMarkdownToolbarKeydown.apply(this, args); }
156
+ handleToolbarImageInsert(...args) { return uiFeature.handleToolbarImageInsert.apply(this, args); }
157
+ isMarkdownBlockMenuOpen(...args) { return uiFeature.isMarkdownBlockMenuOpen.apply(this, args); }
158
+ openMarkdownBlockMenu(...args) { return uiFeature.openMarkdownBlockMenu.apply(this, args); }
159
+ positionMarkdownBlockMenu(...args) { return uiFeature.positionMarkdownBlockMenu.apply(this, args); }
160
+ renderMarkdownBlockMenuPopover(...args) { return uiFeature.renderMarkdownBlockMenuPopover.apply(this, args); }
161
+ pickImageFile(...args) { return uiFeature.pickImageFile.apply(this, args); }
162
+ renderMarkdownToolbar(...args) { return uiFeature.renderMarkdownToolbar.apply(this, args); }
163
+ runEditorCommand(...args) { return uiFeature.runEditorCommand.apply(this, args); }
164
+ setActiveMarkdownBlockAction(...args) { return uiFeature.setActiveMarkdownBlockAction.apply(this, args); }
165
+ syncMarkdownToolbarBlockUi(...args) { return uiFeature.syncMarkdownToolbarBlockUi.apply(this, args); }
166
+ toggleMarkdownBlockMenu(...args) { return uiFeature.toggleMarkdownBlockMenu.apply(this, args); }
167
+ handleTabActivated(...args) { return uiFeature.handleTabActivated.apply(this, args); }
168
+ handleTabBlocked(...args) { return uiFeature.handleTabBlocked.apply(this, args); }
169
+ handleTabTakeover(...args) { return uiFeature.handleTabTakeover.apply(this, args); }
170
+ hideTabLockOverlay(...args) { return uiFeature.hideTabLockOverlay.apply(this, args); }
171
+ showTabLockOverlay(...args) { return uiFeature.showTabLockOverlay.apply(this, args); }
172
+ isExcalidrawFile(...args) { return workspaceFeature.isExcalidrawFile.apply(this, args); }
173
+ isBaseFile(...args) { return workspaceFeature.isBaseFile.apply(this, args); }
174
+ isDrawioFile(...args) { return workspaceFeature.isDrawioFile.apply(this, args); }
175
+ isImageFile(...args) { return workspaceFeature.isImageFile.apply(this, args); }
176
+ isMermaidFile(...args) { return workspaceFeature.isMermaidFile.apply(this, args); }
177
+ isPlantUmlFile(...args) { return workspaceFeature.isPlantUmlFile.apply(this, args); }
178
+ createDiagramPreviewDocument(...args) { return workspaceFeature.createDiagramPreviewDocument.apply(this, args); }
179
+ getPreviewSource(...args) { return workspaceFeature.getPreviewSource.apply(this, args); }
180
+ getStaticPreviewDocument(...args) { return workspaceFeature.getStaticPreviewDocument.apply(this, args); }
181
+ setStaticPreviewDocument(...args) { return workspaceFeature.setStaticPreviewDocument.apply(this, args); }
182
+ clearStaticPreviewDocument(...args) { return workspaceFeature.clearStaticPreviewDocument.apply(this, args); }
183
+ supportsFileHistory(...args) { return workspaceFeature.supportsFileHistory.apply(this, args); }
184
+ getDisplayName(...args) { return workspaceFeature.getDisplayName.apply(this, args); }
185
+ resetPreviewMode(...args) { return workspaceFeature.resetPreviewMode.apply(this, args); }
186
+ syncFileChrome(...args) { return workspaceFeature.syncFileChrome.apply(this, args); }
187
+ handleLayoutViewRequest(...args) { return workspaceFeature.handleLayoutViewRequest.apply(this, args); }
188
+ renderExcalidrawFilePreview(...args) { return workspaceFeature.renderExcalidrawFilePreview.apply(this, args); }
189
+ renderDrawioFilePreview(...args) { return workspaceFeature.renderDrawioFilePreview.apply(this, args); }
190
+ renderImageFilePreview(...args) { return workspaceFeature.renderImageFilePreview.apply(this, args); }
191
+ renderBaseFilePreview(...args) { return workspaceFeature.renderBaseFilePreview.apply(this, args); }
192
+ renderTextFilePreview(...args) { return workspaceFeature.renderTextFilePreview.apply(this, args); }
193
+ createResizeHandler(...args) { return workspaceFeature.createResizeHandler.apply(this, args); }
194
+ initializePreviewLayoutObserver(...args) { return workspaceFeature.initializePreviewLayoutObserver.apply(this, args); }
195
+ schedulePreviewLayoutSync(...args) { return workspaceFeature.schedulePreviewLayoutSync.apply(this, args); }
196
+ handleEditorScrollActivityChange(...args) { return workspaceFeature.handleEditorScrollActivityChange.apply(this, args); }
197
+ handleHashChange(...args) { return workspaceFeature.handleHashChange.apply(this, args); }
198
+ showEmptyState(...args) { return workspaceFeature.showEmptyState.apply(this, args); }
199
+ showDiffState(...args) { return workspaceFeature.showDiffState.apply(this, args); }
200
+ openFile(...args) { return workspaceFeature.openFile.apply(this, args); }
201
+ cleanupSession(...args) { return workspaceFeature.cleanupSession.apply(this, args); }
202
+ handleWikiLinkClick(...args) { return workspaceFeature.handleWikiLinkClick.apply(this, args); }
203
+ normalizeNewWikiFilePath(...args) { return workspaceFeature.normalizeNewWikiFilePath.apply(this, args); }
204
+ createAndOpenFile(...args) { return workspaceFeature.createAndOpenFile.apply(this, args); }
205
+ handleFileSelection(...args) { return workspaceFeature.handleFileSelection.apply(this, args); }
206
+
92
207
  constructor() {
93
- installAppShellFeatures(this);
94
208
  renderAppShell(document);
95
209
  this.elements = bindAppShellElements(document);
96
210
  this.runtimeConfig = getRuntimeConfig();
@@ -103,6 +217,9 @@ export class CollabMdAppShell {
103
217
  userNameKey: 'collabmd-user-name',
104
218
  });
105
219
  this.notifications = new BrowserNotificationPort();
220
+ this.backlinksApiClient = backlinksApiClient;
221
+ this.gitApiClient = gitApiClient;
222
+ this.plantUmlApiClient = plantUmlApiClient;
106
223
  this.vaultApiClient = vaultApiClient;
107
224
  this._session = null;
108
225
  this._hasPromptedForDisplayName = false;
@@ -160,6 +277,7 @@ export class CollabMdAppShell {
160
277
  });
161
278
  this.gitPanel = new GitPanelController({
162
279
  enabled: this.runtimeConfig.gitEnabled !== false,
280
+ gitApiClient: this.gitApiClient,
163
281
  onCommitStaged: () => this.openGitCommitDialog(),
164
282
  onOpenPullBackup: (filePath) => filePath && this.navigation.navigateToFile(filePath),
165
283
  onPullBranch: () => this.pullGitBranch(),
@@ -188,8 +306,14 @@ export class CollabMdAppShell {
188
306
  });
189
307
  this.basesPreview = new BasesPreviewController({
190
308
  getActiveFilePath: () => this.currentFilePath,
309
+ getSession: () => this.session,
191
310
  onOpenFile: (filePath) => filePath && this.navigation.navigateToFile(filePath),
192
311
  previewElement: this.elements.previewContent,
312
+ replaceBaseSource: ({ path, source }) => {
313
+ if (path && path === this.currentFilePath) {
314
+ this.session?.replaceText?.(source);
315
+ }
316
+ },
193
317
  toastController: this.toastController,
194
318
  vaultApiClient: this.vaultApiClient,
195
319
  });
@@ -199,6 +323,10 @@ export class CollabMdAppShell {
199
323
  this.previewRenderer = new PreviewRenderer({
200
324
  getContent: () => this.getPreviewSource(),
201
325
  getFileList: () => this.fileExplorer.flatDocumentFiles,
326
+ loadFileSource: async (filePath) => {
327
+ const payload = await this.vaultApiClient.readFile(filePath);
328
+ return String(payload?.content ?? '');
329
+ },
202
330
  getSourceFilePath: () => this.currentFilePath,
203
331
  onAfterRenderCommit: (_previewElement, stats) => {
204
332
  this.recordFileOpenMetric('preview_committed', {
@@ -234,6 +362,7 @@ export class CollabMdAppShell {
234
362
  this.refreshCommentUiLayout();
235
363
  },
236
364
  outlineController: this.outlineController,
365
+ plantUmlRenderClient: this.plantUmlApiClient,
237
366
  previewContainer: this.elements.previewContainer,
238
367
  previewElement: this.elements.previewContent,
239
368
  });
@@ -253,6 +382,7 @@ export class CollabMdAppShell {
253
382
  this.backlinksPanel = new BacklinksPanel({
254
383
  headerPanelElement: this.elements.backlinksHeaderPanel,
255
384
  inlinePanelElement: this.elements.backlinksInlinePanel,
385
+ loadBacklinks: (filePath, options = {}) => this.backlinksApiClient.readBacklinks(filePath, options),
256
386
  onFileSelect: (filePath) => this.handleFileSelection(filePath, { closeSidebarOnMobile: true }),
257
387
  panelElement: this.elements.backlinksPanel,
258
388
  });
@@ -321,6 +451,7 @@ export class CollabMdAppShell {
321
451
  vaultApiClient: this.vaultApiClient,
322
452
  });
323
453
  this.gitDiffView = new GitDiffViewController({
454
+ gitApiClient: this.gitApiClient,
324
455
  onBackToHistory: ({ historyFilePath } = {}) => {
325
456
  if (historyFilePath) {
326
457
  this.navigation.navigateToGitFileHistory({ filePath: historyFilePath });
@@ -336,6 +467,7 @@ export class CollabMdAppShell {
336
467
  });
337
468
  this.fileHistoryView = new FileHistoryViewController({
338
469
  diffRenderer: this.gitDiffView,
470
+ gitApiClient: this.gitApiClient,
339
471
  onOpenCommitDiff: (hash, { historyFilePath, path }) => this.handleGitCommitSelection(hash, {
340
472
  closeSidebarOnMobile: false,
341
473
  historyFilePath,
@@ -0,0 +1,3 @@
1
+ export function normalizeDocumentMode(mode) {
2
+ return mode === 'preview' ? 'preview' : 'edit';
3
+ }