@dereekb/dbx-cli 14.4.0 → 14.5.1

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.
@@ -1,11 +1,11 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli/eslint",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "type": "module",
6
6
  "peerDependencies": {
7
- "@dereekb/dbx-cli": "14.4.0",
8
- "@dereekb/util": "14.4.0",
7
+ "@dereekb/dbx-cli": "14.5.1",
8
+ "@dereekb/util": "14.5.1",
9
9
  "@typescript-eslint/utils": "8.69.0",
10
10
  "typescript": "6.0.3"
11
11
  },
@@ -1860,17 +1860,15 @@ function renderModelField(field, emitConverters) {
1860
1860
  // packages/dbx-cli/firebase-api-manifest/package.json
1861
1861
  var package_default = {
1862
1862
  name: "@dereekb/dbx-cli-firebase-api-manifest",
1863
- version: "14.4.0",
1863
+ version: "14.5.1",
1864
1864
  sideEffects: false,
1865
1865
  private: true,
1866
1866
  type: "module",
1867
- devDependencies: {
1868
- "ts-morph": "^28.0.0"
1869
- },
1870
1867
  peerDependencies: {
1871
- "@dereekb/dbx-cli": "14.4.0",
1872
- "@dereekb/util": "14.4.0",
1873
- oxfmt: "^0.66.0"
1868
+ "@dereekb/dbx-cli": "14.5.1",
1869
+ "@dereekb/util": "14.5.1",
1870
+ oxfmt: "^0.66.0",
1871
+ "ts-morph": "^28.0.0"
1874
1872
  }
1875
1873
  };
1876
1874
 
@@ -1,15 +1,13 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli-firebase-api-manifest",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "private": true,
6
6
  "type": "module",
7
- "devDependencies": {
8
- "ts-morph": "^28.0.0"
9
- },
10
7
  "peerDependencies": {
11
- "@dereekb/dbx-cli": "14.4.0",
12
- "@dereekb/util": "14.4.0",
13
- "oxfmt": "^0.66.0"
8
+ "@dereekb/dbx-cli": "14.5.1",
9
+ "@dereekb/util": "14.5.1",
10
+ "oxfmt": "^0.66.0",
11
+ "ts-morph": "^28.0.0"
14
12
  }
15
13
  }
@@ -2,6 +2,7 @@ export * from './firestore-indexes-generate';
2
2
  export * from './generate-firestore-indexes-cli';
3
3
  export * from './model-firebase-index-build-manifest';
4
4
  export * from './model-firebase-index-extract';
5
+ export * from './model-firebase-index-package-manifests';
5
6
  export * from './model-firebase-index-runtime';
6
7
  export * from './model-firebase-index-scan-config-schema';
7
8
  export * from './model-firebase-index-schema';
