@dimina-kit/devtools 0.3.2-dev.20260611135124 → 0.4.0-dev.20260612152115

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 (58) hide show
  1. package/README.md +11 -9
  2. package/dist/main/api.d.ts +1 -1
  3. package/dist/main/app/app.js +22 -12
  4. package/dist/main/app/launch.d.ts +4 -4
  5. package/dist/main/app/launch.js +5 -17
  6. package/dist/main/index.bundle.js +372 -225
  7. package/dist/main/ipc/bridge-router.js +35 -8
  8. package/dist/main/ipc/views.js +10 -1
  9. package/dist/main/menu/index.d.ts +2 -2
  10. package/dist/main/menu/index.js +4 -2
  11. package/dist/main/runtime/miniapp-runtime.d.ts +79 -11
  12. package/dist/main/services/notifications/renderer-notifier.d.ts +11 -0
  13. package/dist/main/services/notifications/renderer-notifier.js +3 -0
  14. package/dist/main/services/views/host-toolbar-port-channel.d.ts +10 -0
  15. package/dist/main/services/views/host-toolbar-port-channel.js +89 -10
  16. package/dist/main/services/views/view-manager.d.ts +28 -4
  17. package/dist/main/services/views/view-manager.js +42 -8
  18. package/dist/main/services/workbench-context.d.ts +7 -0
  19. package/dist/main/services/workbench-context.js +5 -0
  20. package/dist/main/services/workspace/workspace-service.d.ts +3 -7
  21. package/dist/main/services/workspace/workspace-service.js +66 -0
  22. package/dist/main/windows/settings-window/index.d.ts +33 -0
  23. package/dist/main/windows/settings-window/index.js +59 -0
  24. package/dist/preload/index.d.ts +2 -2
  25. package/dist/preload/index.js +2 -2
  26. package/dist/preload/runtime/host-toolbar-port.d.ts +10 -5
  27. package/dist/preload/runtime/host-toolbar-port.js +24 -0
  28. package/dist/preload/windows/host-toolbar-runtime.cjs +20 -1
  29. package/dist/preload/windows/host-toolbar-runtime.cjs.map +2 -2
  30. package/dist/preload/windows/main.cjs +9 -7
  31. package/dist/preload/windows/main.cjs.map +2 -2
  32. package/dist/preload/windows/simulator.cjs.map +1 -1
  33. package/dist/renderer/assets/index-Bi_6SS-L.js +50 -0
  34. package/dist/renderer/assets/{input-6fpCXV-n.js → input-DgqX2UvN.js} +2 -2
  35. package/dist/renderer/assets/{ipc-transport-D22e4dv7.js → ipc-transport-CsFhDJ7q.js} +2 -2
  36. package/dist/renderer/assets/ipc-transport-SnOAk0Jq.css +1 -0
  37. package/dist/renderer/assets/{popover-CdGdKkkc.js → popover-D_2o_52M.js} +2 -2
  38. package/dist/renderer/assets/{select-X0sbjwdP.js → select-BJYsdghn.js} +2 -2
  39. package/dist/renderer/assets/{settings-CS4jYaCw.js → settings-CivkfizP.js} +2 -2
  40. package/dist/renderer/assets/{settings-api-CCWTAao_.js → settings-api-7mXkBy5-.js} +2 -2
  41. package/dist/renderer/assets/{workbenchSettings-Bpzaj3bm.js → workbenchSettings-BwpwxuzM.js} +2 -2
  42. package/dist/renderer/entries/main/index.html +6 -6
  43. package/dist/renderer/entries/popover/index.html +5 -5
  44. package/dist/renderer/entries/settings/index.html +5 -5
  45. package/dist/renderer/entries/workbench-settings/index.html +4 -4
  46. package/dist/shared/ipc-channels.d.ts +11 -0
  47. package/dist/shared/ipc-channels.js +14 -0
  48. package/dist/shared/types.d.ts +48 -11
  49. package/dist/simulator/assets/bridge-channels-BUQ5AbvJ.js +2 -0
  50. package/dist/simulator/assets/device-shell-BEnc2k-W.js +2 -0
  51. package/dist/simulator/assets/{simulator-DHylZf9Z.js → simulator-cV1PERi6.js} +3 -3
  52. package/dist/simulator/assets/simulator-mini-app-CYtW6bMd.js +2 -0
  53. package/dist/simulator/simulator.html +1 -1
  54. package/package.json +4 -4
  55. package/dist/renderer/assets/index-DLzjz1wv.js +0 -50
  56. package/dist/renderer/assets/ipc-transport-Bs8Sf1B2.css +0 -1
  57. package/dist/simulator/assets/device-shell-fH2cI-3q.js +0 -2
  58. package/dist/simulator/assets/simulator-mini-app-BDNu5n26.js +0 -2
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # Dimina DevTools
2
2
 
