Skip to content

Commit d7642ac

Browse files
committed
fix(deploy): retry cold playback after purge races
1 parent 66c780a commit d7642ac

1 file changed

Lines changed: 32 additions & 4 deletions

File tree

scripts/playback-readiness-gate.mjs

Lines changed: 32 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@ import { fileURLToPath } from "node:url";
1818
const rootDir = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "..");
1919
const curlTimingFormat =
2020
"http_code=%{http_code}\\ntime_connect=%{time_connect}\\ntime_starttransfer=%{time_starttransfer}\\ntime_total=%{time_total}\\nsize_download=%{size_download}\\nsize_upload=%{size_upload}\\n";
21+
const coldMissPurgeAttempts = 5;
22+
const coldMissRetryDelayMs = 1_000;
2123

2224
const defaultThresholds = {
2325
upload_response_ms: { warn: 5_000, fail: 15_000 },
@@ -709,8 +711,11 @@ async function measurePlayback(config, edge, assetId, artifact, expectedCache, p
709711
throw new SafeError(`${edge.edge_id} ${artifact.label} expected HTTP 200, got ${response.http_code}`);
710712
}
711713
const cache = response.headers.get("x-rend-cache") || "";
712-
if (cache !== expectedCache) {
713-
throw new SafeError(`${edge.edge_id} ${artifact.label} expected X-Rend-Cache ${expectedCache}, got ${cache || "missing"}`);
714+
if (expectedCache) {
715+
const expectedValues = Array.isArray(expectedCache) ? expectedCache : [expectedCache];
716+
if (!expectedValues.includes(cache)) {
717+
throw new SafeError(`${edge.edge_id} ${artifact.label} expected X-Rend-Cache ${expectedValues.join(" or ")}, got ${cache || "missing"}`);
718+
}
714719
}
715720
const contentType = (response.headers.get("content-type") || "").split(";", 1)[0];
716721
if (contentType !== artifact.content_type) {
@@ -734,6 +739,28 @@ async function measurePlayback(config, edge, assetId, artifact, expectedCache, p
734739
};
735740
}
736741

742+
async function purgeAndMeasureColdPlayback(config, edge, assetId, artifact, cookieJar) {
743+
const purgeSummaries = [];
744+
let lastCacheStatus = "";
745+
for (let attempt = 1; attempt <= coldMissPurgeAttempts; attempt += 1) {
746+
purgeSummaries.push(await purgeEdge(config, edge, assetId, [artifact.artifact_path]));
747+
const result = await measurePlayback(config, edge, assetId, artifact, null, "cold_miss", cookieJar);
748+
lastCacheStatus = result.cache_status;
749+
if (result.cache_status === "MISS") {
750+
return { result, purgeSummaries };
751+
}
752+
if (result.cache_status !== "HIT") {
753+
throw new SafeError(`${edge.edge_id} ${artifact.label} expected X-Rend-Cache MISS after purge, got ${result.cache_status || "missing"}`);
754+
}
755+
if (attempt < coldMissPurgeAttempts) {
756+
await sleep(coldMissRetryDelayMs);
757+
}
758+
}
759+
throw new SafeError(`${edge.edge_id} ${artifact.label} expected X-Rend-Cache MISS after purge, got ${lastCacheStatus || "missing"}`, {
760+
purge_attempts: coldMissPurgeAttempts,
761+
});
762+
}
763+
737764
async function fetchEdgeMetrics(config, edge) {
738765
const response = await curlRequest({
739766
method: "GET",
@@ -1073,8 +1100,9 @@ async function runFixture(config, fixtureName, thresholds, warnings, failures, c
10731100
const warmSummaries = [];
10741101
const purgeSummaries = [];
10751102
for (const artifact of artifacts) {
1076-
purgeSummaries.push(await purgeEdge(config, edge, assetId, [artifact.artifact_path]));
1077-
const miss = await measurePlayback(config, edge, assetId, artifact, "MISS", "cold_miss", cookieJar);
1103+
const cold = await purgeAndMeasureColdPlayback(config, edge, assetId, artifact, cookieJar);
1104+
purgeSummaries.push(...cold.purgeSummaries);
1105+
const miss = cold.result;
10781106
miss.fixture = fixtureName;
10791107
edgeResults.push(miss);
10801108
expectedTelemetryEvents += 1;

0 commit comments

Comments
 (0)