@@ -0,0 +1,135 @@
1
+ /**
2
+ * Loader for PRE-BUILT model-firebase-index manifests.
3
+ *
4
+ * `buildModelFirebaseIndexManifest` derives a manifest by parsing query-factory
5
+ * bodies with ts-morph, which only works against a scannable source tree. A
6
+ * published `@dereekb/*` tarball ships `.d.ts` only, so a downstream app cannot
7
+ * derive the framework models' indexes that way and is forced to hand-carry them
8
+ * in its own `firestore.indexes.json` — the gap that nearly dropped the `nbn`
9
+ * notification send-sweep composite in a production workspace.
10
+ *
11
+ * This module closes that gap from the other side: it reads the manifests the
12
+ * framework already generates at release time (`generate-manifests.mjs` writes
13
+ * them into `@dereekb/dbx-components-mcp`'s `generated/` directory) so
14
+ * `generate-firestore-indexes` can merge framework entries without any source to
15
+ * scan.
16
+ *
17
+ * Merge policy is intentionally ADDITIVE and unfiltered: every entry a package
18
+ * declares is emitted, whether or not the consuming app wires that collection.
19
+ * The two failure directions are not symmetric — an index for a collection the
20
+ * app never writes to holds no index entries, so it costs nothing, while a
21
+ * MISSING index breaks the query outright. Filtering to "collections this app
22
+ * wires" is also not the cheap text match it looks like: collection ids are
23
+ * framework constants that never appear literally in consumer source, and the
24
+ * wiring is split across the client model service and the separate server-only
25
+ * `firebaseModelServiceFactory` path. Any escape hatch added later should be an
26
+ * opt-OUT list, which fails safe, rather than an opt-in one, which does not.
27
+ *
28
+ * I/O is fully injectable so tests drive every branch without touching disk.
29
+ */
30
+ import type { Maybe } from '@dereekb/util';
31
+ import { type ScanReadFile } from '../../src/lib/scan-helpers/scan-io.js';
32
+ import { ModelFirebaseIndexManifest } from './model-firebase-index-schema.js';
33
+ /**
34
+ * Filename suffix every generated model-firebase-index manifest carries. The
35
+ * leading segment is the source package's slug (`dereekb-firebase`), so
36
+ * discovery matches on the suffix alone and picks up any package that starts
37
+ * publishing one without a code change here.
38
+ */
39
+ export declare const MODEL_FIREBASE_INDEX_MANIFEST_FILENAME_SUFFIX = ".model-firebase-index.mcp.generated.json";
40
+ /**
41
+ * Package that bundles the generated `@dereekb/*` manifests. The manifests do
42
+ * not ship inside each model-owning package (`@dereekb/firebase` and friends
43
+ * publish no JSON assets); `generate-manifests.mjs` collects them all into this
44
+ * one package's `generated/` directory, which is what actually gets published.
45
+ */
46
+ export declare const BUNDLED_MODEL_FIREBASE_INDEX_MANIFEST_PACKAGE = "@dereekb/dbx-components-mcp";
47
+ /**
48
+ * Function shape used to list a directory's entry names. Defaults to
49
+ * `node:fs/promises.readdir`.
50
+ */
51
+ export type ModelFirebaseIndexManifestReadDir = (absolutePath: string) => Promise<readonly string[]>;
52
+ /**
53
+ * Function shape used to locate the bundled manifest directory from the
54
+ * consuming workspace's cwd. Returns `null` when the bundling package is not
55
+ * installed.
56
+ */
57
+ export type ModelFirebaseIndexManifestDirectoryResolver = (cwd: string) => Maybe<string>;
58
+ /**
59
+ * One successfully loaded manifest plus the absolute path it came from. The
60
+ * path is retained so the CLI can name the offending file in diagnostics.
61
+ */
62
+ export interface LoadedModelFirebaseIndexManifest {
63
+ readonly path: string;
64
+ readonly manifest: ModelFirebaseIndexManifest;
65
+ }
66
+ /**
67
+ * Outcome of one {@link loadModelFirebaseIndexPackageManifests} call.
68
+ */
69
+ export type LoadModelFirebaseIndexPackageManifestsOutcome = {
70
+ readonly kind: 'success';
71
+ readonly loaded: readonly LoadedModelFirebaseIndexManifest[];
72
+ } | {
73
+ readonly kind: 'unreadable-manifest';
74
+ readonly path: string;
75
+ readonly error: string;
76
+ } | {
77
+ readonly kind: 'invalid-manifest';
78
+ readonly path: string;
79
+ readonly error: string;
80
+ } | {
81
+ readonly kind: 'no-bundled-package';
82
+ readonly packageName: string;
83
+ };
84
+ /**
85
+ * Input to {@link loadModelFirebaseIndexPackageManifests}.
86
+ */
87
+ export interface LoadModelFirebaseIndexPackageManifestsInput {
88
+ /**
89
+ * Working directory explicit `manifestPaths` resolve against, and the origin
90
+ * bundled-package resolution starts from.
91
+ */
92
+ readonly cwd: string;
93
+ /**
94
+ * Explicit manifest paths (cwd-relative or absolute). Loaded in the order
95
+ * given, ahead of any discovered bundled manifests.
96
+ */
97
+ readonly manifestPaths?: readonly string[];
98
+ /**
99
+ * When true, also discover every manifest bundled in the installed
100
+ * {@link BUNDLED_MODEL_FIREBASE_INDEX_MANIFEST_PACKAGE}.
101
+ */
102
+ readonly discoverBundled?: boolean;
103
+ readonly readFile?: ScanReadFile;
104
+ readonly readDir?: ModelFirebaseIndexManifestReadDir;
105
+ readonly resolveBundledDirectory?: ModelFirebaseIndexManifestDirectoryResolver;
106
+ }
107
+ /**
108
+ * Resolves the bundled manifest directory by asking Node to resolve the
109
+ * bundling package's `package.json` from the consuming workspace. Going through
110
+ * module resolution (rather than joining `node_modules` by hand) keeps this
111
+ * correct under hoisting and workspace layouts.
112
+ *
113
+ * @param cwd - Working directory the resolution originates from.
114
+ * @returns The absolute `generated/` directory, or null when the package is not installed.
115
+ */
116
+ export declare const defaultBundledManifestDirectoryResolver: ModelFirebaseIndexManifestDirectoryResolver;
117
+ /**
118
+ * Loads and validates pre-built model-firebase-index manifests from explicit
119
+ * paths and/or the installed bundling package. Never throws — every failure
120
+ * path returns a discriminated outcome the CLI renders as a diagnostic.
121
+ *
122
+ * @param input - Cwd, the manifest sources to load, and injectable I/O hooks.
123
+ * @returns The loaded manifests, or the first failure encountered.
124
+ */
125
+ export declare function loadModelFirebaseIndexPackageManifests(input: LoadModelFirebaseIndexPackageManifestsInput): Promise<LoadModelFirebaseIndexPackageManifestsOutcome>;
126
+ /**
127
+ * Renders a non-success outcome as a single actionable line, naming both the
128
+ * cause and the fix.
129
+ *
130
+ * @param outcome - The non-success load outcome.
131
+ * @returns A one-line description suitable for stderr.
132
+ */
133
+ export declare function formatModelFirebaseIndexPackageManifestFailure(outcome: Exclude<LoadModelFirebaseIndexPackageManifestsOutcome, {
134
+ kind: 'success';
135
+ }>): string;
@@ -9,7 +9,7 @@ import { isAbsolute as isAbsolute2, relative as relative2, resolve as resolve3 }
9
9
  // packages/dbx-cli/firestore-query-manifest/package.json
