@lukoweb/apitogo 0.1.82 → 0.1.84

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/cli/cli.js +76 -45
  2. package/package.json +1 -1
package/dist/cli/cli.js CHANGED
@@ -5633,7 +5633,7 @@ import {
5633
5633
  // package.json
5634
5634
  var package_default = {
5635
5635
  name: "@lukoweb/apitogo",
5636
- version: "0.1.82",
5636
+ version: "0.1.84",
5637
5637
  type: "module",
5638
5638
  sideEffects: [
5639
5639
  "**/*.css",
@@ -10574,7 +10574,7 @@ function createDefaultApitogoJsonConfig(options) {
10574
10574
  site: {
10575
10575
  title: options.title,
10576
10576
  logo: {
10577
- src: { light: "/logo-light.png", dark: "/logo-dark.png" },
10577
+ src: { light: "/logo-light.svg", dark: "/logo-dark.svg" },
10578
10578
  alt: "API ToGo",
10579
10579
  width: "130px"
10580
10580
  }
@@ -10586,7 +10586,7 @@ function createDefaultApitogoJsonConfig(options) {
10586
10586
  redirectToAfterSignUp: "/account/dashboard"
10587
10587
  },
10588
10588
  metadata: {
10589
- favicon: "/Icon.png"
10589
+ favicon: "/logo-light.svg"
10590
10590
  },
10591
10591
  theme: {
10592
10592
  fonts: {
@@ -10937,6 +10937,17 @@ export default buildApitogoConfig({
10937
10937
  function isThinConfigWrapper(source) {
10938
10938
  return /export\s+default\s+buildApitogoConfig\s*\(/.test(source);
10939
10939
  }
10940
+ function isManagedConfigWrapper(source) {
10941
+ if (isThinConfigWrapper(source)) {
10942
+ return true;
10943
+ }
10944
+ return /from\s+["']\.\/apitogo\.config\.json["']/.test(source) && /buildApitogoConfig\s*\(/.test(source) && /type:\s*["']custom-page["']/.test(source);
10945
+ }
10946
+ function labelFromRoutePath(routePath) {
10947
+ const slug = routePath.replace(/^\/+/, "");
10948
+ const leaf = slug.split("/").filter(Boolean).pop() ?? slug;
10949
+ return titleFromDirectoryName(leaf);
10950
+ }
10940
10951
  function buildThinWrapperWithCustomPages(tsxRoutePaths) {
10941
10952
  if (tsxRoutePaths.length === 0) {
10942
10953
  return THIN_WRAPPER_SOURCE;
@@ -10949,9 +10960,11 @@ function buildThinWrapperWithCustomPages(tsxRoutePaths) {
10949
10960
  const customPages = tsxRoutePaths.map((routePath) => {
10950
10961
  const slug = routePath.replace(/^\//, "");
10951
10962
  const name = pageComponentName(slug);
10963
+ const label = labelFromRoutePath(routePath);
10952
10964
  return ` {
10953
10965
  type: "custom-page",
10954
10966
  path: ${JSON.stringify(routePath)},
10967
+ label: ${JSON.stringify(label)},
10955
10968
  element: <${name} />,
10956
10969
  },`;
10957
10970
  }).join("\n");
@@ -10973,13 +10986,17 @@ export default {
10973
10986
  label: ${JSON.stringify(DOCUMENTATION_NAV_LABEL)},
10974
10987
  items: [
10975
10988
  ${customPages}
10976
- ...(((config.navigation ?? []).find(
10989
+ ...((((config.navigation ?? []).find(
10977
10990
  (item) =>
10978
10991
  typeof item === "object" &&
10979
10992
  item !== null &&
10980
10993
  "label" in item &&
10981
10994
  item.label === ${JSON.stringify(DOCUMENTATION_NAV_LABEL)},
10982
- ) as { items?: unknown[] } | undefined)?.items ?? []),
10995
+ ) as { items?: unknown[] } | undefined)?.items ?? []).filter(
10996
+ (item) =>
10997
+ typeof item !== "string" ||
10998
+ !${JSON.stringify(tsxRoutePaths)}.includes(item),
10999
+ )),
10983
11000
  ],
10984
11001
  },
10985
11002
  ...(config.navigation ?? []).filter(
@@ -11021,7 +11038,7 @@ function printPaidPlanPlatformWarning() {
11021
11038
  }
11022
11039
  function printInteractiveWrapUp(hasPaidPlans) {
11023
11040
  printDiagnosticsToConsole("");
11024
- printDiagnosticsToConsole("Configuration saved. Next steps:");
11041
+ printDiagnosticsToConsole("Configuration is done. Next steps:");
11025
11042
  printDiagnosticsToConsole("- Preview locally: npm run dev");
11026
11043
  if (hasPaidPlans) {
11027
11044
  printPaidPlanPlatformWarning();
@@ -11261,7 +11278,7 @@ export default function ${componentName}() {
11261
11278
  // src/cli/make-config/scaffold-project.ts
11262
11279
  init_package_json();
11263
11280
  import { constants } from "node:fs";
11264
- import { access as access2, mkdir as mkdir6, readFile as readFile4, writeFile as writeFile6 } from "node:fs/promises";
11281
+ import { access as access2, copyFile, mkdir as mkdir6, readFile as readFile4, writeFile as writeFile6 } from "node:fs/promises";
11265
11282
  import path35 from "node:path";
11266
11283
  import { glob as glob4 } from "glob";
11267
11284
  var OPENAPI_GLOBS = [
@@ -11466,6 +11483,26 @@ async function ensurePortalStubFiles(dir) {
11466
11483
  await mkdir6(path35.join(dir, "user-panel"), { recursive: true });
11467
11484
  await writeFile6(plansPath, ACCOUNT_PLANS_PAGE_SOURCE, "utf8");
11468
11485
  }
11486
+ await ensurePublicBrandingFiles(dir);
11487
+ }
11488
+ var BRANDING_ASSETS = ["logo-light.svg", "logo-dark.svg"];
11489
+ async function ensurePublicBrandingFiles(dir) {
11490
+ const destDir = path35.join(dir, "public");
11491
+ await mkdir6(destDir, { recursive: true });
11492
+ const srcDir = path35.join(
11493
+ getZudokuRootDir(),
11494
+ "src",
11495
+ "cli",
11496
+ "make-config",
11497
+ "public"
11498
+ );
11499
+ for (const name of BRANDING_ASSETS) {
11500
+ const dest = path35.join(destDir, name);
11501
+ if (await fileExists2(dest)) {
11502
+ continue;
11503
+ }
11504
+ await copyFile(path35.join(srcDir, name), dest);
11505
+ }
11469
11506
  }
11470
11507
  async function ensureThinConfigTsx(dir) {
11471
11508
  const tsxPath = path35.join(dir, "apitogo.config.tsx");
@@ -11519,7 +11556,8 @@ async function persistConfig(config2, ctx) {
11519
11556
  (file) => toRoutePath(file, ctx.pagesDir)
11520
11557
  );
11521
11558
  const tsxRoutes = tsxFiles.map((file) => toRoutePath(file, ctx.pagesDir));
11522
- if (markdownRoutes.length === 0 && tsxRoutes.length === 0) {
11559
+ const docRoutes = [.../* @__PURE__ */ new Set([...markdownRoutes, ...tsxRoutes])];
11560
+ if (docRoutes.length === 0) {
11523
11561
  printDiagnosticsToConsole(
11524
11562
  `No docs pages under '${ctx.pagesDir}/' \u2014 skipping documentation nav scan.`
11525
11563
  );
@@ -11528,7 +11566,7 @@ async function persistConfig(config2, ctx) {
11528
11566
  ...config2,
11529
11567
  navigation: mergeDocumentationNavigation(
11530
11568
  config2.navigation,
11531
- markdownRoutes,
11569
+ docRoutes,
11532
11570
  { force: ctx.force }
11533
11571
  )
11534
11572
  };
@@ -11537,7 +11575,7 @@ async function persistConfig(config2, ctx) {
11537
11575
  const tsxPath = path36.join(ctx.dir, "apitogo.config.tsx");
11538
11576
  if (await fileExists3(tsxPath) && tsxRoutes.length > 0) {
11539
11577
  const tsxSource = await readFile5(tsxPath, "utf8");
11540
- if (isThinConfigWrapper(tsxSource)) {
11578
+ if (isManagedConfigWrapper(tsxSource)) {
11541
11579
  await writeFile7(
11542
11580
  tsxPath,
11543
11581
  buildThinWrapperWithCustomPages(tsxRoutes),
@@ -11636,50 +11674,17 @@ async function makeConfig(argv) {
11636
11674
  interactiveHasPaidPlans = prompted.hasPaidPlans;
11637
11675
  } else {
11638
11676
  config2 = applyConfigPatches(config2, flagPatches);
11639
- const pageFiles = await glob5(`${pagesDir}/**/*.{md,mdx,tsx,jsx}`, {
11640
- cwd: dir,
11641
- ignore: ["**/node_modules/**", "**/.git/**", "**/dist/**"],
11642
- posix: true
11643
- });
11644
- const markdownFiles = pageFiles.filter((file) => /\.mdx?$/i.test(file));
11645
- const tsxFiles = pageFiles.filter((file) => /\.(tsx|jsx)$/i.test(file));
11646
- const markdownRoutes = markdownFiles.map(
11647
- (file) => toRoutePath(file, pagesDir)
11648
- );
11649
- const tsxRoutes = tsxFiles.map((file) => toRoutePath(file, pagesDir));
11650
- if (markdownRoutes.length === 0 && tsxRoutes.length === 0) {
11651
- printDiagnosticsToConsole(
11652
- `No docs pages under '${pagesDir}/' \u2014 skipping documentation nav scan.`
11653
- );
11654
- }
11655
- config2.navigation = mergeDocumentationNavigation(
11656
- config2.navigation,
11657
- markdownRoutes,
11658
- { force: argv.force === true }
11659
- );
11660
11677
  if (discoveredOpenApi) {
11661
11678
  config2 = applyOpenApiToJsonConfig(
11662
11679
  config2,
11663
11680
  openapiInputForConfig(discoveredOpenApi)
11664
11681
  );
11665
11682
  }
11666
- await writeFile7(jsonPath, `${JSON.stringify(config2, null, 2)}
11667
- `, "utf8");
11668
- const tsxPath = path36.join(dir, "apitogo.config.tsx");
11669
- if (await fileExists3(tsxPath) && tsxRoutes.length > 0) {
11670
- const tsxSource = await readFile5(tsxPath, "utf8");
11671
- if (isThinConfigWrapper(tsxSource)) {
11672
- await writeFile7(
11673
- tsxPath,
11674
- buildThinWrapperWithCustomPages(tsxRoutes),
11675
- "utf8"
11676
- );
11677
- }
11678
- }
11683
+ config2 = await persistConfig(config2, persistCtx);
11679
11684
  }
11680
11685
  const action = createdJson ? "Initialized" : "Updated";
11681
11686
  printResultToConsole(
11682
- `${action} ${APITOGO_JSON_FILENAME} (site/auth/navigation/OpenAPI/plans as applicable; redirects unchanged).`
11687
+ `${action} ${APITOGO_JSON_FILENAME}.`
11683
11688
  );
11684
11689
  if (createdPackageJson) {
11685
11690
  printDiagnosticsToConsole(
@@ -12163,10 +12168,36 @@ var dev_default = {
12163
12168
  };
12164
12169
 
12165
12170
  // src/cli/init/handler.ts
12171
+ import { mkdir as mkdir8, readdir, stat as stat4 } from "node:fs/promises";
12166
12172
  import path40 from "node:path";
12173
+ var IGNORED_TARGET_ENTRIES = /* @__PURE__ */ new Set([".DS_Store", "Thumbs.db"]);
12174
+ async function ensureEmptyTargetDir(dir) {
12175
+ try {
12176
+ const existing = await stat4(dir);
12177
+ if (!existing.isDirectory()) {
12178
+ throw new Error(`${dir} exists and is not a directory.`);
12179
+ }
12180
+ } catch (err) {
12181
+ const code = err.code;
12182
+ if (code !== "ENOENT") {
12183
+ throw err;
12184
+ }
12185
+ await mkdir8(dir, { recursive: true });
12186
+ return;
12187
+ }
12188
+ const entries = (await readdir(dir)).filter(
12189
+ (name) => !IGNORED_TARGET_ENTRIES.has(name)
12190
+ );
12191
+ if (entries.length > 0) {
12192
+ throw new Error(
12193
+ `Directory '${dir}' is not empty. Choose a new directory or remove existing files.`
12194
+ );
12195
+ }
12196
+ }
12167
12197
  async function init2(argv) {
12168
12198
  const dir = path40.resolve(process.cwd(), argv.dir ?? ".");
12169
12199
  try {
12200
+ await ensureEmptyTargetDir(dir);
12170
12201
  const createdPackageJson = await ensurePackageJson(dir);
12171
12202
  const createdTsconfig = await ensureTsconfigJson(dir);
12172
12203
  await ensurePortalStubFiles(dir);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lukoweb/apitogo",
3
- "version": "0.1.82",
3
+ "version": "0.1.84",
4
4
  "type": "module",
5
5
  "sideEffects": [
6
6
  "**/*.css",