betterstart-cli 0.0.34 → 0.0.36

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.
package/dist/cli.js CHANGED
@@ -1664,8 +1664,8 @@ function ensureDatabasePushDependencies(cwd, pm) {
1664
1664
  Installing database push dependencies (${missing.map((dependency) => dependency.name).join(", ")})...`
1665
1665
  );
1666
1666
  for (const dependency of missing) {
1667
- const installed = installDependency(cwd, pm, dependency.name, dependency.dev);
1668
- if (!installed) {
1667
+ const installed2 = installDependency(cwd, pm, dependency.name, dependency.dev);
1668
+ if (!installed2) {
1669
1669
  console.log(` Failed to install ${dependency.name}`);
1670
1670
  return false;
1671
1671
  }
@@ -3460,7 +3460,7 @@ function schemaManifestContainsMailchimpImports(cwd, config, schemaName) {
3460
3460
  return false;
3461
3461
  }
3462
3462
  const content = fs14.readFileSync(fullPath, "utf-8");
3463
- return markers.some((marker) => content.includes(marker));
3463
+ return markers.some((marker2) => content.includes(marker2));
3464
3464
  });
3465
3465
  }
3466
3466
  function findBlockingIntegrationDependencies(cwd, config, integrationId) {
@@ -3605,7 +3605,7 @@ async function installIntegrations({
3605
3605
  const orderedIntegrationIds = resolveIntegrationInstallOrder(integrationIds);
3606
3606
  const installedIntegrationIds = normalizeInstalledIntegrations(config);
3607
3607
  const skipped = [];
3608
- const installed = [];
3608
+ const installed2 = [];
3609
3609
  const activated = [];
3610
3610
  const warnings = [];
3611
3611
  for (const integrationId of orderedIntegrationIds) {
@@ -3704,7 +3704,7 @@ async function installIntegrations({
3704
3704
  });
3705
3705
  saveInstalledIntegrationManifest(cwd, manifest);
3706
3706
  writeConfigFile(cwd, config);
3707
- installed.push(integrationId);
3707
+ installed2.push(integrationId);
3708
3708
  if (!configureResult.configured && isProviderIntegration(definition)) {
3709
3709
  warnings.push(
3710
3710
  `${integrationId} was installed but not activated because its required environment variables are still missing.`
@@ -3712,7 +3712,7 @@ async function installIntegrations({
3712
3712
  }
3713
3713
  }
3714
3714
  return {
3715
- installed,
3715
+ installed: installed2,
3716
3716
  activated,
3717
3717
  skipped,
3718
3718
  warnings,
@@ -18727,7 +18727,7 @@ async function installPlugins({
18727
18727
  const orderedPluginIds = resolvePluginInstallOrder(pluginIds);
18728
18728
  const installedPluginIds = normalizeInstalledPlugins(config);
18729
18729
  const skipped = [];
18730
- const installed = [];
18730
+ const installed2 = [];
18731
18731
  const warnings = [];
18732
18732
  ensureSnapshotGitFiles(cwd);
18733
18733
  for (const pluginId of orderedPluginIds) {
@@ -18796,10 +18796,10 @@ async function installPlugins({
18796
18796
  };
18797
18797
  saveInstalledPluginManifest(cwd, manifest);
18798
18798
  writeConfigFile(cwd, config);
18799
- installed.push(pluginId);
18799
+ installed2.push(pluginId);
18800
18800
  }
18801
18801
  return {
18802
- installed,
18802
+ installed: installed2,
18803
18803
  skipped,
18804
18804
  warnings,
18805
18805
  config
@@ -21828,6 +21828,89 @@ import fs39 from "fs";
21828
21828
  import path50 from "path";
21829
21829
  import * as p17 from "@clack/prompts";
21830
21830
 
21831
+ // core-engine/utils/prompt-theme.ts
21832
+ var GREEN_STEP_SUBMIT = "\x1B[32m\u25C7\x1B[39m";
21833
+ var GREEN_CHECK = "\x1B[32m\u2713\x1B[39m";
21834
+ function restyleStepSubmitSymbols(text7) {
21835
+ return text7.split(GREEN_STEP_SUBMIT).join(GREEN_CHECK);
21836
+ }
21837
+ var ROW_ESCAPES = /\u001B\[(\d*)([ABEF])/g;
21838
+ function rowDelta(text7) {
21839
+ let delta = text7.split("\n").length - 1;
21840
+ for (const match of text7.matchAll(ROW_ESCAPES)) {
21841
+ const n = match[1] === "" ? 1 : Number(match[1]);
21842
+ delta += match[2] === "A" || match[2] === "F" ? -n : n;
21843
+ }
21844
+ return delta;
21845
+ }
21846
+ var installed = false;
21847
+ var armed = false;
21848
+ var marker = null;
21849
+ var generation = 0;
21850
+ var rawStdoutWrite;
21851
+ function installPromptCheckmarks() {
21852
+ if (installed || !process.stdout.isTTY || process.env.CI === "true") return () => {
21853
+ };
21854
+ installed = true;
21855
+ const unpatchedOut = process.stdout.write;
21856
+ const unpatchedErr = process.stderr.write;
21857
+ const writeOut = unpatchedOut.bind(process.stdout);
21858
+ const writeErr = unpatchedErr.bind(process.stderr);
21859
+ rawStdoutWrite = writeOut;
21860
+ process.stdout.write = ((chunk, encoding, callback) => {
21861
+ if (typeof chunk !== "string") return writeOut(chunk, encoding, callback);
21862
+ const idx = armed ? chunk.indexOf(GREEN_STEP_SUBMIT) : -1;
21863
+ if (idx === -1) {
21864
+ if (marker) marker.rowsAbove += rowDelta(chunk);
21865
+ return writeOut(restyleStepSubmitSymbols(chunk), encoding, callback);
21866
+ }
21867
+ armed = false;
21868
+ const rest = chunk.slice(idx + GREEN_STEP_SUBMIT.length);
21869
+ marker = { rowsAbove: rowDelta(rest) };
21870
+ return writeOut(
21871
+ restyleStepSubmitSymbols(chunk.slice(0, idx)) + GREEN_STEP_SUBMIT + restyleStepSubmitSymbols(rest),
21872
+ encoding,
21873
+ callback
21874
+ );
21875
+ });
21876
+ process.stderr.write = ((chunk, encoding, callback) => {
21877
+ if (typeof chunk === "string" && marker) marker.rowsAbove += rowDelta(chunk);
21878
+ return writeErr(chunk, encoding, callback);
21879
+ });
21880
+ return () => {
21881
+ process.stdout.write = unpatchedOut;
21882
+ process.stderr.write = unpatchedErr;
21883
+ rawStdoutWrite = void 0;
21884
+ installed = false;
21885
+ armed = false;
21886
+ marker = null;
21887
+ };
21888
+ }
21889
+ function deferNextPromptCheck() {
21890
+ if (!installed) return { confirm() {
21891
+ }, skip() {
21892
+ } };
21893
+ generation += 1;
21894
+ const token = generation;
21895
+ armed = true;
21896
+ marker = null;
21897
+ return {
21898
+ confirm() {
21899
+ if (token !== generation) return;
21900
+ armed = false;
21901
+ const rows = marker?.rowsAbove;
21902
+ marker = null;
21903
+ if (rows === void 0 || rows <= 0 || rows >= (process.stdout.rows ?? 24)) return;
21904
+ rawStdoutWrite?.(`\x1B[${rows}A\r${GREEN_CHECK}\x1B[${rows}B\r`);
21905
+ },
21906
+ skip() {
21907
+ if (token !== generation) return;
21908
+ armed = false;
21909
+ marker = null;
21910
+ }
21911
+ };
21912
+ }
21913
+
21831
21914
  // adapters/next/init/prompts/database.ts
21832
21915
  import { execFileSync as execFileSync4 } from "child_process";
21833
21916
  import * as p10 from "@clack/prompts";
@@ -22076,6 +22159,7 @@ async function promptPlugins(cwd, options = {}) {
22076
22159
  overwriteKeys.add(key);
22077
22160
  }
22078
22161
  };
22162
+ const storageStep = deferNextPromptCheck();
22079
22163
  const storage = await p11.select({
22080
22164
  message: "Choose a file storage",
22081
22165
  options: [
@@ -22101,6 +22185,7 @@ async function promptPlugins(cwd, options = {}) {
22101
22185
  }
22102
22186
  if (storage === "r2") {
22103
22187
  mergeIntegrationConfig(await collectIntegrationConfig(cwd, ["r2"]));
22188
+ storageStep.confirm();
22104
22189
  } else if (storage === "vercel-blob") {
22105
22190
  const existingToken = readEnvVar(cwd, "BLOB_READ_WRITE_TOKEN")?.trim();
22106
22191
  const flow = !existingToken && options.provisionVercelBlob ? await options.provisionVercelBlob() : void 0;
@@ -22112,6 +22197,8 @@ async function promptPlugins(cwd, options = {}) {
22112
22197
  vars: [{ key: "BLOB_READ_WRITE_TOKEN", value: flow.token }]
22113
22198
  });
22114
22199
  overwriteKeys.add("BLOB_READ_WRITE_TOKEN");
22200
+ if (flow.usedTerminalFallback) storageStep.skip();
22201
+ else storageStep.confirm();
22115
22202
  } else {
22116
22203
  if (existingToken) {
22117
22204
  p11.log.info("Using the existing Vercel Blob token from .env.local");
@@ -22119,7 +22206,11 @@ async function promptPlugins(cwd, options = {}) {
22119
22206
  p11.log.info("Falling back to a manual Vercel Blob token.");
22120
22207
  }
22121
22208
  mergeIntegrationConfig(await collectIntegrationConfig(cwd, ["vercel-blob"]));
22209
+ if (flow) storageStep.skip();
22210
+ else storageStep.confirm();
22122
22211
  }
22212
+ } else {
22213
+ storageStep.confirm();
22123
22214
  }
22124
22215
  const selectedPlugins = await p11.multiselect({
22125
22216
  message: "Select presets",
@@ -24468,7 +24559,7 @@ async function provisionBlobStoreInteractive(runner, cwd, options) {
24468
24559
  return { storeName: quiet.storeName, failure: "env-pull-empty" };
24469
24560
  }
24470
24561
  pullSpinner.clear();
24471
- return { token, storeName: quiet.storeName };
24562
+ return { token, storeName: quiet.storeName, usedTerminalFallback: true };
24472
24563
  }
24473
24564
  async function provisionBlobStore(runner, cwd, options) {
24474
24565
  const provisionSpinner = spinner2();
@@ -24845,7 +24936,8 @@ async function runVercelBlobFlow(options) {
24845
24936
  return {
24846
24937
  ok: true,
24847
24938
  token: blob.token,
24848
- blobStoreName: blob.storeName
24939
+ blobStoreName: blob.storeName,
24940
+ usedTerminalFallback: blob.usedTerminalFallback
24849
24941
  };
24850
24942
  } catch (error) {
24851
24943
  p16.log.warn(
@@ -24881,7 +24973,9 @@ async function runVercelDeployFlow(options) {
24881
24973
  } else {
24882
24974
  envSpinner.clear();
24883
24975
  }
24976
+ let printedWarnings = false;
24884
24977
  for (const key of sync.failed) {
24978
+ printedWarnings = true;
24885
24979
  p16.log.warn(
24886
24980
  `Could not set ${pc6.cyan(key)} on Vercel \u2014 add it in the project's environment settings.`
24887
24981
  );
@@ -24891,6 +24985,7 @@ async function runVercelDeployFlow(options) {
24891
24985
  }
24892
24986
  const packageGuard = guardProjectForDeploy(options.cwd);
24893
24987
  for (const dep of packageGuard.localSpecDeps) {
24988
+ printedWarnings = true;
24894
24989
  p16.log.warn(
24895
24990
  `Dependency ${pc6.cyan(dep)} uses a local spec that cannot install on Vercel \u2014 the remote build may fail.`
24896
24991
  );
@@ -24912,7 +25007,7 @@ async function runVercelDeployFlow(options) {
24912
25007
  const linkedName = readLinkedProjectName(options.cwd);
24913
25008
  const url = linkedName ? `https://${linkedName}.vercel.app` : deploy.url;
24914
25009
  deploySpinner.stop(url ? `Deployed ${pc6.cyan(url)}` : "Deployed to Vercel");
24915
- return { ok: true, url, syncedEnvKeys: sync.synced };
25010
+ return { ok: true, url, syncedEnvKeys: sync.synced, cleanScreen: !printedWarnings };
24916
25011
  } catch (error) {
24917
25012
  p16.log.warn(`Vercel deploy failed: ${error instanceof Error ? error.message : String(error)}`);
24918
25013
  printManualDeployHint();
@@ -25387,6 +25482,7 @@ function removeExistingAdminPaths(cwd, namespaces) {
25387
25482
  return removed;
25388
25483
  }
25389
25484
  async function runInitCommand(name, options) {
25485
+ installPromptCheckmarks();
25390
25486
  p17.box(
25391
25487
  `
25392
25488
  \u2584 \u2597 \u2597 \u2584\u2596\u2597 \u2597
@@ -25613,6 +25709,7 @@ async function runInitCommand(name, options) {
25613
25709
  p17.log.info(`Using existing database URL from .env.local ${pc7.dim(`(${masked})`)}`);
25614
25710
  databaseUrl = existingDbUrl;
25615
25711
  } else {
25712
+ const databaseStep = deferNextPromptCheck();
25616
25713
  const servicesResult = await promptServices({ allowVercel: options.vercel !== false });
25617
25714
  if (servicesResult.provider === "vercel-cli") {
25618
25715
  const flow = await runVercelNeonFlow({
@@ -25626,17 +25723,22 @@ async function runInitCommand(name, options) {
25626
25723
  databaseUrl = flow.databaseUrl;
25627
25724
  persistDatabaseUrl(cwd, databaseUrl);
25628
25725
  dismissVercelSignedInNote = flow.dismissSignedInNote;
25726
+ if (flow.dismissSignedInNote) databaseStep.confirm();
25727
+ else databaseStep.skip();
25629
25728
  } else if (flow.ok) {
25729
+ databaseStep.skip();
25630
25730
  openBrowserVercelNeonResource(flow.dashboardUrl ?? flow.resourceUrl);
25631
25731
  databaseUrl = await promptConnectionString();
25632
25732
  persistDatabaseUrl(cwd, databaseUrl);
25633
25733
  } else {
25734
+ databaseStep.skip();
25634
25735
  p17.log.info("Falling back to a manual database connection string.");
25635
25736
  openBrowserVercelNeon();
25636
25737
  databaseUrl = await promptConnectionString();
25637
25738
  }
25638
25739
  } else {
25639
25740
  databaseUrl = servicesResult.url;
25741
+ databaseStep.confirm();
25640
25742
  }
25641
25743
  }
25642
25744
  const selectedPlugins = (() => {
@@ -26152,12 +26254,17 @@ Run manually: ${pc7.cyan(betterstartExecCommand(pm, "seed"))}`,
26152
26254
  if (options.vercel !== false && !options.skipDeploy) {
26153
26255
  const linkedVercelProject = Boolean(readLinkedProjectId(cwd));
26154
26256
  if (!options.yes) {
26257
+ const deployStep = deferNextPromptCheck();
26155
26258
  const deployNow = await p17.confirm({
26156
26259
  message: "Deploy to Vercel now?",
26157
26260
  initialValue: linkedVercelProject
26158
26261
  });
26159
26262
  if (!p17.isCancel(deployNow) && deployNow) {
26160
- await runVercelDeployFlow({ cwd, projectName, env: process.env });
26263
+ const deployFlow = await runVercelDeployFlow({ cwd, projectName, env: process.env });
26264
+ if (deployFlow.ok && deployFlow.cleanScreen) deployStep.confirm();
26265
+ else deployStep.skip();
26266
+ } else {
26267
+ deployStep.confirm();
26161
26268
  }
26162
26269
  } else if (linkedVercelProject && process.env.VERCEL_TOKEN) {
26163
26270
  const deployFlow = await runVercelDeployFlow({