10
10
  var package_default = {
11
11
  name: "@dereekb/dbx-cli-firestore-query-manifest",
12
- version: "14.4.0",
12
+ version: "14.5.1",
13
13
  sideEffects: false,
14
14
  private: true,
15
15
  type: "module",
@@ -17,8 +17,8 @@ var package_default = {
17
17
  eslint: "10.9.1"
18
18
  },
19
19
  peerDependencies: {
20
- "@dereekb/dbx-cli": "14.4.0",
21
- "@dereekb/util": "14.4.0"
20
+ "@dereekb/dbx-cli": "14.5.1",
21
+ "@dereekb/util": "14.5.1"
22
22
  }
23
23
  };
24
24
 
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli-firestore-query-manifest",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "private": true,
6
6
  "type": "module",
@@ -8,7 +8,7 @@
8
8
  "eslint": "10.9.1"
9
9
  },
10
10
  "peerDependencies": {
11
- "@dereekb/dbx-cli": "14.4.0",
12
- "@dereekb/util": "14.4.0"
11
+ "@dereekb/dbx-cli": "14.5.1",
12
+ "@dereekb/util": "14.5.1"
13
13
  }
14
14
  }
@@ -5,7 +5,7 @@ const require = __createRequire(import.meta.url);
5
5
  // packages/dbx-cli/generate-firestore-indexes/package.json
