create-astro 3.1.12 → 3.2.0

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.
Files changed (2) hide show
  1. package/dist/index.js +89 -56
  2. package/package.json +4 -5
package/dist/index.js CHANGED
@@ -176,8 +176,7 @@ import detectPackageManager2 from "which-pm-runs";
176
176
 
177
177
  // src/messages.ts
178
178
  import { color, say as houston, label, spinner as load } from "@astrojs/cli-kit";
179
- import { align, sleep } from "@astrojs/cli-kit/utils";
180
- import { execa } from "execa";
179
+ import { align, sleep as sleep2 } from "@astrojs/cli-kit/utils";
181
180
  import fetch from "node-fetch-native";
182
181
  import { exec } from "node:child_process";
183
182
 
@@ -201,11 +200,42 @@ function stripAnsi(string) {
201
200
 
202
201
  // src/messages.ts
203
202
  import detectPackageManager from "which-pm-runs";
203
+
204
+ // src/shell.ts
205
+ import { spawn } from "node:child_process";
206
+ import { text as textFromStream } from "node:stream/consumers";
207
+ import { setTimeout as sleep } from "node:timers/promises";
208
+ var text = (stream) => stream ? textFromStream(stream).then((t) => t.trimEnd()) : "";
209
+ async function shell(command, flags, opts = {}) {
210
+ const controller = opts.timeout ? new AbortController() : void 0;
211
+ const child = spawn(command, flags, {
212
+ cwd: opts.cwd,
213
+ shell: true,
214
+ stdio: opts.stdio,
215
+ signal: controller == null ? void 0 : controller.signal
216
+ });
217
+ const stdout2 = await text(child.stdout);
218
+ const stderr = await text(child.stderr);
219
+ if (opts.timeout) {
220
+ sleep(opts.timeout).then(() => {
221
+ controller.abort();
222
+ throw { stdout: stdout2, stderr, exitCode: 1 };
223
+ });
224
+ }
225
+ await new Promise((resolve) => child.on("exit", resolve));
226
+ const { exitCode } = child;
227
+ if (exitCode !== 0) {
228
+ throw { stdout: stdout2, stderr, exitCode };
229
+ }
230
+ return { stdout: stdout2, stderr, exitCode };
231
+ }
232
+
233
+ // src/messages.ts
204
234
  async function getRegistry() {
205
235
  var _a, _b;
206
236
  const packageManager = ((_a = detectPackageManager()) == null ? void 0 : _a.name) || "npm";
207
237
  try {
208
- const { stdout: stdout2 } = await execa(packageManager, ["config", "get", "registry"]);
238
+ const { stdout: stdout2 } = await shell(packageManager, ["config", "get", "registry"]);
209
239
  return ((_b = stdout2 == null ? void 0 : stdout2.trim()) == null ? void 0 : _b.replace(/\/$/, "")) || "https://registry.npmjs.org";
210
240
  } catch (e) {
211
241
  return "https://registry.npmjs.org";
@@ -221,7 +251,7 @@ async function say(messages, { clear = false, hat = "" } = {}) {
221
251
  async function spinner(args) {
222
252
  await load(args, { stdout });
223
253
  }
224
- var title = (text) => align(label(text), "end", 7) + " ";
254
+ var title = (text2) => align(label(text2), "end", 7) + " ";
225
255
  var welcome = [
226
256
  `Let's claim your corner of the internet.`,
227
257
  `I'll be your assistant today.`,
@@ -272,39 +302,39 @@ var banner = async (version) => log(
272
302
  `
273
303
  ${label("astro", color.bgGreen, color.black)} ${version ? color.green(color.bold(`v${version}`)) : ""} ${color.bold("Launch sequence initiated.")}`
274
304
  );
275
- var info = async (prefix, text) => {
276
- await sleep(100);
305
+ var info = async (prefix, text2) => {
306
+ await sleep2(100);
277
307
  if (stdout.columns < 80) {
278
308
  log(`${" ".repeat(5)} ${color.cyan("\u25FC")} ${color.cyan(prefix)}`);
279
- log(`${" ".repeat(9)}${color.dim(text)}`);
309
+ log(`${" ".repeat(9)}${color.dim(text2)}`);
280
310
  } else {
281
- log(`${" ".repeat(5)} ${color.cyan("\u25FC")} ${color.cyan(prefix)} ${color.dim(text)}`);
311
+ log(`${" ".repeat(5)} ${color.cyan("\u25FC")} ${color.cyan(prefix)} ${color.dim(text2)}`);
282
312
  }
283
313
  };
284
- var error = async (prefix, text) => {
314
+ var error = async (prefix, text2) => {
285
315
  if (stdout.columns < 80) {
286
316
  log(`${" ".repeat(5)} ${color.red("\u25B2")} ${color.red(prefix)}`);
287
- log(`${" ".repeat(9)}${color.dim(text)}`);
317
+ log(`${" ".repeat(9)}${color.dim(text2)}`);
288
318
  } else {
289
- log(`${" ".repeat(5)} ${color.red("\u25B2")} ${color.red(prefix)} ${color.dim(text)}`);
319
+ log(`${" ".repeat(5)} ${color.red("\u25B2")} ${color.red(prefix)} ${color.dim(text2)}`);
290
320
  }
291
321
  };
292
322
  var typescriptByDefault = async () => {
293
323
  await info(`No worries!`, "TypeScript is supported in Astro by default,");
294
324
  log(`${" ".repeat(9)}${color.dim("but you are free to continue writing JavaScript instead.")}`);
295
- await sleep(1e3);
325
+ await sleep2(1e3);
296
326
  };
297
327
  var nextSteps = async ({ projectDir, devCmd }) => {
298
328
  const max = stdout.columns;
299
329
  const prefix = max < 80 ? " " : " ".repeat(9);
300
- await sleep(200);
330
+ await sleep2(200);
301
331
  log(
302
332
  `
303
333
  ${color.bgCyan(` ${color.black("next")} `)} ${color.bold(
304
334
  "Liftoff confirmed. Explore your project!"
305
335
  )}`
306
336
  );
307
- await sleep(100);
337
+ await sleep2(100);
308
338
  if (projectDir !== "") {
309
339
  projectDir = projectDir.includes(" ") ? `"./${projectDir}"` : `./${projectDir}`;
310
340
  const enter = [
@@ -318,16 +348,16 @@ ${prefix}Enter your project directory using`,
318
348
  log(
319
349
  `${prefix}Run ${color.cyan(devCmd)} to start the dev server. ${color.cyan("CTRL+C")} to stop.`
320
350
  );
321
- await sleep(100);
351
+ await sleep2(100);
322
352
  log(
323
353
  `${prefix}Add frameworks like ${color.cyan(`react`)} or ${color.cyan(
324
354
  "tailwind"
325
355
  )} using ${color.cyan("astro add")}.`
326
356
  );
327
- await sleep(100);
357
+ await sleep2(100);
328
358
  log(`
329
359
  ${prefix}Stuck? Join us at ${color.cyan(`https://astro.build/chat`)}`);
330
- await sleep(200);
360
+ await sleep2(200);
331
361
  };
332
362
  function printHelp({
333
363
  commandName,
@@ -355,7 +385,7 @@ function printHelp({
355
385
  if (headline) {
356
386
  message.push(
357
387
  linebreak(),
358
- `${title(commandName)} ${color.green(`v${"3.1.12"}`)} ${headline}`
388
+ `${title(commandName)} ${color.green(`v${"3.2.0"}`)} ${headline}`
359
389
  );
360
390
  }
361
391
  if (usage) {
@@ -456,7 +486,8 @@ async function getContext(argv) {
456
486
 
457
487
  // src/actions/dependencies.ts
458
488
  import { color as color2 } from "@astrojs/cli-kit";
459
- import { execa as execa2 } from "execa";
489
+ import fs from "node:fs";
490
+ import path from "node:path";
460
491
  async function dependencies(ctx) {
461
492
  let deps = ctx.install ?? ctx.yes;
462
493
  if (deps === void 0) {
@@ -496,21 +527,23 @@ async function dependencies(ctx) {
496
527
  }
497
528
  }
498
529
  async function install({ pkgManager, cwd }) {
499
- const installExec = execa2(pkgManager, ["install"], { cwd });
500
- return new Promise((resolve, reject) => {
501
- setTimeout(() => reject(`Request timed out after one minute`), 6e4);
502
- installExec.on("error", (e) => reject(e));
503
- installExec.on("close", () => resolve());
504
- });
530
+ if (pkgManager === "yarn")
531
+ await ensureYarnLock({ cwd });
532
+ return shell(pkgManager, ["install"], { cwd, timeout: 9e4, stdio: "ignore" });
533
+ }
534
+ async function ensureYarnLock({ cwd }) {
535
+ const yarnLock = path.join(cwd, "yarn.lock");
536
+ if (fs.existsSync(yarnLock))
537
+ return;
538
+ return fs.promises.writeFile(yarnLock, "", { encoding: "utf-8" });
505
539
  }
506
540
 
507
541
  // src/actions/git.ts
508
- import fs from "node:fs";
509
- import path from "node:path";
542
+ import fs2 from "node:fs";
543
+ import path2 from "node:path";
510
544
  import { color as color3 } from "@astrojs/cli-kit";
511
- import { execa as execa3 } from "execa";
512
545
  async function git(ctx) {
513
- if (fs.existsSync(path.join(ctx.cwd, ".git"))) {
546
+ if (fs2.existsSync(path2.join(ctx.cwd, ".git"))) {
514
547
  await info("Nice!", `Git has already been initialized`);
515
548
  return;
516
549
  }
@@ -545,9 +578,9 @@ async function git(ctx) {
545
578
  }
546
579
  async function init({ cwd }) {
547
580
  try {
548
- await execa3("git", ["init"], { cwd, stdio: "ignore" });
549
- await execa3("git", ["add", "-A"], { cwd, stdio: "ignore" });
550
- await execa3(
581
+ await shell("git", ["init"], { cwd, stdio: "ignore" });
582
+ await shell("git", ["add", "-A"], { cwd, stdio: "ignore" });
583
+ await shell(
551
584
  "git",
552
585
  [
553
586
  "commit",
@@ -607,9 +640,9 @@ async function intro(ctx) {
607
640
  }
608
641
 
609
642
  // src/actions/next-steps.ts
610
- import path2 from "node:path";
643
+ import path3 from "node:path";
611
644
  async function next(ctx) {
612
- let projectDir = path2.relative(process.cwd(), ctx.cwd);
645
+ let projectDir = path3.relative(process.cwd(), ctx.cwd);
613
646
  const devCmd = ctx.pkgManager === "npm" ? "npm run dev" : `${ctx.pkgManager} dev`;
614
647
  await nextSteps({ projectDir, devCmd });
615
648
  if (!ctx.skipHouston) {
@@ -620,10 +653,10 @@ async function next(ctx) {
620
653
 
621
654
  // src/actions/project-name.ts
622
655
  import { color as color5, generateProjectName } from "@astrojs/cli-kit";
623
- import path3 from "node:path";
656
+ import path4 from "node:path";
624
657
 
625
658
  // src/actions/shared.ts
626
- import fs2 from "node:fs";
659
+ import fs3 from "node:fs";
627
660
  var VALID_PROJECT_DIRECTORY_SAFE_LIST = [
628
661
  ".DS_Store",
629
662
  ".git",
@@ -649,10 +682,10 @@ var VALID_PROJECT_DIRECTORY_SAFE_LIST = [
649
682
  /^yarn-error\.log/
650
683
  ];
651
684
  function isEmpty(dirPath) {
652
- if (!fs2.existsSync(dirPath)) {
685
+ if (!fs3.existsSync(dirPath)) {
653
686
  return true;
654
687
  }
655
- const conflicts = fs2.readdirSync(dirPath).filter((content) => {
688
+ const conflicts = fs3.readdirSync(dirPath).filter((content) => {
656
689
  return !VALID_PROJECT_DIRECTORY_SAFE_LIST.some((safeContent) => {
657
690
  return typeof safeContent === "string" ? content === safeContent : safeContent.test(content);
658
691
  });
@@ -695,7 +728,7 @@ async function projectName(ctx) {
695
728
  } else {
696
729
  let name = ctx.cwd;
697
730
  if (name === "." || name === "./") {
698
- const parts = process.cwd().split(path3.sep);
731
+ const parts = process.cwd().split(path4.sep);
699
732
  name = parts[parts.length - 1];
700
733
  } else if (name.startsWith("./") || name.startsWith("../")) {
701
734
  const parts = name.split("/");
@@ -719,8 +752,8 @@ async function checkCwd(cwd) {
719
752
  // src/actions/template.ts
720
753
  import { color as color6 } from "@astrojs/cli-kit";
721
754
  import { downloadTemplate } from "giget";
722
- import fs3 from "node:fs";
723
- import path4 from "node:path";
755
+ import fs4 from "node:fs";
756
+ import path5 from "node:path";
724
757
  async function template(ctx) {
725
758
  if (!ctx.template) {
726
759
  const { template: tmpl } = await ctx.prompt({
@@ -761,10 +794,10 @@ async function template(ctx) {
761
794
  }
762
795
  var FILES_TO_REMOVE = ["sandbox.config.json", "CHANGELOG.md"];
763
796
  var FILES_TO_UPDATE = {
764
- "package.json": (file, overrides) => fs3.promises.readFile(file, "utf-8").then((value) => {
797
+ "package.json": (file, overrides) => fs4.promises.readFile(file, "utf-8").then((value) => {
765
798
  var _a;
766
799
  const indent = ((_a = /(^\s+)/m.exec(value)) == null ? void 0 : _a[1]) ?? " ";
767
- fs3.promises.writeFile(
800
+ fs4.promises.writeFile(
768
801
  file,
769
802
  JSON.stringify(
770
803
  Object.assign(JSON.parse(value), Object.assign(overrides, { private: void 0 })),
@@ -796,25 +829,25 @@ async function copyTemplate(tmpl, ctx) {
796
829
  dir: "."
797
830
  });
798
831
  } catch (err) {
799
- fs3.rmdirSync(ctx.cwd);
832
+ fs4.rmdirSync(ctx.cwd);
800
833
  if (err.message.includes("404")) {
801
834
  throw new Error(`Template ${color6.reset(tmpl)} ${color6.dim("does not exist!")}`);
802
835
  } else {
803
836
  throw new Error(err.message);
804
837
  }
805
838
  }
806
- if (fs3.readdirSync(ctx.cwd).length === 0) {
839
+ if (fs4.readdirSync(ctx.cwd).length === 0) {
807
840
  throw new Error(`Template ${color6.reset(tmpl)} ${color6.dim("is empty!")}`);
808
841
  }
809
842
  const removeFiles = FILES_TO_REMOVE.map(async (file) => {
810
- const fileLoc = path4.resolve(path4.join(ctx.cwd, file));
811
- if (fs3.existsSync(fileLoc)) {
812
- return fs3.promises.rm(fileLoc, { recursive: true });
843
+ const fileLoc = path5.resolve(path5.join(ctx.cwd, file));
844
+ if (fs4.existsSync(fileLoc)) {
845
+ return fs4.promises.rm(fileLoc, { recursive: true });
813
846
  }
814
847
  });
815
848
  const updateFiles = Object.entries(FILES_TO_UPDATE).map(async ([file, update]) => {
816
- const fileLoc = path4.resolve(path4.join(ctx.cwd, file));
817
- if (fs3.existsSync(fileLoc)) {
849
+ const fileLoc = path5.resolve(path5.join(ctx.cwd, file));
850
+ if (fs4.existsSync(fileLoc)) {
818
851
  return update(fileLoc, { name: ctx.projectName });
819
852
  }
820
853
  });
@@ -824,9 +857,9 @@ async function copyTemplate(tmpl, ctx) {
824
857
 
825
858
  // src/actions/typescript.ts
826
859
  import { color as color7 } from "@astrojs/cli-kit";
827
- import fs4 from "node:fs";
860
+ import fs5 from "node:fs";
828
861
  import { readFile } from "node:fs/promises";
829
- import path5 from "node:path";
862
+ import path6 from "node:path";
830
863
 
831
864
  // ../../node_modules/.pnpm/strip-json-comments@5.0.0/node_modules/strip-json-comments/index.js
832
865
  var singleComment = Symbol("singleComment");
@@ -946,7 +979,7 @@ async function typescript(ctx) {
946
979
  } else {
947
980
  if (!["strict", "strictest", "relaxed", "default", "base"].includes(ts)) {
948
981
  if (!ctx.dryRun) {
949
- fs4.rmSync(ctx.cwd, { recursive: true, force: true });
982
+ fs5.rmSync(ctx.cwd, { recursive: true, force: true });
950
983
  }
951
984
  error(
952
985
  "Error",
@@ -976,7 +1009,7 @@ async function typescript(ctx) {
976
1009
  }
977
1010
  }
978
1011
  async function setupTypeScript(value, { cwd }) {
979
- const templateTSConfigPath = path5.join(cwd, "tsconfig.json");
1012
+ const templateTSConfigPath = path6.join(cwd, "tsconfig.json");
980
1013
  try {
981
1014
  const data = await readFile(templateTSConfigPath, { encoding: "utf-8" });
982
1015
  const templateTSConfig = JSON.parse(stripJsonComments(data));
@@ -984,7 +1017,7 @@ async function setupTypeScript(value, { cwd }) {
984
1017
  const result = Object.assign(templateTSConfig, {
985
1018
  extends: `astro/tsconfigs/${value}`
986
1019
  });
987
- fs4.writeFileSync(templateTSConfigPath, JSON.stringify(result, null, 2));
1020
+ fs5.writeFileSync(templateTSConfigPath, JSON.stringify(result, null, 2));
988
1021
  } else {
989
1022
  throw new Error(
990
1023
  "There was an error applying the requested TypeScript settings. This could be because the template's tsconfig.json is malformed"
@@ -992,7 +1025,7 @@ async function setupTypeScript(value, { cwd }) {
992
1025
  }
993
1026
  } catch (err) {
994
1027
  if (err && err.code === "ENOENT") {
995
- fs4.writeFileSync(
1028
+ fs5.writeFileSync(
996
1029
  templateTSConfigPath,
997
1030
  JSON.stringify({ extends: `astro/tsconfigs/${value}` }, null, 2)
998
1031
  );
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-astro",
3
- "version": "3.1.12",
3
+ "version": "3.2.0",
4
4
  "type": "module",
5
5
  "author": "withastro",
6
6
  "license": "MIT",
@@ -26,15 +26,14 @@
26
26
  "//b": "DEPENDENCIES IS FOR UNBUNDLED PACKAGES",
27
27
  "dependencies": {
28
28
  "@astrojs/cli-kit": "^0.2.3",
29
- "chai": "^4.3.7",
30
- "execa": "^6.1.0",
31
- "giget": "1.0.0",
32
- "mocha": "^9.2.2",
29
+ "giget": "^1.1.2",
33
30
  "node-fetch-native": "^1.2.0",
34
31
  "which-pm-runs": "^1.1.0"
35
32
  },
36
33
  "devDependencies": {
37
34
  "@types/which-pm-runs": "^1.0.0",
35
+ "chai": "^4.3.7",
36
+ "mocha": "^9.2.2",
38
37
  "arg": "^5.0.2",
39
38
  "strip-ansi": "^7.1.0",
40
39
  "strip-json-comments": "^5.0.0",