nearNames

tcmts.cli.help.nearNames · #xs2y3tpl · term · runs anywhere

The names closest to one that isn't there, most likely first: the same last part under another namespace (sharing more of the namespace first), then the names fewest letters off, if they're only a few.

import { distance } from "#codebase/tcmts/cli/help";

export function nearNames(paths: string[], target: string, most = 5): string[] {
  const lower = target.toLowerCase();
  const last = lower.slice(lower.lastIndexOf(".") + 1);
  const shared = (p: string) => {
    let n = 0;
    while (n < p.length && n < lower.length && p[n]!.toLowerCase() === lower[n]) n++;
    return n;
  };
  const sameLast = paths.filter(
    (p) => p.toLowerCase().endsWith(`.${last}`) || p.toLowerCase() === last,
  );
  if (sameLast.length) return sameLast.sort((a, b) => shared(b) - shared(a)).slice(0, most);
  const limit = Math.max(1, Math.floor(target.length / 6));
  const scored = paths.map((p) => [p, distance(lower, p.toLowerCase())] as const);
  const best = Math.min(...scored.map(([, d]) => d));
  return best > limit
    ? []
    : scored
        .filter(([, d]) => d === best)
        .slice(0, most)
        .map(([p]) => p);
}

uses

used by