6
6
  var package_default = {
7
7
  name: "@dereekb/dbx-cli-generate-firestore-indexes",
8
- version: "14.4.0",
8
+ version: "14.5.1",
9
9
  sideEffects: false,
10
10
  private: true,
11
11
  type: "module",
@@ -13,7 +13,7 @@ var package_default = {
13
13
  eslint: "10.9.1"
14
14
  },
15
15
  peerDependencies: {
16
- "@dereekb/dbx-cli": "14.4.0"
16
+ "@dereekb/dbx-cli": "14.5.1"
17
17
  }
18
18
  };
19
19
 
@@ -324,7 +324,7 @@ function computeDiff(input) {
324
324
 
325
325
  // packages/dbx-cli/firestore-indexes/src/generate-firestore-indexes-cli.ts
326
326
  import { readFile as nodeReadFile2, writeFile as nodeWriteFile } from "node:fs/promises";
327
- import { resolve as resolve2 } from "node:path";
327
+ import { resolve as resolve3 } from "node:path";
328
328
 
329
329
  // packages/dbx-cli/firestore-indexes/src/model-firebase-index-build-manifest.ts
330
330
  import { relative, resolve } from "node:path";
@@ -1063,10 +1063,10 @@ function collectParams(decl, descriptions) {
1063
1063
  for (const param of params) {
1064
1064
  const name = param.getName();
1065
1065
  const typeNode = param.getTypeNode()?.getText();
1066
- const type4 = typeNode ?? param.getType().getText() ?? "unknown";
1066
+ const type5 = typeNode ?? param.getType().getText() ?? "unknown";
1067
1067
  const description = descriptions.get(name) ?? "";
1068
1068
  const optional = param.isOptional() || param.hasInitializer();
1069
- out.push({ name, type: type4, description, optional });
1069
+ out.push({ name, type: type5, description, optional });
1070
1070
  }
1071
1071
  return out;
1072
1072
  }
@@ -2077,17 +2077,128 @@ function pushInto(map, key, entry) {
2077
2077
  }
2078
2078
  }
2079
2079
 
