Для группировки нескольких сообщений за день нужен массив в значении Record, иначе сообщения перезапишут друг друга. Комнаты индексируйте по id, а часовой пояс дня задайте явно.
Группировка полученных сообщений по датам с указанием названия комнаты
Для группировки нескольких сообщений за день нужен массив в значении Record, иначе сообщения перезапишут друг друга. Комнаты индексируйте по id, а часовой пояс дня задайте явно.
Короткий ответ
Что ответить на собеседовании
Подробный разбор
Ответ с пояснениями
Условие
В системе доступны два эндпоинта: один возвращает массив комнат, второй — массив сообщений. Необходимо выполнить запросы к обоим ресурсам, добавить каждому сообщению название соответствующей комнаты и собрать сообщения в структуру, где ключом будет строковое представление даты начала дня в ISO‑формате, а значением — объект сообщения без поля roomId, но с полем roomName. Ниже приведены типы данных и пример ожидаемого результата.
interface IRoom {
id: number;
name: string;
type: string;
}
interface IMessage {
roomId: IRoom['id'];
id: number;
text: string;
ts: Date;
}
// // Эндпоинт GET '/rooms' возвращает IRoom[]
// // Эндпоинт GET '/messages' возвращает IMessage[]
// // Необходимо запросить сообщения и комнаты и сгруппировать сообщения по дням
type ProcessedMessage = Omit<IMessage, 'roomId'> & {
roomName: IRoom['name'];
};
type ProcessedData = Record<string, ProcessedMessage>;
// // при этом строковый ключ – ISO представление даты начала дня ('2022-06-23T00:00:00')
// // Пример результата:
//
// '2023-03-23T00:00:00': { // ISO представление даты начала дня
// "roomName": "Room name", // название комнаты из rooms
// "id": 1,
// "text": "sunt aut facere repellat provident occaecati excepturi optio reprehenderit",
// "ts": Thu Mar 23 2023 12:15:15 GMT+0200 (Восточная Европа, стандартное время)
// }
// ...
Ответ
Для группировки нескольких сообщений за день нужен массив в значении Record, иначе сообщения перезапишут друг друга. Комнаты индексируйте по id, а часовой пояс дня задайте явно.
async function groupedMessages() {
const load = async url => {
const response = await fetch(url);
if (!response.ok) throw new Error('Ошибка HTTP');
return response.json();
};
const [rooms, messages] = await Promise.all([load('/rooms'), load('/messages')]);
const names = new Map(rooms.map(room => [room.id, room.name]));
const result = Object.create(null);
for (const { roomId, ts, ...message } of messages) {
if (!names.has(roomId)) throw new Error('Неизвестная комната');
const date = new Date(ts);
if (Number.isNaN(date.getTime())) throw new Error('Неверная дата');
const day = date.toISOString().slice(0, 10) + 'T00:00:00.000Z';
(result[day] ??= []).push({ ...message, ts: date, roomName: names.get(roomId) });
}
return result;
}
Выбран UTC-день; тип результата — Record<string, ProcessedMessage[]>. По JSON Date приходит строкой, поэтому ts преобразуется явно. Если нужен местный день, нельзя брать UTC-срез; необходимо задать нужную зону. Ключ из условия без Z сам по себе эту зону не определяет.