MCPcopy
hub / github.com/lingodotdev/lingo.dev / alignPatternToSource

Function alignPatternToSource

packages/cli/src/cli/utils/buckets.ts:322–390  ·  view source on GitHub ↗
(
  pattern: string[],
  source: string[],
  locale: string,
  options?: { forbid?: { patternIndex: number; sourceIndex: number } },
)

Source from the content-addressed store, hash-verified

320// patternIndex to a given sourceIndex, which lets us probe for alternative
321// [locale] placements.
322function alignPatternToSource(
323 pattern: string[],
324 source: string[],
325 locale: string,
326 options?: { forbid?: { patternIndex: number; sourceIndex: number } },
327): { patToSrc: number[] } | null {
328 const patternLength = pattern.length;
329 const sourceLength = source.length;
330 const memo = new Map<string, boolean>();
331 const parent = new Map<string, { i2: number; j2: number }>();
332 const isDoubleStar = (segment: string) => segment === "**";
333 const segmentMatches = (patternSegment: string, sourceSegment: string) => {
334 const concrete = patternSegment.replaceAll("[locale]", locale);
335 return minimatch(sourceSegment, concrete, { dot: true, nocase: true });
336 };
337 const forbid = options?.forbid;
338 const key = (i: number, j: number) => `${i}|${j}`;
339 const dfs = (i: number, j: number): boolean => {
340 const memoKey = key(i, j);
341 if (memo.has(memoKey)) {
342 return memo.get(memoKey)!;
343 }
344 if (i === patternLength) {
345 const done = j === sourceLength;
346 memo.set(memoKey, done);
347 return done;
348 }
349 let matched = false;
350 if (isDoubleStar(pattern[i])) {
351 for (let k = j; k <= sourceLength; k += 1) {
352 if (dfs(i + 1, k)) {
353 parent.set(memoKey, { i2: i + 1, j2: k });
354 matched = true;
355 break;
356 }
357 }
358 } else if (j < sourceLength && segmentMatches(pattern[i], source[j])) {
359 const blocked =
360 forbid && forbid.patternIndex === i && forbid.sourceIndex === j;
361 if (!blocked && dfs(i + 1, j + 1)) {
362 parent.set(memoKey, { i2: i + 1, j2: j + 1 });
363 matched = true;
364 }
365 }
366 memo.set(memoKey, matched);
367 return matched;
368 };
369
370 if (!dfs(0, 0)) {
371 return null;
372 }
373
374 const patToSrc = Array(patternLength).fill(-1) as number[];
375 let i = 0;
376 let j = 0;
377 while (i < patternLength) {
378 const step = parent.get(key(i, j));
379 if (!step) {

Callers 1

mapPatternToSourceFunction · 0.85

Calls 4

dfsFunction · 0.85
keyFunction · 0.85
isDoubleStarFunction · 0.85
getMethod · 0.65

Tested by

no test coverage detected