afx-team / afx-team/evjs

0.4: replace resolve slots with environment-scoped module rules

未關閉
#119 0 則留言 0 個 reaction 已指派 0 人 在 GitHub 檢視
主要語言
TypeScript
星號
23
分支
6
平均合併
10 小時 8 分鐘
30 天內合併 PR
27

描述

## Summary

Redesign plugin-owned module aliases and externalization rules for the EVJS 0.4 release.

The current `resolve.alias` and `resolve.external` entries are exposed as `FrameworkSlotName` values even though they are build/module rules rather than framework composition slots. Their client/server behavior is also asymmetric and overlaps with server config and `configureBundler`.

This is intentionally a breaking 0.4 change. Do **not** retain a deprecated adapter or runtime translation for the old slot names.

## Current problems

- `resolve.alias` has no client/server selector and is effectively shared, with `server.resolve.alias` acting as a server override.
- `resolve.external` has `runtime: "client" | "server" | "all"`, although client/server are build environments rather than runtimes.
- Resolve externals are keyed only by specifier, so two plugin contributions cannot express different client and server bindings for the same specifier; the later contribution silently replaces the earlier one.
- Alias and external rules are mixed into `FrameworkSlotName` alongside real composition points such as entries, wrappers, middleware, and HTML tags.
- `configureBundler` can mutate the same bundler fields after BuildPlan projection, but the ownership and precedence rules are not explicit.
- The current `source?: string` external representation is weakly typed and can leak adapter-specific syntax into an otherwise adapter-neutral plan.

## Proposed authoring API

Remove module rules from `ctx.slot()` and introduce a dedicated API:

```ts
ctx.modules.alias({
id: "runtime-config",
specifier: "@plugin/runtime-config",
replacement: generatedModule,
environment: "all",
});

ctx.modules.externalize({
id: "qiankun",
specifier: "qiankun",
environment: "client",
});
```

Requirements:

- Use `environment: "client" | "server" | "all"`; default to `"all"`.
- Keep `GeneratedModuleRef` support for alias replacements.
- Define an adapter-neutral external binding contract instead of passing arbitrary bundler syntax where practical.
- Reserve `ctx.slot()` for actual framework composition points.

## BuildPlan model

Materialize authoring rules into explicit environment-specific plans, for example:

```ts
interface ResolvePlan {
client?: EnvironmentResolvePlan;
server?: EnvironmentResolvePlan;
}

interface EnvironmentResolvePlan {
aliases?: Record;
externals?: Record;
}
```

- Expand `environment: "all"` into both concrete branches during planning.
- Allow the same specifier to have different client and server values.
- Reject conflicting contributions within the same environment instead of silently using plugin order, unless an explicit override mechanism is designed.
- Normalize existing application authoring inputs `server.resolve.alias` and `server.externals` into the server branch. Renaming those application config fields is not required by this issue.
- Document precedence between framework defaults, plugin contributions, application server overrides, and the final adapter-specific `configureBundler` escape hatch.

## Framework analysis

Alias rules are not only bundler configuration: project-local aliases participate in framework static-import closure analysis and PPR/server-function discovery.

The 0.4 implementation must avoid missing framework semantics when client and server aliases differ. Either:

1. analyze client and server source closures separately, or
2. conservatively analyze the union of both alias targets.

Do not implement environment-specific bundler aliases while leaving CoreGraph analysis on an ambiguous single alias map.

## Breaking changes

- Remove `"resolve.alias"` and `"resolve.external"` from `FrameworkSlotName`.
- Remove the corresponding old contribution types and runtime acceptance paths.
- Change the shared BuildPlan contract to the environment-specific representation.
- Do not provide deprecated aliases, compatibility shims, or old-to-new slot translation in 0.4.
- Ensure package peer/dependency ranges reject mixed 0.3/0.4 core, adapter, and plugin combinations.

## Ecosystem migration

Coordinate these known consumers:

- `@evjs/plugin-qiankun`: migrate qiankun externalization to `environment: "client"`.
- `@alipay/evjs` CAPR plugin: migrate the generated prefetch alias; preserve current behavior initially with `environment: "all"`.
- `@alipay/evjs` Tern plugin: upgrade to the migrated qiankun plugin. `externalQiankun` defaults to true.
- `@alipay/evjs` H5 plugin: keep `server.resolve.alias` as application authoring input and verify that it projects only to the server environment.
- Audit third-party plugins and downstream BuildPlan consumers.

## Release coordination

Publish the affected EVJS packages as one 0.4-compatible release train, including at least:

- `@evjs/shared`
- `@evjs/ev`
- `@evjs/bundler-utoopack`
- `@evjs/bundler-webpack`
- `@evjs/cli`
- `@evjs/plugin-qiankun`

Then publish a compatible `@alipay/evjs` release with updated peer/dependency ranges.

## Acceptance criteria

- Client-only, server-only, shared, and different-per-environment aliases are covered.
- Client-only, server-only, shared, and different-per-environment externals are covered.
- Both Utoopack and Webpack consume the same concrete environment plans.
- CoreGraph analysis remains correct with aliased project-local imports.
- Same-environment conflicts produce actionable diagnostics.
- `ev inspect` exposes the final normalized rules.
- Old resolve slot names fail clearly under 0.4.
- English and Chinese plugin/contribution documentation are updated together.
- CAPR, H5, Tern, and qiankun integration tests pass against the coordinated 0.4 package set.

## Validation

```bash
npm run check-types
npm run lint
npm test
git diff --check
```

貢獻指南

開啟貢獻指南

研究方向

Start in `@evjs/shared` and `@evjs/ev`, where `FrameworkSlotName`, `BuildPlan`, and `ctx.slot()`/`ctx.modules` APIs are defined, then trace how `@evjs/bundler-utoopack` and `@evjs/bundler-webpack` consume resolve plans. Inspect plugin entry points (`@evjs/plugin-qiankun`, CAPR/H5/Tern under `@alipay/evjs`) for migration behavior, then run `npm run check-types`, `npm run lint`, `npm test`, and `git diff --check`; done means `ev inspect` shows normalized client/server/all rules, conflicts are rejected, old slot names fail, and migration-related behavior matches the acceptance criteria.

由索引模型根據 Issue 內容生成。

評估

技術堆疊
typescript, webpack
領域
build-system
Issue 類型
重構
難度
5/5
預估耗時
一週以上
活躍度
活躍
描述清晰度
基本清楚
新手友好度
30/100

把新 issue 寄到你的電子郵件信箱

精選適合新手參與的 GitHub issue 摘要。