create-windy 0.3.7 → 0.3.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.js CHANGED
@@ -2767,6 +2767,34 @@ function isDirectoryNotRemovable(error) {
2767
2767
  // src/workspace-membership.ts
2768
2768
  import { readdir as readdir2 } from "fs/promises";
2769
2769
  import { join as join5 } from "path";
2770
+ function deriveFinalWorkspaceMembership(current, target, files) {
2771
+ const membersByBase = new Map;
2772
+ for (const expectation of [...current, ...target]) {
2773
+ if (!membersByBase.has(expectation.base)) {
2774
+ membersByBase.set(expectation.base, new Set);
2775
+ }
2776
+ }
2777
+ for (const expectation of current) {
2778
+ const members = membersByBase.get(expectation.base);
2779
+ for (const path of expectation.members)
2780
+ members.add(path);
2781
+ }
2782
+ for (const file of files) {
2783
+ for (const [base, members] of membersByBase) {
2784
+ if (!isDirectWorkspaceManifest(base, file.path))
2785
+ continue;
2786
+ if (file.action === "delete")
2787
+ members.delete(file.path);
2788
+ if (file.action === "create" || file.action === "update") {
2789
+ members.add(file.path);
2790
+ }
2791
+ }
2792
+ }
2793
+ return [...membersByBase].sort(([left], [right]) => left.localeCompare(right)).map(([base, members]) => ({
2794
+ base,
2795
+ members: [...members].sort((left, right) => left.localeCompare(right))
2796
+ }));
2797
+ }
2770
2798
  async function snapshotWorkspaceBase(root, base) {
2771
2799
  assertSafeWorkspaceBase(base);
2772
2800
  await inspectSafePath(root, base);
@@ -2808,6 +2836,14 @@ function assertSafeWorkspaceBase(base) {
2808
2836
  throw new Error(`workspace \u4E0D\u5F97\u904D\u5386 node_modules\uFF1A${base}`);
2809
2837
  }
2810
2838
  }
2839
+ function isDirectWorkspaceManifest(base, path) {
2840
+ const prefix = `${base}/`;
2841
+ if (!path.startsWith(prefix))
2842
+ return false;
2843
+ const relative3 = path.slice(prefix.length);
2844
+ const segments = relative3.split("/");
2845
+ return segments.length === 2 && segments[0]?.length > 0 && segments[1] === "package.json";
2846
+ }
2811
2847
  function isMissing(error) {
2812
2848
  return error instanceof Error && "code" in error && error.code === "ENOENT";
2813
2849
  }
@@ -8698,7 +8734,7 @@ async function planFile(path2, baseRoot, targetRoot, source, target, ours, prove
8698
8734
  if (manageGeneratedProjectOwned) {
8699
8735
  return planGeneratedProjectOwned(path2, source, target, ours, theirs, expected);
8700
8736
  }
8701
- return !source && !ours && theirs ? readyPlannedFile(path2, ownership, "create", "\u65B0\u589E\u9879\u76EE\u6269\u5C55\u70B9", expected, theirs) : readyPlannedFile(path2, ownership, "preserve", "\u9879\u76EE\u62E5\u6709\uFF0CWindy \u4E0D\u8986\u76D6", expected);
8737
+ return !source && !ours && theirs ? readyPlannedFile(path2, ownership, "create", "\u65B0\u589E\u9879\u76EE\u6269\u5C55\u70B9", expected, theirs) : readyPlannedFile(path2, ownership, "preserve", "\u9ED8\u8BA4\u4FDD\u7559\u9879\u76EE\u7248\u672C", expected);
8702
8738
  }
8703
8739
  const repaired = ours && theirs ? repairKnownDerivedFile({
8704
8740
  path: path2,
@@ -8736,12 +8772,17 @@ async function planFile(path2, baseRoot, targetRoot, source, target, ours, prove
8736
8772
  const oursChanged = hashContent(ours) !== source.hash;
8737
8773
  const sourceArtifactHash = artifactHashOf(source);
8738
8774
  const targetChanged = targetChangedSinceBase(sourceArtifactHash, base, theirs);
8739
- if (shouldForcePlatformBaseline({
8775
+ const forceTargetBaseline = shouldForcePlatformBaseline({
8740
8776
  forcePlatformBaseline,
8741
8777
  oursChanged,
8742
8778
  sourceArtifactHash,
8743
8779
  base
8744
- })) {
8780
+ });
8781
+ if (forceTargetBaseline && path2.endsWith("package.json") && base) {
8782
+ const merged = mergePackageJson(base, ours, theirs);
8783
+ return merged.content ? readyPlannedFile(path2, ownership, "update", "package.json \u5B57\u6BB5\u7EA7\u5408\u5E76", expected, merged.content) : conflict2(path2, ownership, `\u5B57\u6BB5\u51B2\u7A81\uFF1A${merged.conflicts.join("\u3001")}`, expected);
8784
+ }
8785
+ if (forceTargetBaseline) {
8745
8786
  return readyPlannedFile(path2, ownership, "update", "\u5F3A\u5236\u91C7\u7528\u76EE\u6807\u5E73\u53F0\u57FA\u7EBF", expected, theirs);
8746
8787
  }
8747
8788
  if (!oursChanged && !targetChanged) {
@@ -8760,7 +8801,7 @@ async function planFile(path2, baseRoot, targetRoot, source, target, ours, prove
8760
8801
  const merged = mergePackageJson(base, ours, theirs);
8761
8802
  return merged.content ? readyPlannedFile(path2, ownership, "update", "package.json \u5B57\u6BB5\u7EA7\u5408\u5E76", expected, merged.content) : conflict2(path2, ownership, `\u5B57\u6BB5\u51B2\u7A81\uFF1A${merged.conflicts.join("\u3001")}`, expected);
8762
8803
  }
8763
- if (ownership === "shared-scaffold" && base) {
8804
+ if (base) {
8764
8805
  const merged = await mergeTextFile(base, ours, theirs);
8765
8806
  return merged.content ? readyPlannedFile(path2, ownership, "update", "\u4E09\u65B9\u5408\u5E76", expected, merged.content) : conflict2(path2, ownership, merged.conflict || "\u4E09\u65B9\u5408\u5E76\u5931\u8D25", expected);
8766
8807
  }
@@ -8971,7 +9012,9 @@ var recipes = [
8971
9012
  { id: "starter-0.3.3-to-0.3.4", from: "0.3.3", to: "0.3.4" },
8972
9013
  { id: "starter-0.3.4-to-0.3.5", from: "0.3.4", to: "0.3.5" },
8973
9014
  { id: "starter-0.3.5-to-0.3.6", from: "0.3.5", to: "0.3.6" },
8974
- { id: "starter-0.3.6-to-0.3.7", from: "0.3.6", to: "0.3.7" }
9015
+ { id: "starter-0.3.6-to-0.3.7", from: "0.3.6", to: "0.3.7" },
9016
+ { id: "starter-0.3.7-to-0.3.8", from: "0.3.7", to: "0.3.8" },
9017
+ { id: "starter-0.3.8-to-0.3.9", from: "0.3.8", to: "0.3.9" }
8975
9018
  ];
8976
9019
  function resolveRecipeChain(sourceVersion, targetVersion) {
8977
9020
  if (sourceVersion === targetVersion)
@@ -9118,7 +9161,7 @@ async function createUpdatePlan(request, artifacts) {
9118
9161
  files,
9119
9162
  dependencyExpectations,
9120
9163
  workspaceMembershipExpectations: workspaceSnapshot.membershipExpectations,
9121
- finalWorkspaceMembershipExpectations: targetWorkspaceSnapshot.membershipExpectations,
9164
+ finalWorkspaceMembershipExpectations: deriveFinalWorkspaceMembership(workspaceSnapshot.membershipExpectations, targetWorkspaceSnapshot.membershipExpectations, files),
9122
9165
  conflicts,
9123
9166
  detachedToolchain,
9124
9167
  targetProvenance,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-windy",
3
- "version": "0.3.7",
3
+ "version": "0.3.9",
4
4
  "description": "创建单组织、单租户、私有部署优先的 Windy 企业 Dashboard Starter",
5
5
  "type": "module",
6
6
  "bin": {
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "schemaVersion": 1,
3
- "templateCommit": "fca8f541b8d5593ff4e69daf665624ba131eb3e5",
4
- "generatorVersion": "0.3.7",
3
+ "templateCommit": "fe9c5197b083b0d4ff03f9550043d96a392992a1",
4
+ "generatorVersion": "0.3.9",
5
5
  "modules": [
6
6
  {
7
7
  "name": "system",
@@ -31,26 +31,30 @@
31
31
  - 这是 Starter 的初始配置;项目所有者可按团队需要保留、替换或扩展。
32
32
  - 实际可用命令和提交检查以当前项目的 `package.json` 与 Git hooks 为准。
33
33
 
34
- ## Windy 升级边界
34
+ ## Windy 升级策略
35
35
 
36
- - 业务需求优先通过自有模块和既有扩展点实现,尽量不要直接修改 Windy 提供的平台核心、
37
- Composition Root、共享脚手架和根工具链配置,以减少后续升级冲突。
38
- - 修改前先查看 `.windy/files.json` 的 ownership;优先扩展 `project-owned` 路径,
39
- 对 `windy-managed` 路径仅在没有可用扩展点时做最小改动。
40
- - 确需修改 Windy 受管代码时,使用独立小提交记录原因和影响;升级前先运行
36
+ - 除 `node_modules` 等依赖产物外,生成到仓库中的源码都归项目所有者所有,可以按需
37
+ 修改、替换或删除。`.windy/files.json` 的 ownership 是兼容字段名,只表示 updater
38
+ 的默认合并策略和冲突风险,不是源码权限控制。
39
+ - 业务需求优先通过自有模块和既有扩展点实现;直接修改平台核心、Composition Root、
40
+ 共享脚手架或根工具链同样受支持,但通常会增加后续三方合并成本。
41
+ - 修改前可查看 ownership 评估升级风险;优先扩展 `project-owned` 路径,对
42
+ `windy-managed` 路径建议保持改动小而清晰。
43
+ - 直接修改 Windy 基线代码时,使用独立小提交记录原因和影响;升级前先运行
41
44
  `bun run windy update --dry-run`,根据三方合并计划处理冲突。
42
45
  - 完整定制登录页时,在 project-owned 的
43
- `apps/web/src/app/auth/login-page.ts` 注册业务组件;不要修改
44
- `apps/web/src/pages/auth/LoginPage.vue` 或 Router。业务页面复用
46
+ `apps/web/src/app/auth/login-page.ts` 注册业务组件可获得最低升级成本。若直接修改
47
+ `apps/web/src/pages/auth/LoginPage.vue` 或 Router,升级器会尝试三方合并。业务页面复用
45
48
  `useLoginFlow`、`DevelopmentAuthWarning` 和平台品牌设置,保留安全
46
49
  `returnTo`、真实认证与开发认证提示。
47
- - 定制 404、500、维护中或网络异常页时,只修改 project-owned 的
50
+ - 定制 404、500、维护中或网络异常页时,优先修改 project-owned 的
48
51
  `apps/web/src/app/error-pages.ts`,并把业务 SFC 放在 `apps/web/src/app/`;
49
- 保留四个类型化注册项,不要为换视觉修改 Router、HTTP 核心或平台默认错误页。
52
+ 直接修改 Router、HTTP 核心或平台默认错误页时会增加三方合并成本。
50
53
  - 新增业务管理页面时,在业务 Module Manifest 注册 Feature、Permission、菜单和
51
54
  Admin Route,再把 Vue 页面绑定到 project-owned 的
52
- `apps/web/src/app/business-routes.ts`;不要修改 Router 或 AppSidebar。导航来自
53
- 服务端 Manifest 快照,接入见 `docs/development/business-web-routes.md`。
55
+ `apps/web/src/app/business-routes.ts` 是推荐接入方式。直接修改 Router 或 AppSidebar
56
+ 时同样按 Base/Ours/Theirs 合并。导航来自服务端 Manifest 快照,接入见
57
+ `docs/development/business-web-routes.md`。
54
58
  - 业务 Agent Operation 开启 Provider 出网时,必须在 Manifest 同时声明最小
55
59
  `providerDataPolicy.inputFields` JSON Pointer allowlist 与
56
60
  `envelopeFields`;raw input 会在进入 `prepare` 前裁剪并执行 DLP。接入与升级
@@ -9,8 +9,9 @@ apps/web/src/app/error-pages.ts
9
9
 
10
10
  该文件在 `.windy/files.json` 中属于 `project-owned`。Windy 升级会给尚无此文件的
11
11
  项目创建默认选择器;文件存在后,后续更新只保留业务选择。平台默认页面
12
- `apps/web/src/pages/errors/PlatformErrorPage.vue` 属于 `windy-managed`,Router 和
13
- 全局错误导航属于 `shared-scaffold`,业务项目不应为换视觉而修改这些文件。
12
+ `apps/web/src/pages/errors/PlatformErrorPage.vue` 标记为 `windy-managed`,Router 和
13
+ 全局错误导航标记为 `shared-scaffold`。优先使用 project-owned 接缝可降低升级合并
14
+ 成本;项目仍可直接修改这些文件,updater 会按 Base/Ours/Theirs 尝试合并。
14
15
 
15
16
  ## 默认行为
16
17
 
@@ -8,8 +8,9 @@ apps/web/src/app/auth/login-page.ts
8
8
 
9
9
  该文件在 `.windy/files.json` 中属于 `project-owned`。Windy 升级会为旧项目新增它,
10
10
  但一旦文件存在,后续 `windy update` 只会保留,不会覆盖业务选择。平台默认登录页
11
- `apps/web/src/pages/auth/LoginPage.vue` 仍是 `windy-managed`,Router 仍是
12
- `shared-scaffold`;业务项目不应直接修改这两处。
11
+ `apps/web/src/pages/auth/LoginPage.vue` 标记为 `windy-managed`,Router 标记为
12
+ `shared-scaffold`。优先使用 project-owned 接缝可降低升级合并成本;业务项目仍可直接
13
+ 修改这两处,updater 会按 Base/Ours/Theirs 尝试合并。
13
14
 
14
15
  ## 默认行为
15
16