Skip to content

Commit eebf332

Browse files
committed
fix: keep default release when latest has no compatible SKU artifact
After the getDefaultRelease SKU-compat fix, the default path was graceful but the rollout-upgrade path stayed strict: if a device was in the rollout bucket and the latest release lacked a compatible artifact for the requested SKU, dbReleaseToMetadata still threw and 404'd the whole request — even though responseJson already held a valid default. Short-circuit the upgrade when the latest release has no compatible artifact and update the regression test to assert the default is kept instead of asserting the throw.
1 parent 68b1000 commit eebf332

2 files changed

Lines changed: 29 additions & 16 deletions

File tree

src/releases.ts

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -617,26 +617,30 @@ export async function Retrieve(req: Request, res: Response) {
617617

618618
// Background update checks follow rollout percentages so new releases roll
619619
// out gradually. Devices outside the bucket fall back to the default (the
620-
// newest 100%-rolled-out release).
620+
// newest 100%-rolled-out release). If the latest release lacks a compatible
621+
// artifact for this SKU (e.g. a SKU-specific build hasn't shipped yet) we
622+
// silently keep the default rather than 404 the whole request.
621623
const responseJson = toRelease(
622624
dbReleaseToMetadata(defaultAppRelease, query.sku),
623625
dbReleaseToMetadata(defaultSystemRelease, query.sku),
624626
);
625627

626628
if (
627-
await isDeviceEligibleForLatestRelease(
629+
latestAppRelease.artifacts.length > 0 &&
630+
(await isDeviceEligibleForLatestRelease(
628631
latestAppRelease.rolloutPercentage,
629632
query.deviceId,
630-
)
633+
))
631634
) {
632635
setAppRelease(responseJson, dbReleaseToMetadata(latestAppRelease, query.sku));
633636
}
634637

635638
if (
636-
await isDeviceEligibleForLatestRelease(
639+
latestSystemRelease.artifacts.length > 0 &&
640+
(await isDeviceEligibleForLatestRelease(
637641
latestSystemRelease.rolloutPercentage,
638642
query.deviceId,
639-
)
643+
))
640644
) {
641645
setSystemRelease(responseJson, dbReleaseToMetadata(latestSystemRelease, query.sku));
642646
}

test/releases.test.ts

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -489,7 +489,7 @@ describe("Retrieve handler", () => {
489489
});
490490
});
491491

492-
it("does not fall back when the latest release lacks a compatible artifact", async () => {
492+
it("keeps the default when the latest release lacks a compatible artifact for an in-bucket device", async () => {
493493
await createDbRelease("app", "3.3.0", 100, [
494494
{
495495
...releaseArtifact("app", "3.3.0", DEFAULT_SKU),
@@ -506,19 +506,28 @@ describe("Retrieve handler", () => {
506506
releaseArtifact("system", "3.3.0", DEFAULT_SKU, "system-default-hash"),
507507
releaseArtifact("system", "3.3.0", SDMMC_SKU, "system-sdmmc-hash"),
508508
]);
509+
// system 3.3.1 ships only with the default-SKU artifact — no sdmmc binary.
509510
await createDbRelease("system", "3.3.1", 100);
510511

511-
await expect(
512-
Retrieve(
513-
createMockRequest({
514-
deviceId: "sdmmc-compatible-fallback-device",
515-
sku: SDMMC_SKU,
516-
}),
517-
createMockResponse(),
518-
),
519-
).rejects.toThrow(
520-
'Version 3.3.1 predates SKU support and cannot serve SKU "jetkvm-v2-sdmmc"',
512+
// Every device is in-bucket at 100% rollout, so this exercises the
513+
// upgrade path. The request must keep the default 3.3.0 system release
514+
// rather than 404 because 3.3.1 has no sdmmc binary.
515+
const res = createMockResponse();
516+
await Retrieve(
517+
createMockRequest({
518+
deviceId: "sdmmc-compatible-fallback-device",
519+
sku: SDMMC_SKU,
520+
}),
521+
res,
521522
);
523+
524+
expect(jsonBody(res)).toMatchObject({
525+
appVersion: "3.3.1",
526+
appUrl: artifactUrl("app", "3.3.1"),
527+
systemVersion: "3.3.0",
528+
systemUrl: artifactUrl("system", "3.3.0", SDMMC_SKU),
529+
systemHash: "system-sdmmc-hash",
530+
});
522531
});
523532

524533
it("does not discover or create stable releases from S3", async () => {

0 commit comments

Comments
 (0)