В международных интерфейсах массивы элементов почти никогда не отображаются через фиксированные разделители вроде запятой. Разные языки используют собственные правила перечисления: различаются союзы, порядок знаков препинания, наличие серийной запятой и даже формы соединительных слов в зависимости от длины списка.
Библиотека Globalize опирается на данные CLDR (Unicode Common Locale Data Repository), где для каждой локали определены шаблоны форматирования списков. Эти шаблоны описывают, как должны соединяться элементы массива в текстовую строку.
Ключевая задача форматирования списков:
CLDR различает несколько типов списков:
Каждый тип списка имеет собственные правила соединения элементов.
Пример логики:
Globalize требует загрузки CLDR-данных, включая раздел listPatterns.
import Globalize from "globalize";
// предполагается, что CLDR данные уже загружены:
// cldr/supplemental/listPatterns.json
// cldr/main/{locale}/listPatterns.json
Globalize.locale("en");
Без данных listPatterns форматирование списков работать не будет, так как библиотека не содержит встроенных локализаций.
Для преобразования массива в строку используется метод:
Globalize.formatList(array, options);
Пример:
const g = Globalize("en");
g.formatList(["apples", "bananas", "oranges"]);
Результат:
apples, bananas, and oranges
Для локали с другими правилами результат будет отличаться.
Globalize.locale("en");
Globalize.formatList(["A", "B", "C"]);
Результат:
A, B, and C
Используется серийная запятая (Oxford comma).
Globalize.locale("de");
Globalize.formatList(["A", "B", "C"]);
Результат:
A, B und C
Особенность: отсутствие запятой перед союзом.
Globalize.locale("fr");
Globalize.formatList(["A", "B", "C"]);
Результат:
A, B et C
Используется для обычных перечислений.
g.formatList(["HTML", "CSS", "JavaScript"], { type: "standard" });
Используется для альтернативных вариантов.
g.formatList(["light", "dark"], { type: "or" });
Результат может выглядеть как:
light or dark
В других локалях:
light ou dark
light oder dark
Используется для комбинирования единиц измерения.
g.formatList(["10 kg", "200 g"], { type: "unit" });
Этот тип часто исключает союзы и использует более компактное соединение.
CLDR описывает список через набор шаблонов:
Пример структуры:
{0}, {1}
{0}, {1}
{0}, and {1}
Globalize выбирает шаблон в зависимости от длины массива.
Globalize.formatList(["A"]);
Результат:
A
Шаблоны не применяются.
Globalize.formatList(["A", "B"]);
Используется шаблон pair:
A and B
Globalize.formatList(["A", "B", "C", "D"]);
Результат:
A, B, C, and D
Метод formatList принимает опции:
Globalize.formatList(array, {
type: "standard"
});
Основные параметры:
Форматирование списков часто применяется к результатам API или пользовательским данным.
const users = ["Anna", "Ivan", "Sara", "John"];
Globalize.formatList(users);
При изменении локали формат автоматически адаптируется:
Globalize.locale("ru");
Globalize.formatList(users);
Результат:
Anna, Ivan, Sara и John
Перед форматированием часто требуется нормализация данных:
const items = response.data.map(item => item.title);
Globalize.formatList(items);
Если элементы содержат сложные строки, Globalize не изменяет их содержимое, а только соединяет.
Globalize.formatList([]);
Результат:
""
Globalize.formatList(["A", null, "C"]);
Поведение зависит от предварительной очистки данных; Globalize не фильтрует значения автоматически.
Форматирование списков опирается на заранее загруженные CLDR-шаблоны. Это означает:
При частом использовании рекомендуется:
Форматирование списков часто комбинируется с другими возможностями:
const dates = [
Globalize.formatDate(new Date(2024, 0, 1)),
Globalize.formatDate(new Date(2024, 0, 2))
];
Globalize.formatList(dates);
const numbers = [
Globalize.formatNumber(1000),
Globalize.formatNumber(2000)
];
Globalize.formatList(numbers);
Локаль влияет не только на союзы, но и на:
Например, в некоторых азиатских локалях список может быть оформлен без союзов вообще.
При работе с интерфейсами форматирование списков применяется для:
Типичный пример:
const filters = ["React", "TypeScript", "GraphQL"];
label.textContent = Globalize.formatList(filters);
const g = Globalize("en");
g.formatList(["A", "B"]);
Globalize.locale("ja");
g.formatList(["A", "B"]);
Результат изменится автоматически в зависимости от активной локали, если экземпляр Globalize использует глобальный locale state.