@rshono/create 1.0.0-rc.18 → 1.0.0-rc.19

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/api.mjs CHANGED
@@ -147,7 +147,7 @@ __webpack_require__.d(__webpack_exports__, {
147
147
 
148
148
  ;// CONCATENATED MODULE: ./src/generated/framework.ts
149
149
  // GENERATED by scripts/codegen.mjs from packages/core — do not edit. Run `pnpm --filter @rshono/create codegen`.
150
- /** The framework release a scaffolded app is pinned to: this package and rshono ship together. */ const RSHONO_VERSION = '1.0.0-rc.18';
150
+ /** The framework release a scaffolded app is pinned to: this package and rshono ship together. */ const RSHONO_VERSION = '1.0.0-rc.19';
151
151
  /**
152
152
  * The Node range rshono declares, restated in every scaffolded app's `engines` — so a CI image or a contributor
153
153
  * on an older Node hears it from their package manager rather than from a stack trace.
@@ -569,6 +569,11 @@ const QUALITY_PRESETS = [
569
569
  /**
570
570
  * Turns whatever the user typed into a name npm will accept, or `null` when nothing usable is left.
571
571
  * Lowercasing and replacing runs of invalid characters covers the ordinary cases (`My App`, `my_app`).
572
+ *
573
+ * The promise is checked rather than assumed: the result goes through {@link isValidPackageName} on the way
574
+ * out. It used to be spelled as a rule per character class here and the check made again by the caller, which
575
+ * left the exported function able to return a name npm refuses — `_leading` was one, because a leading
576
+ * underscore is stripped by npm's rule and not by this one.
572
577
  */ function toPackageName(input) {
573
578
  const trimmed = input.trim().replace(/^\.\/+/, '').replace(/\/+$/, '');
574
579
  if (!trimmed || trimmed === '.') return null;
@@ -577,9 +582,11 @@ const QUALITY_PRESETS = [
577
582
  const scoped = /^@[^\\/]+[\\/][^\\/]+$/.test(trimmed);
578
583
  const base = scoped ? trimmed : trimmed.split(/[\\/]/).filter(Boolean).pop() ?? '';
579
584
  if (!base) return null;
580
- const name = base.toLowerCase().replace(/[\\/]/g, '/').replace(/[^a-z\d\-._~/@]+/g, '-').replace(/^-+/, '').replace(/-+$/, '');
581
- if (!name || name === '@' || !scoped && name.startsWith('.')) return null;
582
- return name.slice(0, 214);
585
+ const name = base.toLowerCase().replace(/[\\/]/g, '/').replace(/[^a-z\d\-._~/@]+/g, '-')// `_` alongside `-`: npm refuses a leading underscore too, and it is what `My_App` and `_internal` leave
586
+ // behind once the invalid runs are replaced.
587
+ .replace(/^[-_]+/, '').replace(/-+$/, '');
588
+ const trimmedName = name.slice(0, 214);
589
+ return isValidPackageName(trimmedName) ? trimmedName : null;
583
590
  }
584
591
  /** npm's own rule, narrowed to what we ever generate: no uppercase, no leading dot or underscore. */ function isValidPackageName(name) {
585
592
  return /^(?:@[a-z\d\-*~][a-z\d\-*._~]*\/)?[a-z\d\-~][a-z\d\-._~]*$/.test(name) && name.length <= 214;
package/dist/cli.mjs CHANGED
@@ -2941,7 +2941,7 @@ function hasGit(cwd) {
2941
2941
 
2942
2942
  ;// CONCATENATED MODULE: ./src/generated/framework.ts
2943
2943
  // GENERATED by scripts/codegen.mjs from packages/core — do not edit. Run `pnpm --filter @rshono/create codegen`.
2944
- /** The framework release a scaffolded app is pinned to: this package and rshono ship together. */ const RSHONO_VERSION = '1.0.0-rc.18';
2944
+ /** The framework release a scaffolded app is pinned to: this package and rshono ship together. */ const RSHONO_VERSION = '1.0.0-rc.19';
2945
2945
  /**
2946
2946
  * The Node range rshono declares, restated in every scaffolded app's `engines` — so a CI image or a contributor
2947
2947
  * on an older Node hears it from their package manager rather than from a stack trace.
@@ -3043,6 +3043,11 @@ const QUALITY_PRESETS = [
3043
3043
  /**
3044
3044
  * Turns whatever the user typed into a name npm will accept, or `null` when nothing usable is left.
3045
3045
  * Lowercasing and replacing runs of invalid characters covers the ordinary cases (`My App`, `my_app`).
3046
+ *
3047
+ * The promise is checked rather than assumed: the result goes through {@link isValidPackageName} on the way
3048
+ * out. It used to be spelled as a rule per character class here and the check made again by the caller, which
3049
+ * left the exported function able to return a name npm refuses — `_leading` was one, because a leading
3050
+ * underscore is stripped by npm's rule and not by this one.
3046
3051
  */ function toPackageName(input) {
3047
3052
  const trimmed = input.trim().replace(/^\.\/+/, '').replace(/\/+$/, '');
3048
3053
  if (!trimmed || trimmed === '.') return null;
@@ -3051,9 +3056,11 @@ const QUALITY_PRESETS = [
3051
3056
  const scoped = /^@[^\\/]+[\\/][^\\/]+$/.test(trimmed);
3052
3057
  const base = scoped ? trimmed : trimmed.split(/[\\/]/).filter(Boolean).pop() ?? '';
3053
3058
  if (!base) return null;
3054
- const name = base.toLowerCase().replace(/[\\/]/g, '/').replace(/[^a-z\d\-._~/@]+/g, '-').replace(/^-+/, '').replace(/-+$/, '');
3055
- if (!name || name === '@' || !scoped && name.startsWith('.')) return null;
3056
- return name.slice(0, 214);
3059
+ const name = base.toLowerCase().replace(/[\\/]/g, '/').replace(/[^a-z\d\-._~/@]+/g, '-')// `_` alongside `-`: npm refuses a leading underscore too, and it is what `My_App` and `_internal` leave
3060
+ // behind once the invalid runs are replaced.
3061
+ .replace(/^[-_]+/, '').replace(/-+$/, '');
3062
+ const trimmedName = name.slice(0, 214);
3063
+ return isValidPackageName(trimmedName) ? trimmedName : null;
3057
3064
  }
3058
3065
  /** npm's own rule, narrowed to what we ever generate: no uppercase, no leading dot or underscore. */ function isValidPackageName(name) {
3059
3066
  return /^(?:@[a-z\d\-*~][a-z\d\-*._~]*\/)?[a-z\d\-~][a-z\d\-._~]*$/.test(name) && name.length <= 214;
@@ -3920,7 +3927,7 @@ function fail(message) {
3920
3927
  async function main() {
3921
3928
  const { values, positionals } = parse();
3922
3929
  if (values.help) return console.log(HELP);
3923
- if (values.version) return console.log("1.0.0-rc.18");
3930
+ if (values.version) return console.log("1.0.0-rc.19");
3924
3931
  // A pipe, a CI job or an agent gets the defaults rather than a prompt nothing can answer. Both streams have to
3925
3932
  // be a terminal: the prompts draw on stdout but read from stdin.
3926
3933
  const interactive = Boolean(process.stdin.isTTY && process.stdout.isTTY) && !values.yes;
@@ -3946,11 +3953,17 @@ async function main() {
3946
3953
  })) : DEFAULT_DIRECTORY;
3947
3954
  }
3948
3955
  const targetDir = resolve(process.cwd(), directory);
3949
- const packageName = toPackageName(directory === '.' ? basename(targetDir) : directory);
3950
- if (!packageName || !isValidPackageName(packageName)) fail(`"${directory}" does not give a usable npm package name.`);
3951
- const conflicts = conflictingEntries(targetDir);
3956
+ // Resolved rather than compared as text: `.`, `./`, `foo/..` and the cwd's own absolute path all name this
3957
+ // directory, and its own basename is the only thing left to call the package. Matching the literal `'.'`
3958
+ // covered one spelling and left `./` failing on "does not give a usable npm package name".
3959
+ const intoCwd = targetDir === process.cwd();
3960
+ const packageName = toPackageName(intoCwd ? basename(targetDir) : directory);
3961
+ if (!packageName) fail(`"${directory}" does not give a usable npm package name.`);
3962
+ // Not under --dry-run: nothing is written, so there is nothing to conflict with, and the advice it would
3963
+ // give (`--force`) describes an action the user did not ask for.
3964
+ const conflicts = values['dry-run'] ? [] : conflictingEntries(targetDir);
3952
3965
  if (conflicts.length > 0 && !values.force) {
3953
- const where = directory === '.' ? 'this directory' : `"${directory}"`;
3966
+ const where = intoCwd ? 'this directory' : `"${directory}"`;
3954
3967
  const listed = `${conflicts.slice(0, 3).join(', ')}${conflicts.length > 3 ? ', …' : ''}`;
3955
3968
  if (!interactive) fail(`${where} is not empty (${listed}) — pass --force to scaffold into it anyway.`);
3956
3969
  const proceed = unwrap(await dist_confirm({
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rshono/create",
3
- "version": "1.0.0-rc.18",
3
+ "version": "1.0.0-rc.19",
4
4
  "description": "Scaffold a new rshono app — Hono + Rspack + React Server Components",
5
5
  "author": "Lasse <lasse@lassetange.com> (https://www.lassetange.com)",
6
6
  "license": "MIT",
@@ -43,10 +43,10 @@
43
43
  },
44
44
  "devDependencies": {
45
45
  "@clack/prompts": "^1.7.0",
46
- "@rspack/core": "2.2.1",
46
+ "@rspack/core": "2.2.2",
47
47
  "@types/node": "^26.4.0",
48
48
  "typescript": "^7.0.2",
49
- "@rshono/core": "1.0.0-rc.18"
49
+ "@rshono/core": "1.0.0-rc.19"
50
50
  },
51
51
  "scripts": {
52
52
  "build": "node scripts/codegen.mjs && node scripts/build.mjs",
@@ -27,6 +27,10 @@ Interactive parts are `'use client'` components a page imports — only those sh
27
27
  variables reach the browser — everything else is server-only, and a stray read of it in client code
28
28
  compiles to `undefined` rather than shipping. `src/components/layout.tsx` reads `PUBLIC_APP_NAME` that way.
29
29
 
30
+ Both are read **once, at startup**, and the `PUBLIC_` view of them is compiled into the bundle — so editing
31
+ either while `pnpm dev` is running changes nothing until you restart it. The dev server says so when it
32
+ happens; the same is true of `rshono.config.ts`.
33
+
30
34
  ## Deploying
31
35
 
32
36
  This app is built for `{{DEPLOY_TARGET}}`. {{DEPLOY_STEP}}
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "$schema": "https://biomejs.dev/schemas/2.5.6/schema.json",
3
- "files": { "includes": ["**", "!dist", "!.wrangler", "!.vercel", "!.netlify", "!wrangler.jsonc"] },
3
+ "files": { "includes": ["**", "!dist", "!.rshono", "!.wrangler", "!.vercel", "!.netlify", "!wrangler.jsonc"] },
4
4
  "formatter": { "indentStyle": "space", "indentWidth": 2, "lineWidth": 140 },
5
5
  "javascript": { "formatter": { "quoteStyle": "single", "jsxQuoteStyle": "double" } },
6
6
  "css": { "formatter": { "quoteStyle": "single" } },
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "$schema": "https://biomejs.dev/schemas/2.5.6/schema.json",
3
- "files": { "includes": ["**", "!dist", "!.wrangler", "!.vercel", "!.netlify", "!wrangler.jsonc", "!**/*.css"] },
3
+ "files": { "includes": ["**", "!dist", "!.rshono", "!.wrangler", "!.vercel", "!.netlify", "!wrangler.jsonc", "!**/*.css"] },
4
4
  "formatter": { "indentStyle": "space", "indentWidth": 2, "lineWidth": 140 },
5
5
  "javascript": { "formatter": { "quoteStyle": "single", "jsxQuoteStyle": "double" } },
6
6
  "linter": { "enabled": true, "rules": { "preset": "recommended" } }