3
- 基于 Electron 的小程序开发者工具。提供模拟器、Chrome DevTools 面板、WXML/AppData/Storage 面板、编译配置等功能。
3
+ 基于 Electron 的小程序开发者工具。提供模拟器、Chrome DevTools 面板、WXML/AppData/Storage/编译 面板、编译配置等功能。
4
4
 
5
5
  下游 host 通过 `launch(config)` 集成并定制 devtools(零配置直接 `launch()`,配置驱动 `launch({...})`;见下方「两种用法」)。两种用法都经领域中立的 [`@dimina-kit/electron-deck`](../electron-deck) 框架编排——框架接管 Electron 进程生命周期(whenReady / will-quit)、wire/trust 原语,devtools 作为 `RuntimeBackend` 注入完整运行时(见 [`framework-extraction-v2.md`](../electron-deck/docs/framework-extraction-v2.md))。
6
6
 
@@ -147,7 +147,7 @@ src/
147
147
  main.tsx # 主窗口 React 根
148
148
  features/ # 主窗口内的业务区域
149
149
  project-runtime/ # 项目视图 + 工具栏 + 右侧面板切换
150
- right-panel/ # WXML / AppData / Storage 面板
150
+ right-panel/ # WXML / AppData / Storage / 编译 面板
151
151
  popover/ settings/ workbench-settings/
152
152
  shared/
153
153
  components/ # UI 组件(ui / layout / json-viewer / ...)
@@ -177,7 +177,7 @@ src/
177
177
  | ------------------ | -------------------- | ------------------- | ---------------------------------- |
178
178
  | `appName` | `string` | `'Dimina DevTools'` | 窗口标题 |
179
179
  | `adapter` | `CompilationAdapter` | 内置 | 项目编译适配器 |
180
- | `panels` | `BuiltinPanelId[]` | — | **已废弃,运行时忽略**:界面恒显示全部四个内置面板;保留字段仅为兼容仍传它的 host |
180
+ | `panels` | `BuiltinPanelId[]` | — | **已废弃,运行时忽略**:界面恒显示全部内置面板(WXML / AppData / Storage / Console / 编译);保留字段仅为兼容仍传它的 host |
181
181
  | `preloadPath` | `string` | 内置 | 统一的 host 级 preload 入口;native-host simulator(WCV)自动跑其 `.cjs` sibling(`cjsSiblingPreloadPath`) |
182
182
  | `apiNamespaces` | `string[]` | `[]` | 自定义 API 命名空间(如 `['qd']`) |
183
183
  | `brandingProvider` | `() => { appName }` | — | 品牌信息 provider |
@@ -192,7 +192,7 @@ src/
192
192
  | `modules` | `Partial<Record<BuiltinModuleId, boolean>>` | 全部 `true` | 开关内置 IPC 模块组 |
193
193
  | `rendererDir` | `string` | 内置 | 自定义 renderer HTML 目录 |
194
194
  | `icon` | `string` | — | 窗口/任务栏图标路径(macOS 使用 app bundle 图标) |
195
- | `menuBuilder` | `(mainWindow, menuContext: MenuContext) => void` | 内置菜单 | 自定义菜单构建器;`menuContext` 为收窄后的 `MenuContext`,不含 `registry`/`senderPolicy` 等内部管线 |
195
+ | `menuBuilder` | `(mainWindow, menuContext: MenuContext) => void` | 内置菜单 | 自定义菜单构建器;`menuContext` 为手写窄契约 `MenuContext`(`appName` + workspace 窄集 + `openSettings` + `notify.{projectStatus, windowNavigateBack}`),不含内部管线 |
196
196
  | `onSetup` | `(instance) => void` | — | 窗口和 context 创建后的回调,用于注册 Contribution(见下文)|
197
197
  | `onBeforeClose` | `(instance) => void` | — | 窗口关闭前的回调,session 关闭由框架自动处理 |
198
198
  | `window` | `WorkbenchWindowConfig` | — | 窗口尺寸覆盖 |
