@base44-preview/cli 0.1.32-pr.663.57b7b28 → 0.1.32-pr.663.7602773

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/README.md CHANGED
@@ -43,8 +43,9 @@ The CLI will guide you through project setup. For step-by-step tutorials, see th
43
43
 
44
44
  | Command | Description |
45
45
  | ------- | ----------- |
46
+ | `api catalog [area]` | List the API's areas, or every operation in one area |
46
47
  | `api search <text>` | Search every public Base44 API operation by what it does |
47
- | `api grep <pattern>` | Search the raw API spec with a regular expression |
48
+ | `api grep <pattern>` | Search the raw API spec with a regular expression; `--area` narrows it to one area |
48
49
  | `api fetch <METHOD> <path>` | Call any public Base44 API operation, like curl; `--help` after a path prints its contract |
49
50
  | [`create`](https://docs.base44.com/developers/references/cli/commands/create) | Create a new Base44 project from a template |
50
51
  | [`deploy`](https://docs.base44.com/developers/references/cli/commands/deploy) | Deploy all project resources and site to Base44 |
package/dist/cli/index.js CHANGED
@@ -248042,28 +248042,6 @@ function getAgentsCommand() {
248042
248042
  return new Command2("agents").description("Manage project agents").addCommand(getAgentsPushCommand()).addCommand(getAgentsPullCommand());
248043
248043
  }
248044
248044
 
248045
- // src/core/api-spec/body.ts
248046
- var METHODS_WITHOUT_BODY = new Set(["GET", "HEAD"]);
248047
- async function resolveRequestBody(method, flag, source) {
248048
- const takesBody = !METHODS_WITHOUT_BODY.has(method.toUpperCase());
248049
- if (flag !== undefined && !takesBody) {
248050
- throw new InvalidInputError(`${method.toUpperCase()} requests cannot have a body.`);
248051
- }
248052
- if (flag === "@-") {
248053
- return source.readStdin();
248054
- }
248055
- if (flag?.startsWith("@")) {
248056
- return readTextFile(flag.slice(1));
248057
- }
248058
- if (flag !== undefined) {
248059
- return flag;
248060
- }
248061
- if (!takesBody || source.stdinIsTTY) {
248062
- return;
248063
- }
248064
- const piped = await source.readStdin();
248065
- return piped.trim() ? piped : undefined;
248066
- }
248067
248045
  // ../../node_modules/minisearch/dist/es/index.js
248068
248046
  var ENTRIES = "ENTRIES";
248069
248047
  var KEYS = "KEYS";
@@ -249164,6 +249142,38 @@ function searchOperations(operations, query, options = {}) {
249164
249142
  });
249165
249143
  }
249166
249144
 
249145
+ // src/core/api-spec/catalog.ts
249146
+ var INLINE_AREA_MAX = 2;
249147
+ var AREA_SAMPLE_MAX = 3;
249148
+ var byCodePoint = (a, b) => a < b ? -1 : a > b ? 1 : 0;
249149
+ function areaOf(path) {
249150
+ const parts = path.split("/").filter(Boolean);
249151
+ const appIdIndex = parts.indexOf("{app_id}");
249152
+ if (appIdIndex !== -1 && appIdIndex + 1 < parts.length) {
249153
+ return parts[appIdIndex + 1] ?? "other";
249154
+ }
249155
+ if (parts[0] === "api" && parts.length > 1) {
249156
+ return parts[1] ?? "other";
249157
+ }
249158
+ return parts[0] ?? "other";
249159
+ }
249160
+ function groupByArea(operations) {
249161
+ const sorted = [...operations].sort((a, b) => byCodePoint(`${a.method} ${a.path}`, `${b.method} ${b.path}`));
249162
+ const areas = new Map;
249163
+ for (const op of sorted) {
249164
+ const area = areaOf(op.path);
249165
+ areas.set(area, [...areas.get(area) ?? [], op]);
249166
+ }
249167
+ return new Map([...areas].sort(([a], [b]) => byCodePoint(a, b)));
249168
+ }
249169
+ function catalogIndex(operations) {
249170
+ const areas = [...groupByArea(operations)].map(([area, ops]) => ops.length <= INLINE_AREA_MAX ? { area, operations: ops.map(toOperationSummary) } : {
249171
+ area,
249172
+ operationCount: ops.length,
249173
+ sample: ops.slice(0, AREA_SAMPLE_MAX).map((op) => op.summary)
249174
+ });
249175
+ return { areas, total: operations.length };
249176
+ }
249167
249177
  // src/core/api-spec/grep.ts
