更新摘要锚点支持 CI 兜底
Project CI / AI game creator shell Rust shard 1/4 (push) Has been cancelled
Project CI / AI game creator shell Rust shard 2/4 (push) Has been cancelled
Project CI / AI game creator shell Rust shard 3/4 (push) Has been cancelled
Project CI / AI game creator shell Rust shard 4/4 (push) Has been cancelled
Project CI / AI game creator shell Rust smoke (push) Has been cancelled
Project CI / AI game creator shell Rust crates (push) Has been cancelled
Project CI / Backend tests (push) Has been cancelled
Project CI / Native shell tests (push) Has been cancelled
Project CI / Frontend tests (push) Has been cancelled
Project CI / Repository checks (push) Has been cancelled
Project CI / AI game creator shell web tests (push) Has been cancelled

- 摘要锚点优先取渠道清单 commit,缺失时回退 CI 传入的上一次成功构建 COMMIT_HASH
- Jenkins 构建阶段解析上一次成功构建的 COMMIT_HASH 并注入 AGC_UPDATE_PREVIOUS_COMMIT,读取失败保持为空
- 新增锚点优先级与非法值忽略的定向用例
- 技术方案补充锚点兜底说明
This commit is contained in:
kdletters
2026-09-17 19:42:10 +08:00
parent 5ccc46ac1a
commit e146859ea2
4 changed files with 66 additions and 1 deletions
@@ -196,9 +196,21 @@ async function readRemoteChannelManifest(channel = resolveReleaseChannel()) {
return fetchManifest(updateManifestUrl(channel), 'OSS 渠道清单');
}
/**
* 摘要锚点:上次发布对应的提交。
*
* 首选渠道清单里的 `commit`(发布产物自己的事实来源);清单缺该字段时(首次启用
* 摘要、或更换渠道后清单还没带过 commit)回退到 CI 传入的 `AGC_UPDATE_PREVIOUS_COMMIT`
* —— 它是上一次成功构建的 COMMIT_HASH,同样指向用户拿到的那个版本。
*/
export async function resolvePreviousReleaseCommit(
channel = resolveReleaseChannel(),
{ override = process.env.AGC_UPDATE_PREVIOUS_COMMIT } = {},
) {
const explicit = override?.trim();
if (explicit && /^[0-9a-f]{7,40}$/u.test(explicit)) {
return explicit;
}
const manifest = await readRemoteChannelManifest(channel);
const commit =
typeof manifest?.commit === 'string' ? manifest.commit.trim() : '';
@@ -22,6 +22,7 @@ import {
formatReleaseNotes,
nextPatchVersion,
resolveManifestPlatformKeys,
resolvePreviousReleaseCommit,
resolveReleaseChannel,
resolveRemoteHighWaterVersion,
selectReleaseArtifact,
@@ -241,6 +242,41 @@ test('version high water ignores the windows migration pointer for other channel
);
});
test('release notes anchor prefers the explicit commit and falls back to the manifest', async () => {
await withStubbedFetch(
() => jsonResponse({ version: '0.1.61', commit: 'abcdef1234567890' }),
async () => {
assert.equal(
await resolvePreviousReleaseCommit('dev-win', {
override: '6017d46088c04199e99cf89f347b12d67591475e',
}),
'6017d46088c04199e99cf89f347b12d67591475e',
);
// 覆盖值非法时忽略,继续用清单里的 commit。
assert.equal(
await resolvePreviousReleaseCommit('dev-win', {
override: 'not-a-sha',
}),
'abcdef1234567890',
);
assert.equal(
await resolvePreviousReleaseCommit('dev-win', { override: ' ' }),
'abcdef1234567890',
);
},
);
await withStubbedFetch(
() => jsonResponse({ version: '0.1.61' }),
async () => {
assert.equal(
await resolvePreviousReleaseCommit('dev-win', { override: undefined }),
null,
);
},
);
});
test('release upload forces overwrite for artifact, signature and channel pointers', () => {
const source = readFileSync(
new URL('./release-upload.mjs', import.meta.url),