@@ -483,7 +483,7 @@ launch({
483
483
 
484
484
  ## Host Toolbar(宿主自定义工具栏)
485
485
 
486
- 下游通过 `instance.context.views.hostToolbar` 拥有 devtools 头部下方的工具栏条(一个 WebContentsView):`loadURL` / `loadFile` 加载自己的内容,`setPreloadPath` 注入自己的 preload,`setHeightMode` 钉死或自动跟随内容高度(自动模式要求内容自带 shrink-to-fit 的 `[data-host-toolbar-root]` 包裹元素)。
486
+ 下游通过 `instance.context.views.hostToolbar` 拥有 devtools 头部下方的工具栏条(一个 WebContentsView):`loadURL` / `loadFile` 加载自己的内容,`setPreloadPath` 注入自己的 preload,`setHeightMode` 钉死或自动跟随内容高度(自动模式要求内容自带 shrink-to-fit 的 `[data-host-toolbar-root]` 包裹元素;`{ fixed }` 校验入参——非有限数或负数同步抛 `TypeError` 且不污染既有模式)。主进程保留最后一次下发的高度(`views.getHostToolbarHeight()`),项目视图的占位条挂载时会主动拉取并回放——广播器对已上报的高度去重不再重发,没有这一步,冷启动在项目列表期间的上报、以及关闭项目再打开后的高度都会永久丢失(工具栏条塌缩为 0)。
487
487
 
488
488
  ### 双向消息:onMessage / send
489
489
 
@@ -491,8 +491,9 @@ launch({
491
491
 
492
492
  - `hostToolbar.onMessage(channel, handler): { dispose() }` — 接收页面消息。控制面级注册:可在 view 创建前调用,且跨页面 reload 自动续接,无需重新注册。空串/非 string channel 抛错。
493
493
  - `hostToolbar.send(channel, payload): boolean` — 发消息给页面。门控不排队:没有活的工具栏 webContents、本次 load 的握手未完成、或正处于换文档导航窗口期(`loadURL`/`loadFile` 发起后、以及页面自发的主框架跨文档导航开始后,直到新文档握手完成)时返回 `false`(不投递、不建 view);返回 `true` 即已发出。返回值本身就是就绪信号,下游不再需要拿 `getHostToolbarWebContentsId()` 手工判断工具栏是否就绪(该 API 保留)。
494
+ - `hostToolbar.onReady(handler): { dispose() }` — 握手完成的推送信号(每个 load generation fire 一次;已就绪后注册在微任务上补发一次,补发前复查订阅与 generation)。在 handler 内 `send()` 必然返回 `true`,可用于推送初始状态,替代轮询 retry loop。
494
495
 
495
- 页面侧由框架自动注入 `window.diminaHostToolbar`(仅 `{ send, onMessage }` 两个函数;握手前的 `send` 进队列、握手后按序送达。队列上限 128 条:超限丢弃最新一条、首次超限 console.warn 一次,不抛错):
496
+ 页面侧由框架自动注入 `window.diminaHostToolbar`(仅 `{ send, onMessage }` 两个函数;类型可从根入口导入 `DiminaHostToolbarPageBridge`,并附带 optional 的 `Window` 增强。握手前的 `send` 进队列、握手后按序送达。队列上限 128 条:超限丢弃最新一条、首次超限 console.warn 一次,不抛错。`send`/`onMessage` 对空串/非 string channel 同步抛 `TypeError`,与主进程同语义):
496
497
 
497
498
  ```js
498
499
  // 工具栏页面内
@@ -515,7 +516,8 @@ instance.context.views.hostToolbar.send('host:cmd', { theme: 'dark' }) // false
515
516
  ```
516
517
  @dimina-kit/devtools launch, buildDefaultMenu,
517
518
  openSettingsWindow, suppressEpipe, setupCdpPort,
518
- asMiniappRuntime, MiniappRuntime(type),
519
+ asMiniappRuntime, MiniappRuntime / MiniappSessionAppInfo /
520
+ DiminaHostToolbarPageBridge(type),
519
521
  createWorkbenchContext, createMainWindow,
520
522
  createViewManager, IpcRegistry,
521
523
  UpdateManager, createGitHubReleaseChecker, ...
@@ -556,11 +558,11 @@ runtime.views.hostToolbar.send('host:cmd', { theme: 'dark' })
556
558
  runtime.notify.projectStatus({ status: 'ready', message: '编译完成' })
557
559
  ```
558
560
 
559
- 契约面:`rendererDir` / `views.hostToolbar`(6 成员,无 `webContents`)/ `workspace`(7 方法)/ `notify.projectStatus` / `registry.add` / `windows`(不透明句柄)。零 Electron 类型。
561
+ 契约面:`views.hostToolbar`(7 成员,含 `onReady`,无 `webContents`)/ `workspace`(7 方法,`getSession().appInfo` 为结构化 `MiniappSessionAppInfo`,`appId` 必有)/ `notify.projectStatus` / `registry.add`(接受 `{ dispose }` 对象或裸函数两种习语)/ `openSettings()`。零 Electron 类型。0.4.0 起不再含 `rendererDir`(用 `/paths` 导出)与 `windows`(用 `openSettings()`)。
560
562
 
561
563
  ## WorkbenchContext
562
564
 
563
- `WorkbenchContext` 是所有扩展点的唯一容器。配置字段直接暴露,运行时状态通过 service 访问。host hook 拿到的 `instance.context` 即此类型;`menuBuilder` 拿到的是收窄后的 `MenuContext`(剔除 `registry` / `senderPolicy` / `trustedWindowSenderIds` / `simulatorApis` 等内部管线)。
565
+ `WorkbenchContext` 是所有扩展点的唯一容器。配置字段直接暴露,运行时状态通过 service 访问。host hook 拿到的 `instance.context` 即此类型;`menuBuilder` 拿到的是手写窄契约 `MenuContext`(`appName` + workspace 窄集 + `openSettings` + `notify.{projectStatus, windowNavigateBack}`,不再是 `WorkbenchContext` 的 Omit 投影)。
564
566
 
565
567
  ```typescript
566
568
  interface WorkbenchContext {
@@ -2,7 +2,7 @@ export { launch, buildDefaultMenu, openSettingsWindow } from './app/launch.js';
2
2
  export type { WorkbenchAppInstance } from './app/app.js';
3
3
  export { suppressEpipe, setupCdpPort } from './app/bootstrap.js';
4
4
  export { asMiniappRuntime } from './runtime/miniapp-runtime.js';
5
- export type { MiniappRuntime } from './runtime/miniapp-runtime.js';
5
+ export type { MiniappRuntime, MiniappSessionAppInfo, DiminaHostToolbarPageBridge, } from './runtime/miniapp-runtime.js';
6
6
  export { createWorkbenchContext } from './services/workbench-context.js';
7
7
  export type { WorkbenchContext, CreateContextOptions } from './services/workbench-context.js';
8
8
  export { createMainWindow } from './windows/main-window/index.js';
@@ -6,6 +6,7 @@ import path from 'path';
6
6
  import { rendererDir as defaultRendererDir, defaultPreloadPath } from '../utils/paths.js';
7
7
  import { installThemeBackgroundSync } from '../utils/theme.js';
8
8
  import { createMainWindow, wireMainWindowEvents } from '../windows/main-window/index.js';
9
+ // eslint-disable-next-line no-restricted-syntax -- grandfathered(workbench-context): shrink-only
9
10
  import { createWorkbenchContext } from '../services/workbench-context.js';
10
11
  import { loadWorkbenchSettings, applyTheme } from '../services/settings/index.js';
11
12
  import { installAppMenu } from '../menu/index.js';
@@ -166,20 +167,29 @@ function registerBuiltinModules(config, context) {
166
167
  });
167
168
  }
168
169
  /**
169
- * Strip the internal-plumbing fields a host menu builder must not reach
170
- * (registry / senderPolicy / trustedWindowSenderIds / simulatorApis)
171
- * so `menuBuilder` receives the narrowed `MenuContext` its contract promises
172
- * at runtime, not just at the type level.
170
+ * Build the hand-written narrow `MenuContext` a host menu builder receives
171
+ * explicit construction (not clone+delete), so the runtime object carries
172
+ * EXACTLY the contract members and nothing else. Every member is a lazy
173
+ * closure over the live context: a host monkey-patch of
174
+ * `context.workspace.openProject` (the documented permission-gate pattern)
175
+ * still intercepts calls made through this menu surface.
173
176
  */
174
177
  function toMenuContext(context) {
175
- // Shallow-copy, then drop the internal-plumbing fields. A rest-destructure
176
- // would be terser but trips no-unused-vars on the dropped siblings.
177
- const menuContext = { ...context };
178
- delete menuContext.registry;
179
- delete menuContext.senderPolicy;
180
- delete menuContext.trustedWindowSenderIds;
181
- delete menuContext.simulatorApis;
182
- return menuContext;
178
+ return {
179
+ appName: context.appName,
180
+ workspace: {
181
+ hasActiveSession: () => context.workspace.hasActiveSession(),
182
+ getProjectPath: () => context.workspace.getProjectPath(),
183
+ openProject: (projectPath) => context.workspace.openProject(projectPath),
184
+ closeProject: () => context.workspace.closeProject(),
185
+ getSession: () => context.workspace.getSession(),
186
+ },
187
+ openSettings: () => context.openSettings(),
188
+ notify: {
189
+ projectStatus: (payload) => context.notify.projectStatus(payload),
190
+ windowNavigateBack: () => context.notify.windowNavigateBack(),
191
+ },
192
+ };
183
193
  }
184
194
  function installMenu(config, mainWindow, context) {
185
195
  // Menu: use host-provided builder or fall back to default
@@ -1,5 +1,4 @@
1
- import type { WorkbenchAppConfig } from '../../shared/types.js';
2
- import type { WorkbenchContext } from '../services/workbench-context.js';
1
+ import type { MenuContext, WorkbenchAppConfig } from '../../shared/types.js';
3
2
  /**
4
3
  * Host-shell entry for the devtools app. Boots through the
5
4
  * `@dimina-kit/electron-deck` framework orchestrator (process lifecycle gate +
@@ -9,6 +8,7 @@ import type { WorkbenchContext } from '../services/workbench-context.js';
9
8
  * passing `WorkbenchAppConfig` (incl. `onSetup`, `apiNamespaces`, `menuBuilder`, …).
10
9
  */
11
10
  export declare function launch(config?: WorkbenchAppConfig): Promise<void>;
12
- export declare function buildDefaultMenu(ctx: WorkbenchContext): void;
13
- export declare function openSettingsWindow(ctx: Pick<WorkbenchContext, 'rendererDir' | 'notify' | 'windows'>): Promise<void>;
11
+ export declare function buildDefaultMenu(ctx: MenuContext): void;
12
+ export { openSettingsWindow } from '../windows/settings-window/index.js';
13
+ export type { OpenSettingsWindowDeps } from '../windows/settings-window/index.js';
14
14
  //# sourceMappingURL=launch.d.ts.map
@@ -1,8 +1,6 @@
1
1
  import { electronDeck as frameworkElectronDeck } from '@dimina-kit/electron-deck';
2
2
  import { createDevtoolsBackend } from '../runtime/devtools-backend.js';
3
3
  import { installAppMenu } from '../menu/index.js';
4
- import { createSettingsWindow, wireSettingsWindowEvents } from '../windows/settings-window/index.js';
5
- import { loadWorkbenchSettings } from '../services/settings/index.js';
6
4
  /**
7
5
  * Host-shell entry for the devtools app. Boots through the
8
6
  * `@dimina-kit/electron-deck` framework orchestrator (process lifecycle gate +
@@ -17,19 +15,9 @@ export function launch(config = {}) {
17
15
  export function buildDefaultMenu(ctx) {
18
16
  installAppMenu(ctx);
19
17
  }
20
- export async function openSettingsWindow(ctx) {
21
- let win = ctx.windows.settingsWindow;
22
- if (!win || win.isDestroyed()) {
23
- win = await createSettingsWindow(ctx.windows.mainWindow, ctx.rendererDir);
24
- ctx.windows.setSettingsWindow(win);
25
- wireSettingsWindowEvents(win, () => {
26
- ctx.windows.setSettingsWindow(null);
27
- });
28
- }
29
- win.show();
30
- win.focus();
31
- ctx.notify.workbenchSettingsInit(win, {
32
- settings: loadWorkbenchSettings(),
33
- });
34
- }
18
+ // The implementation lives with the settings-window domain module and takes
19
+ // its own narrow `OpenSettingsWindowDeps` (a full WorkbenchContext satisfies
20
+ // it structurally). Re-exported here so the public barrel path is unchanged.
21
+ // Contract holders should prefer `ctx.openSettings()` / `runtime.openSettings()`.
22
+ export { openSettingsWindow } from '../windows/settings-window/index.js';
35
23
  //# sourceMappingURL=launch.js.map