@biffo/cli 0.210.0 → 0.211.1

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.
@@ -285,3 +285,68 @@ jobs:
285
285
  echo "::error::Health check failed after deploy — the Lambda uploaded but isn't serving requests. Check CloudWatch logs for ${{ vars.LAMBDA_FUNCTION_NAME }}."
286
286
  exit 1
287
287
  fi
288
+
289
+ # A Deploy run that deploys NOTHING must not report success (#1065).
290
+ #
291
+ # `deploy-infra` and `deploy-app` are both gated on
292
+ # `vars.SIBLING_DEPLOY_ENABLED == 'true'`. GitHub evaluates an unset variable
293
+ # to the empty string, so before that variable exists both jobs are simply
294
+ # SKIPPED — and a workflow whose every job skipped concludes **success**.
295
+ # Every sibling was therefore born with a green Deploy run that had created
296
+ # no bucket, no Lambda, no route, and nothing distinguished it from a real
297
+ # deploy: it was found only by opening the run and reading the job list.
298
+ #
299
+ # `biffo sibling create` no longer triggers that premature run at all, but
300
+ # ordering alone only fixes the instance of the bug we saw. This job fixes
301
+ # the CLASS: any future run in which the deploy jobs do not actually run is
302
+ # red, whatever the reason.
303
+ #
304
+ # The three states are deliberately distinguished, because "deliberately off"
305
+ # and "never configured" are different facts and only one of them is a defect:
306
+ deploy-status:
307
+ name: Deploy status
308
+ needs: [resolve-environment, deploy-infra, deploy-app]
309
+ if: always()
310
+ runs-on: ${{ vars.RUNNER_LABEL || 'ubuntu-latest' }}
311
+ steps:
312
+ - name: Fail a run that deployed nothing
313
+ env:
314
+ ENABLED: ${{ vars.SIBLING_DEPLOY_ENABLED }}
315
+ INFRA: ${{ needs.deploy-infra.result }}
316
+ APP: ${{ needs.deploy-app.result }}
317
+ run: |
318
+ echo "SIBLING_DEPLOY_ENABLED='${ENABLED}' deploy-infra=${INFRA} deploy-app=${APP}"
319
+
320
+ if [ "${ENABLED}" = "false" ]; then
321
+ echo "::notice::Deploys are deliberately disabled for this repo (SIBLING_DEPLOY_ENABLED=false). Nothing was deployed, by choice."
322
+ exit 0
323
+ fi
324
+
325
+ if [ -z "${ENABLED}" ]; then
326
+ echo "::error::SIBLING_DEPLOY_ENABLED is not set, so every deploy job skipped and this run created nothing. A repo variable named SIBLING_DEPLOY_ENABLED must be set to 'true'; \`biffo sibling create\` sets it in step 7."
327
+ exit 1
328
+ fi
329
+
330
+ # A real failure already makes the run red for the right reason, and
331
+ # `deploy-app` needs `deploy-infra` — so a failed infra job SKIPS the
332
+ # app job. Reporting that skip as "deployed nothing" would bury the
333
+ # actual cause under a second, wrong error. Defer to the real one.
334
+ case "${INFRA}:${APP}" in
335
+ *failure*|*cancelled*)
336
+ echo "A deploy job failed or was cancelled; that failure is the run's result. Not adding a second error."
337
+ exit 0
338
+ ;;
339
+ esac
340
+
341
+ # Enabled — the jobs were meant to run. 'skipped' here means a gate
342
+ # upstream of them suppressed the work while the run still went green.
343
+ for pair in "deploy-infra:${INFRA}" "deploy-app:${APP}"; do
344
+ job="${pair%%:*}"
345
+ result="${pair#*:}"
346
+ if [ "${result}" = "skipped" ]; then
347
+ echo "::error::${job} was skipped although deploys are enabled — this run reported success while deploying nothing."
348
+ exit 1
349
+ fi
350
+ done
351
+
352
+ echo "Deploy jobs ran (infra=${INFRA}, app=${APP})."
package/dist/index.js CHANGED
@@ -6134,12 +6134,14 @@ async function runSiblingCreateCommand(name, options) {
6134
6134
  this sibling automatically: the SIBLING_GITHUB_TOKEN secret, the CORE_* identity variables,
6135
6135
  and \u2014 once the registration PR has merged and the core has redeployed \u2014
6136
6136
  PARENT_CLOUDFRONT_DISTRIBUTION_ARN. No manual variable/secret setup is needed (issue #337).
6137
- 3. Push to \`dev\` (or run the Deploy workflow manually) to provision this sibling's own AWS resources.
6137
+ 3. This sibling's first Deploy has already been dispatched (step 9) \u2014 watch it rather than
6138
+ pushing to trigger one. If it was reported as not dispatched above, run it by hand:
6139
+ \`gh workflow run deploy.yml --ref dev -f environment=dev\`
6138
6140
  `
6139
6141
  );
6140
6142
  }