2080
+ // packages/dbx-cli/firestore-indexes/src/model-firebase-index-package-manifests.ts
2081
+ import { type as type4 } from "arktype";
2082
+ import { readdir as nodeReadDir } from "node:fs/promises";
2083
+ import { createRequire } from "node:module";
2084
+ import { dirname, resolve as resolve2 } from "node:path";
2085
+ var MODEL_FIREBASE_INDEX_MANIFEST_FILENAME_SUFFIX = ".model-firebase-index.mcp.generated.json";
2086
+ var BUNDLED_MODEL_FIREBASE_INDEX_MANIFEST_PACKAGE = "@dereekb/dbx-components-mcp";
2087
+ var BUNDLED_MANIFEST_DIRECTORY_NAME = "generated";
2088
+ var defaultBundledManifestDirectoryResolver = (cwd) => {
2089
+ let result2;
2090
+ try {
2091
+ const requireFromCwd = createRequire(resolve2(cwd, "noop.js"));
2092
+ const packageJsonPath = requireFromCwd.resolve(`${BUNDLED_MODEL_FIREBASE_INDEX_MANIFEST_PACKAGE}/package.json`);
2093
+ result2 = resolve2(dirname(packageJsonPath), BUNDLED_MANIFEST_DIRECTORY_NAME);
2094
+ } catch {
2095
+ result2 = null;
2096
+ }
2097
+ return result2;
2098
+ };
2099
+ var defaultReadDir = (path) => nodeReadDir(path);
2100
+ async function loadModelFirebaseIndexPackageManifests(input) {
2101
+ const { cwd, manifestPaths = [], discoverBundled = false, readFile = defaultReadFile, readDir = defaultReadDir, resolveBundledDirectory = defaultBundledManifestDirectoryResolver } = input;
2102
+ const paths = manifestPaths.map((path) => resolve2(cwd, path));
2103
+ let failure = null;
2104
+ if (discoverBundled) {
2105
+ const bundledDirectory = resolveBundledDirectory(cwd);
2106
+ if (bundledDirectory == null) {
2107
+ failure = { kind: "no-bundled-package", packageName: BUNDLED_MODEL_FIREBASE_INDEX_MANIFEST_PACKAGE };
2108
+ } else {
2109
+ paths.push(...await readBundledManifestPaths(bundledDirectory, readDir));
2110
+ }
2111
+ }
2112
+ const loaded = [];
2113
+ for (const path of paths) {
2114
+ if (failure != null) {
2115
+ break;
2116
+ }
2117
+ const readResult = await readManifestFile(path, readFile);
2118
+ if (readResult.kind === "ok") {
2119
+ loaded.push({ path, manifest: readResult.manifest });
2120
+ } else {
2121
+ failure = readResult.outcome;
2122
+ }
2123
+ }
2124
+ return failure ?? { kind: "success", loaded };
2125
+ }
2126
+ function formatModelFirebaseIndexPackageManifestFailure(outcome) {
2127
+ let result2;
2128
+ switch (outcome.kind) {
2129
+ case "unreadable-manifest":
2130
+ result2 = `could not read manifest at ${outcome.path} \u2014 ${outcome.error}`;
2131
+ break;
2132
+ case "invalid-manifest":
2133
+ result2 = `manifest at ${outcome.path} failed validation \u2014 ${outcome.error}`;
2134
+ break;
2135
+ default:
2136
+ result2 = `${outcome.packageName} is not installed, so no bundled index manifests could be discovered. Install it, or pass --manifest <path> explicitly.`;
2137
+ break;
2138
+ }
2139
+ return result2;
2140
+ }
2141
+ async function readBundledManifestPaths(directory, readDir) {
2142
+ let result2;
2143
+ try {
2144
+ const names = await readDir(directory);
2145
+ result2 = names.filter((name) => name.endsWith(MODEL_FIREBASE_INDEX_MANIFEST_FILENAME_SUFFIX)).toSorted().map((name) => resolve2(directory, name));
2146
+ } catch {
2147
+ result2 = [];
2148
+ }
2149
+ return result2;
2150
+ }
2151
+ async function readManifestFile(path, readFile) {
2152
+ let raw = null;
2153
+ let readError = null;
2154
+ try {
2155
+ raw = await readFile(path);
2156
+ } catch (err) {
2157
+ readError = err instanceof Error ? err.message : String(err);
2158
+ }
2159
+ let result2;
2160
+ if (raw == null) {
2161
+ result2 = { kind: "fail", outcome: { kind: "unreadable-manifest", path, error: readError ?? "unknown error" } };
2162
+ } else {
2163
+ let parsed;
2164
+ let parseError = null;
2165
+ try {
2166
+ parsed = JSON.parse(raw);
2167
+ } catch (err) {
2168
+ parseError = err instanceof Error ? err.message : String(err);
2169
+ }
2170
+ if (parseError == null) {
2171
+ const validated = ModelFirebaseIndexManifest(parsed);
2172
+ if (validated instanceof type4.errors) {
2173
+ result2 = { kind: "fail", outcome: { kind: "invalid-manifest", path, error: validated.summary } };
2174
+ } else {
2175
+ result2 = { kind: "ok", manifest: validated };
2176
+ }
2177
+ } else {
2178
+ result2 = { kind: "fail", outcome: { kind: "invalid-manifest", path, error: parseError } };
2179
+ }
2180
+ }
2181
+ return result2;
2182
+ }
2183
+
2080
2184
  // packages/dbx-cli/firestore-indexes/src/generate-firestore-indexes-cli.ts
2081
2185
  var DEFAULT_BIN_NAME = "dbx-cli-generate-firestore-indexes";
