fyn 3.1.5 → 3.1.7

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/fyn.mjs +181 -75
  2. package/package.json +4 -4
package/dist/fyn.mjs CHANGED
@@ -27044,8 +27044,6 @@ function processDir(options, extras) {
27044
27044
  */
27045
27045
  function processFile(options, extras) {
27046
27046
  if (!options.includeDir && !options.includeSymlink && extras.stat && extras.stat.isSymbolicLink && extras.stat.isSymbolicLink()) return false;
27047
- if (options.ignoreExt.length > 0 && options.ignoreExt.indexOf(extras.ext) >= 0) return false;
27048
- if (options.filterExt.length > 0 && options.filterExt.indexOf(extras.ext) < 0) return false;
27049
27047
  const filterResult = options.filter ? options.filter(extras.file, extras.path, extras) : true;
27050
27048
  if (filterResult) {
27051
27049
  if (filterResult.skip !== true) addResult(filterResult, options, extras);
@@ -27053,6 +27051,19 @@ function processFile(options, extras) {
27053
27051
  }
27054
27052
  return false;
27055
27053
  }
27054
+ function acceptEntry(options, entry, path) {
27055
+ const isDirectory = entry.isDirectory();
27056
+ if (isDirectory && options._ignoreDirs.has(entry.name)) return false;
27057
+ if (options.prefilter && !options.prefilter(entry.name, path, entry)) return false;
27058
+ if (isDirectory) return true;
27059
+ if (options.ignoreExt.length || options.filterExt.length) {
27060
+ const ix = entry.name.lastIndexOf(".");
27061
+ const ext = ix > 0 ? entry.name.substring(ix) : "";
27062
+ if (options.ignoreExt.indexOf(ext) >= 0) return false;
27063
+ if (options.filterExt.length && options.filterExt.indexOf(ext) < 0) return false;
27064
+ }
27065
+ return true;
27066
+ }
27056
27067
  /**
27057
27068
  * get the result base on grouping enable flag
27058
27069
  *
@@ -27060,10 +27071,23 @@ function processFile(options, extras) {
27060
27071
  * @returns
27061
27072
  */
27062
27073
  function getResult(options) {
27063
- return options.grouping ? Object.assign({ files: [] }, options.result) : options.result.files || [];
27074
+ return options.grouping ? {
27075
+ files: [],
27076
+ ...options.result
27077
+ } : options.result.files || [];
27064
27078
  }
27065
27079
  const asyncReaddir = Util.promisify(fs.readdir);
27066
27080
  const asyncLStat = Util.promisify(fs.lstat);
27081
+ function releaseDirectory(options) {
27082
+ if (options._waitIndex < options._waiting.length) {
27083
+ const resume = options._waiting[options._waitIndex++];
27084
+ if (options._waitIndex === options._waiting.length) {
27085
+ options._waiting = [];
27086
+ options._waitIndex = 0;
27087
+ }
27088
+ resume();
27089
+ } else options._concurrentCount--;
27090
+ }
27067
27091
  /**
27068
27092
  * async version of dir walk
27069
27093
  *
@@ -27073,59 +27097,73 @@ const asyncLStat = Util.promisify(fs.lstat);
27073
27097
  * @returns
27074
27098
  */
27075
27099
  async function walk(path, options, level = 0) {
27100
+ let promises = [];
27101
+ let hasSlot = false;
27076
27102
  try {
27103
+ if (options.concurrency > 1) {
27104
+ if (options._concurrentCount >= options.concurrency) await new Promise((resolve) => options._waiting.push(resolve));
27105
+ else options._concurrentCount++;
27106
+ hasSlot = true;
27107
+ }
27108
+ if (options._stopped) return void 0;
27077
27109
  const dir = Path.join(options.dir, path);
27078
27110
  let files = await asyncReaddir(dir, options.readdirOpts);
27079
27111
  if (options.sortFiles) {
27080
- if (options.fullStat) files = files.sort();
27112
+ if (!options.readdirOpts) files = files.sort();
27081
27113
  else files = files.sort(direntCmp);
27082
27114
  }
27083
27115
  const dirs = [];
27084
- let stop = false;
27085
- for (let ix = 0; !stop && ix < files.length; ix++) {
27116
+ const extrasFiles = options.fullStat && options._earlyFilter && (options.filter || options.filterDir) ? files.map((entry) => entry.name) : files;
27117
+ for (let ix = 0; !options._stopped && ix < files.length; ix++) {
27086
27118
  const file = files[ix];
27119
+ if (options._earlyFilter && !acceptEntry(options, file, path)) continue;
27087
27120
  let extras;
27088
27121
  if (options.fullStat) {
27089
- const fullFile = join2(options._sep, dir, file);
27090
- extras = makeExtrasData(file, fullFile, path, await asyncLStat(fullFile), files, options);
27122
+ const name = options._earlyFilter ? file.name : file;
27123
+ const fullFile = join2(options._sep, dir, name);
27124
+ const stat = await asyncLStat(fullFile);
27125
+ if (options._stopped) break;
27126
+ extras = makeExtrasData(name, fullFile, path, stat, extrasFiles, options);
27091
27127
  } else {
27092
27128
  const fullFile = join2(options._sep, dir, file.name);
27093
27129
  extras = makeExtrasData(file.name, fullFile, path, file, files, options);
27094
27130
  }
27095
27131
  if (extras.stat.isDirectory()) dirs.push(extras);
27096
- else stop = processFile(options, extras);
27097
- }
27098
- if (!stop && dirs.length > 0) {
27099
- let promises = [];
27100
- for (let ix = 0; ix < dirs.length; ix++) {
27101
- const extras = dirs[ix];
27102
- const flags = processDir(options, extras);
27103
- if (flags.stop) break;
27104
- if (!flags.skip && level < options.maxLevel) {
27105
- const walkP = walk(extras.dirFile, options, level + 1);
27106
- if (options.concurrency > 1) {
27107
- if (options._concurrentCount < options.concurrency) {
27108
- options._concurrentCount++;
27109
- promises.push(walkP);
27110
- } else if (promises.length) {
27111
- await Promise.all(promises);
27112
- options._concurrentCount -= promises.length;
27113
- promises = [walkP];
27114
- options._concurrentCount++;
27115
- } else await walkP;
27116
- } else await walkP;
27117
- }
27118
- }
27119
- if (promises.length) {
27120
- await Promise.all(promises);
27121
- options._concurrentCount -= promises.length;
27122
- promises = [];
27132
+ else options._stopped = !!processFile(options, extras);
27133
+ }
27134
+ if (hasSlot) {
27135
+ releaseDirectory(options);
27136
+ hasSlot = false;
27137
+ }
27138
+ if (!options._stopped && dirs.length > 0) for (let ix = 0; !options._stopped && ix < dirs.length; ix++) {
27139
+ const extras = dirs[ix];
27140
+ const flags = processDir(options, extras);
27141
+ if (flags.stop) {
27142
+ options._stopped = true;
27143
+ break;
27144
+ }
27145
+ if (!flags.skip && level < options.maxLevel) {
27146
+ const walkP = walk(extras.dirFile, options, level + 1);
27147
+ if (options.concurrency > 1) {
27148
+ promises.push(walkP);
27149
+ if (promises.length >= options.concurrency) {
27150
+ await Promise.all(promises);
27151
+ promises = [];
27152
+ }
27153
+ } else await walkP;
27123
27154
  }
27124
27155
  }
27125
27156
  } catch (err) {
27126
- if (options.rethrowError) throw err;
27157
+ if (options.rethrowError) {
27158
+ if (!options._error) options._error = { cause: err };
27159
+ options._stopped = true;
27160
+ }
27161
+ } finally {
27162
+ if (hasSlot) releaseDirectory(options);
27163
+ if (promises.length) await Promise.all(promises);
27127
27164
  }
27128
- return getResult(options);
27165
+ if (level === 0 && options._error) throw options._error.cause;
27166
+ return level === 0 ? getResult(options) : void 0;
27129
27167
  }
27130
27168
  /**
27131
27169
  * make a copy of the user's options with proper defaults
@@ -27135,6 +27173,7 @@ async function walk(path, options, level = 0) {
27135
27173
  */
27136
27174
  function makeOptions(opts) {
27137
27175
  const options = typeof opts === "string" ? { cwd: opts } : opts;
27176
+ if (options.prefilter && options.fullStat === false) throw new TypeError("prefilter requires fullStat: true");
27138
27177
  const sep = options.pathSep || Path.posix.sep;
27139
27178
  let cwd = options.cwd || options.dir || process.cwd();
27140
27179
  if (!options.hasOwnProperty("pathSep") && cwd.includes("\\")) cwd = cwd.replace(/\\/g, "/");
@@ -27156,12 +27195,20 @@ function makeOptions(opts) {
27156
27195
  grouping: void 0
27157
27196
  }, options, {
27158
27197
  dir: cwd,
27159
- result: {},
27198
+ fullStat: options.fullStat === void 0 ? true : options.fullStat,
27199
+ result: Object.create(null),
27160
27200
  ignoreExt: [].concat(options.ignoreExt).map(cleanExt).filter((x) => x),
27161
27201
  filterExt: [].concat(options.filterExt).map(cleanExt).filter((x) => x),
27162
- _concurrentCount: 0
27202
+ _concurrentCount: 0,
27203
+ _waiting: [],
27204
+ _waitIndex: 0,
27205
+ _stopped: false,
27206
+ _error: void 0,
27207
+ _earlyFilter: false,
27208
+ _ignoreDirs: new Set([].concat(options.ignoreDirs || []))
27163
27209
  });
27164
- if (!opts2.fullStat) opts2.readdirOpts = { withFileTypes: true };
27210
+ opts2._earlyFilter = !!opts2.prefilter || opts2._ignoreDirs.size > 0 || opts2.ignoreExt.length > 0 || opts2.filterExt.length > 0;
27211
+ if (!opts2.fullStat || opts2._earlyFilter) opts2.readdirOpts = { withFileTypes: true };
27165
27212
  return opts2;
27166
27213
  }
27167
27214
  function filterScanDir(options = {}) {
@@ -28788,18 +28835,21 @@ const asPathRef = (ref) => REF_TYPES.some((t) => ref.startsWith(t)) ? ref : `pat
28788
28835
  const resolveAutoSearch = (val) => {
28789
28836
  if (val === false) return {
28790
28837
  enable: false,
28791
- respectGitignore: false
28838
+ respectGitignore: false,
28839
+ stopOnPackageJsonFound: false
28792
28840
  };
28793
28841
  if (val && typeof val === "object") {
28794
28842
  const obj = val;
28795
28843
  return {
28796
28844
  enable: obj.enable !== false,
28797
- respectGitignore: obj.respectGitignore === true
28845
+ respectGitignore: obj.respectGitignore === true,
28846
+ stopOnPackageJsonFound: obj.stopOnPackageJsonFound === true
28798
28847
  };
28799
28848
  }
28800
28849
  return {
28801
28850
  enable: true,
28802
- respectGitignore: false
28851
+ respectGitignore: false,
28852
+ stopOnPackageJsonFound: false
28803
28853
  };
28804
28854
  };
28805
28855
  /**
@@ -28823,7 +28873,8 @@ function resolvePackagesConfig(packages) {
28823
28873
  return {
28824
28874
  autoSearch: {
28825
28875
  enable: true,
28826
- respectGitignore: false
28876
+ respectGitignore: false,
28877
+ stopOnPackageJsonFound: false
28827
28878
  },
28828
28879
  include: list,
28829
28880
  exclude: [],
@@ -29685,7 +29736,7 @@ var FynpoDepGraph = class {
29685
29736
  groups = groupMM(mms, {});
29686
29737
  }
29687
29738
  const foundInAutoSearch = (path) => {
29688
- if (!autoSearch) return false;
29739
+ if (!autoSearch || !pkgConfig.autoSearch.stopOnPackageJsonFound) return false;
29689
29740
  for (const e of autoSearchFound) if (isPathInside$1(path, e)) return true;
29690
29741
  return false;
29691
29742
  };
@@ -29714,8 +29765,36 @@ var FynpoDepGraph = class {
29714
29765
  });
29715
29766
  files.push(scanned);
29716
29767
  }
29717
- const allFiles = [].concat(...files).filter((f) => isIncluded(Path.dirname(f))).sort();
29718
- for (const pkgFile of allFiles) await this.addPackageByFile(pkgFile);
29768
+ const filesByDepth = [...[].concat(...files)].sort((a, b) => {
29769
+ const depth = (file) => posixify$2(Path.dirname(file)).split("/").length;
29770
+ return depth(a) - depth(b) || a.localeCompare(b);
29771
+ });
29772
+ const packageRoots = [];
29773
+ const accepted = [];
29774
+ for (const pkgFile of filesByDepth) {
29775
+ const pkgPath = posixify$2(Path.dirname(pkgFile));
29776
+ const nested = autoSearch && packageRoots.some((root) => isPathInside$1(pkgPath, root));
29777
+ const included = isIncluded(pkgPath);
29778
+ if (!included && !nested) continue;
29779
+ const managed = !autoSearch || !nested || includeMms.length > 0 && included;
29780
+ const pkgStr = await promises.readFile(Path.join(cwd, pkgFile), "utf-8");
29781
+ const pkgJson = JSON.parse(pkgStr);
29782
+ if (pkgJson.fynpo === false) continue;
29783
+ if (!pkgJson.name) continue;
29784
+ accepted.push({
29785
+ pkgFile,
29786
+ pkgPath,
29787
+ pkgStr,
29788
+ pkgJson,
29789
+ managed,
29790
+ nested
29791
+ });
29792
+ packageRoots.push(pkgPath);
29793
+ }
29794
+ for (const pkg of accepted.sort((a, b) => a.pkgFile.localeCompare(b.pkgFile))) this.addPackage(pkg.pkgJson, pkg.pkgPath, pkg.pkgStr, {
29795
+ managed: pkg.managed,
29796
+ nested: pkg.nested
29797
+ });
29719
29798
  this.updateAuxPackageData();
29720
29799
  return this.packages;
29721
29800
  }
@@ -29724,10 +29803,10 @@ var FynpoDepGraph = class {
29724
29803
  *
29725
29804
  * @param pkgFile - path to the package.json file
29726
29805
  */
29727
- async addPackageByFile(pkgFile) {
29806
+ async addPackageByFile(pkgFile, management = {}) {
29728
29807
  const pkgStr = await promises.readFile(Path.join(this._options.cwd, pkgFile), "utf-8");
29729
29808
  const pkgJson = JSON.parse(pkgStr);
29730
- this.addPackage(pkgJson, Path.dirname(pkgFile), pkgStr);
29809
+ return this.addPackage(pkgJson, posixify$2(Path.dirname(pkgFile)), pkgStr, management);
29731
29810
  }
29732
29811
  /**
29733
29812
  * Add a package to the graph using the data from its package.json
@@ -29737,7 +29816,7 @@ var FynpoDepGraph = class {
29737
29816
  * @param pkgStr - string form of package.json
29738
29817
  * @returns
29739
29818
  */
29740
- addPackage(pkgJson, pkgPath, pkgStr) {
29819
+ addPackage(pkgJson, pkgPath, pkgStr, management = {}) {
29741
29820
  if (pkgJson.fynpo === false) return;
29742
29821
  assert(pkgJson.name, `package at ${pkgPath} doesn't have name`);
29743
29822
  const pkgDir = pkgJson.name[0] === "@" && (pkgPath.endsWith(`/${pkgJson.name}`) || pkgPath === pkgJson.name) ? pkgJson.name : Path.basename(pkgPath);
@@ -29758,11 +29837,20 @@ var FynpoDepGraph = class {
29758
29837
  };
29759
29838
  Object.defineProperties(pkgInfo, {
29760
29839
  pkgStr: { enumerable: false },
29761
- pkgJson: { enumerable: false }
29840
+ pkgJson: { enumerable: false },
29841
+ managed: {
29842
+ value: management.managed !== false,
29843
+ enumerable: false
29844
+ },
29845
+ nested: {
29846
+ value: management.nested === true,
29847
+ enumerable: false
29848
+ }
29762
29849
  });
29763
29850
  const { byName } = this.packages;
29764
29851
  if (byName[pkgJson.name]) byName[pkgJson.name].push(pkgInfo);
29765
29852
  else byName[pkgJson.name] = [pkgInfo];
29853
+ return pkgInfo;
29766
29854
  }
29767
29855
  /**
29768
29856
  * update auxiliary package data
@@ -29776,11 +29864,17 @@ var FynpoDepGraph = class {
29776
29864
  this.packages.byPath = {};
29777
29865
  const { byName, byPath, byId } = this.packages;
29778
29866
  for (const name in byName) {
29867
+ byName[name].sort((a, b) => {
29868
+ const versionOrder = import_semver.default.compare(b.version, a.version);
29869
+ if (versionOrder !== 0) return versionOrder;
29870
+ if (a.managed !== b.managed) return a.managed === false ? 1 : -1;
29871
+ return a.path.localeCompare(b.path);
29872
+ });
29779
29873
  byName[name].forEach((pkg) => {
29780
29874
  byPath[pkg.path] = pkg;
29781
- byId[`${pkg.name}@${pkg.version}`] = pkg;
29875
+ const id = `${pkg.name}@${pkg.version}`;
29876
+ if (!byId[id] || byId[id].managed === false && pkg.managed !== false) byId[id] = pkg;
29782
29877
  });
29783
- if (byName[name].length > 1) byName[name].sort((a, b) => import_semver.default.compare(b.version, a.version));
29784
29878
  }
29785
29879
  }
29786
29880
  /**
@@ -29847,8 +29941,8 @@ var FynpoDepGraph = class {
29847
29941
  localDepsByPath: Object.create(null),
29848
29942
  dependentsByPath: Object.create(null)
29849
29943
  };
29850
- for (const id in byId) {
29851
- const pkgInfo = byId[id];
29944
+ for (const path in byPath) {
29945
+ const pkgInfo = byPath[path];
29852
29946
  const depData = depMapByPath[pkgInfo.path];
29853
29947
  doResolve(depData, pkgInfo.dependencies, "dep");
29854
29948
  doResolve(depData, pkgInfo.devDependencies, "dev");
@@ -102357,7 +102451,6 @@ function createAbortError(context) {
102357
102451
  return err;
102358
102452
  }
102359
102453
  function lastLines(text, n) {
102360
- if (!text) return [];
102361
102454
  return text.split("\n").filter(Boolean).slice(-n);
102362
102455
  }
102363
102456
  function enhanceError(err, context) {
@@ -102446,12 +102539,11 @@ var VisualExec = class {
102446
102539
  if (typeof command !== "string") command = "user command";
102447
102540
  return `Running ${command}`;
102448
102541
  }
102449
- _createOutputFileStream() {
102450
- if (typeof this._outputFile !== "string") return void 0;
102542
+ _createOutputFileStream(outputFile) {
102451
102543
  const flags = this._outputFileOptions.append ? "a" : "w";
102452
- const dir = Path$1.dirname(this._outputFile);
102544
+ const dir = Path$1.dirname(outputFile);
102453
102545
  if (!fs$2.existsSync(dir)) fs$2.mkdirSync(dir, { recursive: true });
102454
- return fs$2.createWriteStream(this._outputFile, { flags });
102546
+ return fs$2.createWriteStream(outputFile, { flags });
102455
102547
  }
102456
102548
  _writeToOutputFile(data, stream) {
102457
102549
  var _a;
@@ -102571,7 +102663,7 @@ var VisualExec = class {
102571
102663
  child.stdout.on("data", this._onStdoutData);
102572
102664
  child.stderr.on("data", this._onStderrData);
102573
102665
  this._child = child;
102574
- if (typeof this._outputFile === "string") this._outputStream = this._createOutputFileStream();
102666
+ if (typeof this._outputFile === "string") this._outputStream = this._createOutputFileStream(this._outputFile);
102575
102667
  else if (this._outputFile) this._outputStream = void 0;
102576
102668
  let timeoutId;
102577
102669
  const startTime = Date.now();
@@ -102707,6 +102799,7 @@ var VisualExec = class {
102707
102799
  child: result.child
102708
102800
  };
102709
102801
  const duration = () => Date.now() - this._startTime;
102802
+ /* v8 ignore next -- @preserve Every field is overwritten in the context below. */
102710
102803
  const baseContext = (output) => {
102711
102804
  var _a, _b, _c, _d;
102712
102805
  return {
@@ -102726,7 +102819,8 @@ var VisualExec = class {
102726
102819
  stderr: ""
102727
102820
  };
102728
102821
  const exitCode = (_c = err.code) !== null && _c !== void 0 ? _c : 1;
102729
- const signal = (_e = (_d = err.signal) !== null && _d !== void 0 ? _d : ((_a = result.child) === null || _a === void 0 ? void 0 : _a.killed) ? "SIGTERM" : null) !== null && _e !== void 0 ? _e : null;
102822
+ const signal = (_e = (_d = err.signal) !== null && _d !== void 0 ? _d : ((_a = result.child) === null || _a === void 0 ? void 0 : _a.killed) ? "SIGTERM" : null) !== null && _e !== void 0 ? _e :
102823
+ /* v8 ignore next -- @preserve The preceding fallback already returns null. */ null;
102730
102824
  const context = {
102731
102825
  ...baseContext(output),
102732
102826
  exitCode,
@@ -114834,7 +114928,7 @@ async function _internalCheck(options) {
114834
114928
  const existMeta = await readMetaFile();
114835
114929
  const shouldFetch = now - existMeta.time >= checkInterval || !existMeta.distTags;
114836
114930
  const distTags = shouldFetch ? await fetchDistTags() : existMeta.distTags;
114837
- const saveMetaFile = async (notifiedVersion = "", notifiedTime = 0) => {
114931
+ const saveMetaFile = async (notifiedVersion = "", notifiedTime) => {
114838
114932
  await promises.writeFile(metaFile, JSON.stringify({
114839
114933
  ...pkg,
114840
114934
  distTags,
@@ -115883,6 +115977,7 @@ var CliBase = class {
115883
115977
  required,
115884
115978
  name,
115885
115979
  type,
115980
+ array: xm[4] ? true : void 0,
115886
115981
  variadic,
115887
115982
  min,
115888
115983
  max
@@ -116019,9 +116114,9 @@ var Options = class {
116019
116114
  match(data) {
116020
116115
  const alias = data.name;
116021
116116
  let name;
116022
- let option = this._options[alias];
116117
+ let option = Object.hasOwn(this._options, alias) ? this._options[alias] : void 0;
116023
116118
  if (option) name = alias;
116024
- else if (this._optAlias[alias]) {
116119
+ else if (Object.hasOwn(this._optAlias, alias)) {
116025
116120
  name = this._optAlias[alias];
116026
116121
  option = this._options[name];
116027
116122
  } else return false;
@@ -116154,7 +116249,7 @@ var CommandBase = class CommandBase extends CliBase {
116154
116249
  */
116155
116250
  setCommandAliases(alias, name) {
116156
116251
  alias.forEach((a) => {
116157
- if (this.subAliases[a]) throw new Error(`Command ${name} alias ${a} already used by command ${this.subAliases[a]}`);
116252
+ if (Object.hasOwn(this.subAliases, a)) throw new Error(`Command ${name} alias ${a} already used by command ${this.subAliases[a]}`);
116158
116253
  this.subAliases[a] = name;
116159
116254
  });
116160
116255
  }
@@ -116235,10 +116330,10 @@ var CommandBase = class CommandBase extends CliBase {
116235
116330
  * ```
116236
116331
  */
116237
116332
  matchSubCommand(alias) {
116238
- let cmd = this.subCmdsBase[alias];
116333
+ let cmd = Object.hasOwn(this.subCmdsBase, alias) ? this.subCmdsBase[alias] : void 0;
116239
116334
  let name = alias;
116240
116335
  if (!cmd) {
116241
- name = this.subAliases[alias];
116336
+ name = Object.hasOwn(this.subAliases, alias) ? this.subAliases[alias] : void 0;
116242
116337
  if (name) cmd = this.subCmdsBase[name];
116243
116338
  else name = alias;
116244
116339
  }
@@ -116535,11 +116630,18 @@ var CommandNode = class extends ClapNode {
116535
116630
  if (matchOpt) {
116536
116631
  const optNode = this.optNodes[matchOpt.name];
116537
116632
  if (!optNode || !optNode.source.startsWith("cli")) {
116633
+ const camelCaseKey = camelCase(matchOpt.name);
116634
+ const aliasNode = this.optNodes[camelCaseKey];
116538
116635
  this.removeOptionNode(matchOpt.name);
116539
116636
  new ClapNodeGenerator(this).addOptionWithArgs(matchOpt.name, [].concat(data.arg), matchOpt.option, src);
116637
+ if (optNode && aliasNode === optNode) {
116638
+ this.optNodes[camelCaseKey] = this.optNodes[matchOpt.name];
116639
+ this.optCount[camelCaseKey] = this.optCount[matchOpt.name];
116640
+ }
116540
116641
  }
116541
116642
  } else if (!this.optNodes[key]) new ClapNodeGenerator(this).addOptionWithArgs(key, [].concat(data.arg), void 0, src);
116542
116643
  }
116644
+ for (let command = this; command; command = command.getParent()) command._jsonMeta = void 0;
116543
116645
  }
116544
116646
  /**
116545
116647
  * For options that has names with - in them, add it using its name converted to camelCase.
@@ -116720,6 +116822,7 @@ var ClapNodeGenerator = class ClapNodeGenerator {
116720
116822
  fallbackBuilder.parent = this;
116721
116823
  fallbackNode.addVerbatimArg(arg);
116722
116824
  fallbackBuilder.node.addArg(arg);
116825
+ if (fallbackMatched.cmd.expectArgs === fallbackNode.argsList.length) fallbackBuilder.endArgGathering();
116723
116826
  return [fallbackBuilder];
116724
116827
  }
116725
116828
  }
@@ -116921,8 +117024,8 @@ var ClapNodeGenerator = class ClapNodeGenerator {
116921
117024
  optNode.getParent();
116922
117025
  this.cmdNode;
116923
117026
  const builder = new ClapNodeGenerator(optNode, this);
116924
- const minArg = data.value ? 1 : 0;
116925
- if (!(optNode.option.args.length > minArg)) builder.complete();
117027
+ const minArg = data.value !== void 0 ? 1 : 0;
117028
+ if (!(optNode.option.expectArgs > minArg)) builder.complete();
116926
117029
  return [builder];
116927
117030
  }
116928
117031
  /**
@@ -116940,7 +117043,7 @@ var ClapNodeGenerator = class ClapNodeGenerator {
116940
117043
  };
116941
117044
  if (opt.hasArgs) for (let i = 0; i < args.length && i < node.argsList.length; i++) setArg(i, args[i], node.argsList[i]);
116942
117045
  else node.argsMap[0] = node.argsList.length > 0 ? this.convertValue(isBoolean(node.argsList[0]) ? "boolean" : isNumber(node.argsList[0]) ? "number" : "string", node.argsList[0], opt) : true;
116943
- if (opt.isVariadicArgs) {
117046
+ if (args.length > 0 && args[args.length - 1].array) {
116944
117047
  const lastIx = args.length - 1;
116945
117048
  if (node.argsList.length > lastIx) setArg(lastIx, args[lastIx], node.argsList.slice(lastIx));
116946
117049
  }
@@ -116959,7 +117062,7 @@ var ClapNodeGenerator = class ClapNodeGenerator {
116959
117062
  node.argsMap[argIx] = setValue;
116960
117063
  };
116961
117064
  for (let i = 0; i < args.length && i < node.argsList.length; i++) setArg(i, args[i], node.argsList[i]);
116962
- if (cmd.isVariadicArgs) {
117065
+ if (args.length > 0 && args[args.length - 1].array) {
116963
117066
  const lastIx = args.length - 1;
116964
117067
  if (node.argsList.length > lastIx) setArg(lastIx, args[lastIx], node.argsList.slice(lastIx));
116965
117068
  }
@@ -117105,7 +117208,7 @@ var Parser = class {
117105
117208
  * @param arg - a raw argv entry already known to start with '-'
117106
117209
  * @returns count of subsequent argv entries taken as this option's value
117107
117210
  */
117108
- _optionValueCount(arg) {
117211
+ _optionValueCount(arg, nextArg) {
117109
117212
  if (arg.startsWith("--no-")) return 0;
117110
117213
  const dashes = arg.startsWith("--") ? 2 : 1;
117111
117214
  let name = arg.substring(dashes);
@@ -117126,7 +117229,10 @@ var Parser = class {
117126
117229
  dashes,
117127
117230
  arg
117128
117231
  });
117129
- if (matched && matched.option) return matched.option.expectArgs || 0;
117232
+ if (matched && matched.option) {
117233
+ if (matched.option.expectArgs > 0 && matched.option.args[0].type === "boolean" && !isBoolean(nextArg)) return 0;
117234
+ return matched.option.expectArgs || 0;
117235
+ }
117130
117236
  }
117131
117237
  return 0;
117132
117238
  }
@@ -117146,7 +117252,7 @@ var Parser = class {
117146
117252
  hasNonOptionArgs = true;
117147
117253
  break;
117148
117254
  }
117149
- i += this._optionValueCount(arg);
117255
+ i += this._optionValueCount(arg, argv[i + 1]);
117150
117256
  if (arg === "--help" || arg === "-h" || arg === "-?" || arg === "--version" || arg === "-v" || arg === "-V") hasHelpOrVersion = true;
117151
117257
  }
117152
117258
  const hasDefaultCommand = this._nc._rootCommand?.ncConfig?.defaultCommand !== void 0;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "fyn",
3
3
  "type": "module",
4
- "version": "3.1.5",
4
+ "version": "3.1.7",
5
5
  "description": "fyn is a node.js package manager, and supports fynpo -- a zero setup monorepo tool",
6
6
  "main": "./bin/index.mjs",
7
7
  "homepage": "https://github.com/jchip/fynjs/tree/main/packages/fyn",
@@ -82,8 +82,8 @@
82
82
  "Walmart GTP.js Team and Contributors"
83
83
  ],
84
84
  "devDependencies": {
85
- "@fynjs/run": "^1.1.4",
86
- "@fynjs/ts-resolve": "^1.0.2",
85
+ "@fynjs/run": "^1.1.5",
86
+ "@fynjs/ts-resolve": "^1.0.3",
87
87
  "@types/node": "^26.4.1",
88
88
  "@vitest/coverage-v8": "^5.0.0",
89
89
  "@vitest/ui": "^5.0.0",
@@ -92,7 +92,7 @@
92
92
  "patch-package": "^8.0.0",
93
93
  "prettier": "^3.5.3",
94
94
  "rolldown": "^1.2.6",
95
- "run-verify": "^2.1.4",
95
+ "run-verify": "^2.1.5",
96
96
  "typescript": "^7.0.2",
97
97
  "vite": "^8.2.2",
98
98
  "vitest": "^5.0.0",