6141
6143
  async function runSiblingCreate(github, aws, coreAws, git, config, session, options) {
6142
- const totalSteps = 8;
6144
+ const totalSteps = 9;
6143
6145
  const { org, repo } = githubRepo(config);
6144
6146
  const pathPrefix = resolvePathPrefix(config);
6145
6147
  assertGitIdentity(await git.configuredIdentity());
@@ -6248,6 +6250,30 @@ async function runSiblingCreate(github, aws, coreAws, git, config, session, opti
6248
6250
  } else {
6249
6251
  log.step(8, totalSteps, "Already registered with the core project \u2014 skipping");
6250
6252
  }
6253
+ if (!session.completedSteps.includes("trigger_first_deploy")) {
6254
+ const firstEnvironment = config.environments[0] ?? "dev";
6255
+ log.step(9, totalSteps, `Dispatching the first deploy (${firstEnvironment})...`);
6256
+ try {
6257
+ await github.triggerWorkflow(
6258
+ org,
6259
+ repo,
6260
+ "deploy.yml",
6261
+ { environment: firstEnvironment },
6262
+ "dev"
6263
+ );
6264
+ log.info(` Watch it: https://github.com/${org}/${repo}/actions/workflows/deploy.yml`);
6265
+ markSiblingStepComplete(session, "trigger_first_deploy");
6266
+ } catch (err) {
6267
+ log.warn(
6268
+ ` Could not dispatch the first deploy: ${err instanceof Error ? err.message : String(err)}`
6269
+ );
6270
+ log.warn(
6271
+ ` Run it by hand: gh workflow run deploy.yml --repo ${org}/${repo} --ref dev -f environment=dev`
6272
+ );
6273
+ }
6274
+ } else {
6275
+ log.step(9, totalSteps, "First deploy already dispatched \u2014 skipping");
6276
+ }
6251
6277
  reportBranchProtectionSummary();
6252
6278
  deleteSiblingSession(config.project.name);
6253
6279
  }
@@ -6350,7 +6376,12 @@ async function pushSkeleton(git, skeletonRoot, cloneUrl, config, coreConfig, git
6350
6376
  await git.init(workDir, "dev");
6351
6377
  await git.addRemote(workDir, "origin", cloneUrl);
6352
6378
  await git.add(workDir, ["."]);
6353
- await git.commit(workDir, `feat: scaffold ${config.project.name} sibling app (ADR-0007)`);
6379
+ await git.commit(
6380
+ workDir,
6381
+ `feat: scaffold ${config.project.name} sibling app (ADR-0007)
6382
+
6383
+ [skip ci]`
6384
+ );
6354
6385
  await git.push(workDir, "dev", { token: githubToken });
6355
6386
  } finally {
6356
6387
  git.cleanup(workDir);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@biffo/cli",
3
- "version": "0.210.0",
3
+ "version": "0.211.1",
4
4
  "description": "Biffo project scaffolding CLI",
5
5
  "license": "MIT",
6
6
  "type": "module",