2082
2186
  function buildUsage(binName) {
2083
2187
  return [
2084
- `Usage: ${binName} --component <dir> [--component <dir> ...] [--output <path>] [--check] [--json] [--help]`,
2188
+ `Usage: ${binName} [--component <dir> ...] [--packages] [--manifest <path> ...] [--output <path>] [--check] [--json] [--help]`,
2085
2189
  "",
2086
2190
  "Generates `firestore.indexes.json` from `@dbxModelFirebaseIndex`-tagged factories.",
2087
2191
  "",
2088
2192
  "Options:",
2089
- " --component <dir> Required, repeatable. Relative path to a `-firebase` component or package.",
2090
- " Repeat to derive one indexes file from several packages at once.",
2193
+ " --component <dir> Repeatable. Relative path to a `-firebase` component or package whose",
2194
+ " source is scanned for tagged factories. Repeat to derive one indexes",
2195
+ " file from several packages at once.",
2196
+ " --packages Also merge the pre-built index manifests bundled in the installed",
2197
+ " @dereekb/dbx-components-mcp. Lets an app derive the framework models\u2019",
2198
+ " indexes without a scannable copy of their source.",
2199
+ " --manifest <path> Repeatable. Merge a specific pre-built manifest JSON file.",
2200
+ "",
2201
+ " At least one of --component / --packages / --manifest is required.",
2091
2202
  " --output <path> Output path. Defaults to `firestore.indexes.json` at the cwd.",
2092
2203
  " --check Compare against the on-disk file; exit 1 on drift, do not write.",
2093
2204
  " --json Print the diff summary as JSON instead of human-readable text.",
@@ -2107,18 +2218,18 @@ async function runGenerateFirestoreIndexesCli(input) {
2107
2218
  stderr(usage);
2108
2219
  return { exitCode: 2 };
2109
2220
  }
2110
- if (parsed.components.length === 0) {
2111
- stderr("generate-firestore-indexes: --component is required");
2221
+ if (parsed.components.length === 0 && parsed.manifests.length === 0 && !parsed.packages) {
2222
+ stderr("generate-firestore-indexes: at least one of --component / --packages / --manifest is required");
2112
2223
  stderr(usage);
2113
2224
  return { exitCode: 2 };
2114
2225
  }
2115
- const outputAbs = resolve2(cwd, parsed.output);
2226
+ const outputAbs = resolve3(cwd, parsed.output);
2116
2227
  const entries = [];
2117
2228
  const loadedSources = [];
2118
2229
  let sawUnresolvedModel = false;
2119
2230
  for (const component of parsed.components) {
2120
2231
  const buildOutcome = await buildModelFirebaseIndexManifest({
2121
- projectRoot: resolve2(cwd, component),
2232
+ projectRoot: resolve3(cwd, component),
2122
2233
  generator
2123
2234
  });
2124
2235
  if (buildOutcome.kind !== "success") {
@@ -2136,6 +2247,15 @@ async function runGenerateFirestoreIndexesCli(input) {
2136
2247
  }
2137
2248
  loadedSources.push(buildOutcome.manifest.source);
2138
2249
  }
2250
+ if (parsed.packages || parsed.manifests.length > 0) {
2251
+ const merged = await collectPackageManifestEntries({ cwd, manifestPaths: parsed.manifests, discoverBundled: parsed.packages, readFile });
2252
+ if (merged.kind === "fail") {
2253
+ stderr(merged.message);
2254
+ return { exitCode: 1 };
2255
+ }
2256
+ entries.push(...merged.entries);
2257
+ loadedSources.push(...merged.sources);
2258
+ }
2139
2259
  if (sawUnresolvedModel) {
2140
2260
  stderr("generate-firestore-indexes: one or more @dbxModelFirebaseIndexModel tags could not be resolved, so their indexes were dropped. Add the missing identity file to the component\u2019s `dbx-mcp.scan.json` include globs.");
2141
2261
  return { exitCode: 1 };
@@ -2162,8 +2282,29 @@ async function runGenerateFirestoreIndexesCli(input) {
2162
2282
  }
2163
2283
  return { exitCode: 0 };
2164
2284
  }
2285
+ async function collectPackageManifestEntries(input) {
2286
+ const { cwd, manifestPaths, discoverBundled, readFile } = input;
2287
+ const outcome = await loadModelFirebaseIndexPackageManifests({ cwd, manifestPaths, discoverBundled, readFile });
2288
+ let result2;
2289
+ if (outcome.kind === "success") {
2290
+ const entries = [];
2291
+ const sources = [];
2292
+ for (const { manifest } of outcome.loaded) {
2293
+ for (const entry of manifest.entries) {
2294
+ entries.push(toModelFirebaseIndexEntryInfo(entry));
2295
+ }
2296
+ sources.push(manifest.source);
2297
+ }
2298
+ result2 = { kind: "ok", entries, sources };
2299
+ } else {
2300
+ result2 = { kind: "fail", message: `generate-firestore-indexes: ${formatModelFirebaseIndexPackageManifestFailure(outcome)}` };
2301
+ }
2302
+ return result2;
2303
+ }
2165
2304
  function parseArgv(argv) {
2166
2305
  const components = [];
2306
+ const manifests = [];
2307
+ let packages = false;
2167
2308
  let output = "firestore.indexes.json";
2168
2309
  let check = false;
2169
2310
  let json = false;
@@ -2181,6 +2322,17 @@ function parseArgv(argv) {
2181
2322
  components.push(argv[i]);
2182
2323
  }
2183
2324
  break;
2325
+ case "--manifest":
2326
+ i += 1;
2327
+ if (i >= argv.length) {
2328
+ error = "generate-firestore-indexes: --manifest requires a value";
2329
+ } else {
2330
+ manifests.push(argv[i]);
2331
+ }
2332
+ break;
2333
+ case "--packages":
2334
+ packages = true;
2335
+ break;
2184
2336
  case "--output":
2185
2337
  i += 1;
2186
2338
  if (i >= argv.length) {
@@ -2205,7 +2357,7 @@ function parseArgv(argv) {
2205
2357
  }
2206
2358
  i += 1;
2207
2359
  }
2208
- return { components, output, check, json, help, error };
2360
+ return { components, manifests, packages, output, check, json, help, error };
2209
2361
  }
2210
2362
  async function readExistingIndexes(input) {
2211
2363
  const text = await readExistingIndexesText(input);
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli-generate-firestore-indexes",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "private": true,
6
6
  "type": "module",
@@ -8,6 +8,6 @@
8
8
  "eslint": "10.9.1"
9
9
  },
10
10
  "peerDependencies": {
11
- "@dereekb/dbx-cli": "14.4.0"
11
+ "@dereekb/dbx-cli": "14.5.1"
12
12
  }
13
13
  }
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli-generate-mcp-manifest",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "private": true,
6
6
  "type": "module",
7
7
  "peerDependencies": {
8
- "@dereekb/dbx-cli": "14.4.0",
9
- "@dereekb/model": "14.4.0",
8
+ "@dereekb/dbx-cli": "14.5.1",
9
+ "@dereekb/model": "14.5.1",
10
10
  "arktype": "^2.2.0",
11
11
  "jiti": "2.7.0"
12
12
  }
@@ -1,11 +1,11 @@
1
1
  {
2
2
  "name": "@dereekb/dbx-cli-generate-route-manifest",
3
- "version": "14.4.0",
3
+ "version": "14.5.1",
4
4
  "sideEffects": false,
5
5
  "private": true,
6
6
  "type": "module",
7
7
  "peerDependencies": {
8
- "@dereekb/dbx-cli": "14.4.0",
8
+ "@dereekb/dbx-cli": "14.5.1",
9
9
  "ts-morph": "^28.0.0"
10
10
  }
11
11
  }