@steve31415/baselib 2.4.0 → 2.4.2

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.
@@ -263,8 +263,27 @@ export async function runDeploy(options) {
263
263
  if (!newRevision || newRevision === current.revision) {
264
264
  throw new Error(`${service.name}: expected a new revision, got ${newRevision || 'none'}`);
265
265
  }
266
- if (after.status?.latestReadyRevisionName !== newRevision) {
267
- throw new Error(`${service.name}: revision ${newRevision} is not ready`);
266
+ // On a traffic-pinned service, `services update` can return before the
267
+ // 0%-traffic revision reports Ready poll the revision itself.
268
+ let ready = false;
269
+ let lastCondition = '';
270
+ for (let attempt = 0; attempt < 60; attempt += 1) {
271
+ const revision = await mustJson(runner, 'gcloud', [
272
+ 'run', 'revisions', 'describe', newRevision,
273
+ ...gcloudBase, '--region', config.region, '--format=json',
274
+ ]);
275
+ const condition = (revision.status?.conditions ?? []).find((c) => c.type === 'Ready');
276
+ if (condition?.status === 'True') {
277
+ ready = true;
278
+ break;
279
+ }
280
+ lastCondition = condition?.message ?? condition?.status ?? 'unknown';
281
+ if (condition?.status === 'False')
282
+ break; // terminal failure — stop polling
283
+ await sleep(2000);
284
+ }
285
+ if (!ready) {
286
+ throw new Error(`${service.name}: revision ${newRevision} is not ready (${lastCondition})`);
268
287
  }
269
288
  await must(runner, 'gcloud', [
270
289
  'run', 'services', 'update-traffic', service.name,
@@ -378,9 +397,11 @@ export async function runDeploy(options) {
378
397
  })),
379
398
  timingsMs: timer.timings,
380
399
  });
381
- if (hold && !hold.heldShas.includes(sha)) {
400
+ if (hold) {
401
+ // A successful deploy clears any hold: either a different SHA shipped
402
+ // (the fix landed) or the operator deliberately overrode the hold.
382
403
  await clearHold(runner, holdUri);
383
- log('cleared rollback hold (a newer build deployed successfully)');
404
+ log('cleared rollback hold');
384
405
  }
385
406
  log(`deployed ${sha.slice(0, 12)} (${record})`);
386
407
  log(`timings:\n${timer.table()}`);
@@ -141,7 +141,8 @@ export function releaseEntriesFrom(rows, prefix) {
141
141
  return [];
142
142
  return rows.flatMap((row) => {
143
143
  const r = row;
144
- const url = r.url ?? '';
144
+ // `gcloud storage ls --json` appends `#<generation>` to object URLs.
145
+ const url = (r.url ?? '').replace(/#\d+$/, '');
145
146
  const name = url.slice(url.lastIndexOf('/') + 1);
146
147
  const sha = name.endsWith('.json') ? name.slice(0, -5) : '';
147
148
  if (!SHA40.test(sha) || !url.includes(prefix))
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@steve31415/baselib",
3
- "version": "2.4.0",
3
+ "version": "2.4.2",
4
4
  "description": "Plasticine new-world shared platform library: logging, auth, service-to-service auth, db, HTTP, sync, app updates",
5
5
  "type": "module",
6
6
  "license": "MIT",