Skip to content

Commit

Permalink
fix: strip diacritics from letters in search queries (#143)
Browse files Browse the repository at this point in the history
Resolves #142

This commit improves search functionality by
normalizing diacritics in search queries and
searchable text. This ensures that users can
find items even if they use characters with
diacritics, and vice versa.
  • Loading branch information
danelkay93 authored Jan 8, 2025
1 parent 95566c5 commit d3a5280
Show file tree
Hide file tree
Showing 4 changed files with 25 additions and 5 deletions.
11 changes: 9 additions & 2 deletions src/components/ui/combobox/combobox.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import type { Coded } from "@/store/services/queries.types";
import { FLOATING_PORTAL_ID } from "@/utils/constants";
import { cx } from "@/utils/cx";
import { isEmpty } from "@/utils/is-empty";
import { normalizeDiacritics } from "@/utils/normalize-diacritics";
import {
FloatingFocusManager,
FloatingPortal,
Expand Down Expand Up @@ -35,10 +36,16 @@ function fuzzyMatch<T extends Coded>(
) {
if (!search) return items;

const normalizedSearchTerm = normalizeDiacritics(search);

const uf = new uFuzzy();
const searchItems = items.map(itemToString);

const results = uf.search(searchItems, search, 1);
// Normalize diacritics in search items to stripped letters
const searchItems = items.map((item) =>
normalizeDiacritics(itemToString(item)),
);

const results = uf.search(searchItems, normalizedSearchTerm, 1);
if (!results?.[0]) return items;

const matches = results[0].reduce<Record<string, boolean>>((acc, curr) => {
Expand Down
5 changes: 3 additions & 2 deletions src/store/lib/searching.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type { Card } from "@/store/services/queries.types";
import { normalizeDiacritics } from "@/utils/normalize-diacritics";
import uFuzzy from "@leeoniya/ufuzzy";
import type { Search } from "../slices/lists.types";
import type { Metadata } from "../slices/metadata.types";
Expand Down Expand Up @@ -72,7 +73,7 @@ export function applySearch(
if (back) content += prepareCardFace(back, search);
}

return content;
return normalizeDiacritics(content);
});

const results = uf.search(searchCards, prepareNeedle(search.value), 0);
Expand All @@ -88,5 +89,5 @@ export function applySearch(
}

function prepareNeedle(needle: string): string {
return needle.replaceAll(/((?:\+|-)\d+)/g, `"$1"`);
return normalizeDiacritics(needle.replaceAll(/((?:\+|-)\d+)/g, `"$1"`));
}
11 changes: 10 additions & 1 deletion src/store/selectors/deck-filters.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import { assert } from "@/utils/assert";
import { FACTION_ORDER, type FactionName } from "@/utils/constants";
import { capitalize } from "@/utils/formatting";
import { and, or } from "@/utils/fp";
import { normalizeDiacritics } from "@/utils/normalize-diacritics";
import uFuzzy from "@leeoniya/ufuzzy";
import { createSelector } from "reselect";
import { extendedDeckTags } from "../lib/resolve-deck";
Expand Down Expand Up @@ -253,7 +254,15 @@ const selectDecksFiltered = createSelector(
interIns: MATCHING_MAX_TOKEN_DISTANCE_DECKS,
});

const results = finder.search(searchableText, searchTerm);
const normalizedSearchTerm = normalizeDiacritics(searchTerm);

// Normalize letters with diacritics in searchable text to stripped letters
const normalizedSearchableText = searchableText.map(normalizeDiacritics);

const results = finder.search(
normalizedSearchableText,
normalizedSearchTerm,
);

decksToFilter = [];

Expand Down
3 changes: 3 additions & 0 deletions src/utils/normalize-diacritics.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export function normalizeDiacritics(str: string) {
return str.normalize("NFKD").replace(/\p{Diacritic}/gu, "");
}

0 comments on commit d3a5280

Please sign in to comment.