249168
249178
  var CONTEXT_CHARS = 40;
249169
249179
  var MAX_SNIPPETS = 3;
@@ -249183,13 +249193,15 @@ function snippets(text, pattern) {
249183
249193
  function grepSpec(spec, operations, pattern, options = {}) {
249184
249194
  const regex = new RegExp(pattern, options.ignoreCase ? "gi" : "g");
249185
249195
  const hits = [];
249186
- for (const op of operations) {
249196
+ const inArea = (op) => options.area === undefined || areaOf(op.path) === options.area;
249197
+ for (const op of operations.filter(inArea)) {
249187
249198
  const matches = snippets(`${op.method} ${op.path} ${JSON.stringify(op.operation)}`, regex);
249188
249199
  if (matches.length > 0) {
249189
249200
  hits.push({ ...toOperationSummary(op), matches });
249190
249201
  }
249191
249202
  }
249192
- for (const [schema, definition] of Object.entries(spec.components?.schemas ?? {})) {
249203
+ const schemas = options.area === undefined ? spec.components?.schemas : {};
249204
+ for (const [schema, definition] of Object.entries(schemas ?? {})) {
249193
249205
  const matches = snippets(JSON.stringify(definition), regex);
249194
249206
  if (matches.length > 0) {
249195
249207
  hits.push({ schema, matches });
@@ -249437,6 +249449,56 @@ function loadSpecTask({ runTask }, refresh) {
249437
249449
  successMessage: "Loaded the API spec"
249438
249450
  });
249439
249451
  }
249452
+ function operationsInArea(operations, area) {
249453
+ const areas = groupByArea(operations);
249454
+ const inArea = areas.get(area);
249455
+ if (!inArea) {
249456
+ throw new InvalidInputError(`Unknown API area: ${area}`, {
249457
+ details: [`Areas: ${[...areas.keys()].join(", ")}`],
249458
+ hints: [{ message: "List the areas", command: "base44 api catalog" }]
249459
+ });
249460
+ }
249461
+ return inArea;
249462
+ }
249463
+ async function readRequestBody(method, flag) {
249464
+ if (flag === "@-") {
249465
+ return readStdin("--body @-", { trim: false });
249466
+ }
249467
+ if (flag?.startsWith("@")) {
249468
+ return readTextFile(flag.slice(1));
249469
+ }
249470
+ if (flag !== undefined) {
249471
+ return flag;
249472
+ }
249473
+ if (method === "GET" || method === "HEAD" || process.stdin.isTTY) {
249474
+ return;
249475
+ }
249476
+ const piped = await readStdin("--body", { trim: false });
249477
+ return piped.trim() ? piped : undefined;
249478
+ }
249479
+
249480
+ // src/cli/commands/api/catalog.ts
249481
+ async function catalogAction(ctx, area, options) {
249482
+ const { spec } = await loadSpecTask(ctx, options.refresh);
249483
+ const operations = listOperations(spec);
249484
+ if (area === undefined) {
249485
+ return { stdout: formatJson(catalogIndex(operations)) };
249486
+ }
249487
+ const inArea = operationsInArea(operations, area);
249488
+ return {
249489
+ stdout: formatJson({
249490
+ area,
249491
+ operations: inArea.map(toOperationSummary),
249492
+ total: inArea.length
249493
+ })
249494
+ };
249495
+ }
249496
+ function getApiCatalogCommand() {
249497
+ return new Base44Command("catalog", {
249498
+ requireAuth: false,
249499
+ requireAppContext: false
249500
+ }).description("List the API's areas, or every operation in one area (same areas as the MCP bridge)").argument("[area]", 'An area from the list, e.g. "workflows"').option("--refresh", REFRESH_OPTION_HELP).action(catalogAction);
249501
+ }
249440
249502
 
249441
249503
  // src/cli/commands/api/fetch.ts
249442
249504
  async function findOperation(ctx, method, path, refresh) {
@@ -249462,12 +249524,6 @@ async function fetchAction(ctx, methodArg, path, options, command) {
249462
249524
  throw new InvalidInputError("Provide a method and a path, e.g. GET /api/apps.");
249463
249525
  }
249464
249526
  const method = methodArg.toUpperCase();
249465
- if (!HTTP_METHODS.some((m) => m.toUpperCase() === method)) {
249466
- throw new InvalidInputError(`Unknown HTTP method: ${methodArg}`);
249467
- }
249468
- if (!path.startsWith("/")) {
249469
- throw new InvalidInputError(`The path must start with "/", got ${path}.`);
249470
- }
249471
249527
  if (options.help) {
249472
249528
  const { spec, op } = await findOperation(ctx, method, path, options.refresh);
249473
249529
  return { stdout: formatJson(getOperationContract(spec, op)) };
@@ -249478,11 +249534,8 @@ async function fetchAction(ctx, methodArg, path, options, command) {
249478
249534
  throw new InvalidInputError(`Refused under --read-only: ${op.method} ${op.path} is not a read-only operation. Nothing was sent.`);
249479
249535
  }
249480
249536
  }
249481
- const body = await resolveRequestBody(method, options.body, {
249482
- stdinIsTTY: Boolean(process.stdin.isTTY),
249483
- readStdin: () => readStdin("--body @-", { trim: false })
249484
- });
249485
249537
  await ensureAuth(ctx);
249538
+ const body = await readRequestBody(method, options.body);
249486
249539
  const text = await ctx.runTask(`Calling ${method} ${path}`, () => sendApiRequest(method, path, body), { successMessage: `Called ${method} ${path}` });
249487
249540
  return { stdout: formatResponseBody(text) };
249488
249541
  }
@@ -249505,7 +249558,12 @@ async function grepAction(ctx, pattern, options) {
249505
249558
  const limit = parseLimit(options.limit);
249506
249559
  assertValidRegex(pattern);
249507
249560
  const { spec } = await loadSpecTask(ctx, options.refresh);
249508
- const hits = grepSpec(spec, listOperations(spec), pattern, {
249561
+ const operations = listOperations(spec);
249562
+ if (options.area !== undefined) {
249563
+ operationsInArea(operations, options.area);
249564
+ }
249565
+ const hits = grepSpec(spec, operations, pattern, {
249566
+ area: options.area,
249509
249567
  ignoreCase: options.ignoreCase,
249510
249568
  limit
249511
249569
  });
@@ -249515,7 +249573,7 @@ function getApiGrepCommand() {
249515
249573
  return new Base44Command("grep", {
249516
249574
  requireAuth: false,
249517
249575
  requireAppContext: false
249518
- }).description("Search the raw API spec with a regular expression, for when search misses").argument("<pattern>", 'Regular expression, e.g. "runs.*status"').option("-i, --ignore-case", "Case-insensitive match").option("--limit <n>", "Most operations or schemas to return (default 20)").option("--refresh", REFRESH_OPTION_HELP).action(grepAction);
249576
+ }).description("Search the raw API spec with a regular expression, for when search misses").argument("<pattern>", 'Regular expression, e.g. "runs.*status"').option("--area <area>", "Search only one area's operations (see base44 api catalog)").option("-i, --ignore-case", "Case-insensitive match").option("--limit <n>", "Most operations or schemas to return (default 20)").option("--refresh", REFRESH_OPTION_HELP).action(grepAction);
249519
249577
  }
249520
249578
 
249521
249579
  // src/cli/commands/api/search.ts
@@ -249537,7 +249595,7 @@ function getApiSearchCommand() {
249537
249595
 
249538
249596
  // src/cli/commands/api/index.ts
249539
249597
  function getApiCommand() {
249540
- return new Command2("api").description("Search and call any public Base44 API operation").addCommand(getApiSearchCommand()).addCommand(getApiGrepCommand()).addCommand(getApiFetchCommand());
249598
+ return new Command2("api").description("Search and call any public Base44 API operation").addCommand(getApiCatalogCommand()).addCommand(getApiSearchCommand()).addCommand(getApiGrepCommand()).addCommand(getApiFetchCommand());
249541
249599
  }
249542
249600
 
249543
249601
  // src/cli/commands/auth/password-login.ts
@@ -272902,4 +272960,4 @@ export {
272902
272960
  runCLI
272903
272961
  };
272904
272962
 
272905
- //# debugId=FA1E97B3DE15B20C64756E2164756E21
272963
+ //# debugId=9595882D8F2B0F6464756E2164756E21