JSON в CSV: как развернуть ответ API в таблицу
Что конвертируется чисто, как обрабатываются вложенные объекты и пропущенные ключи и какая ловушка с разделителем ломает CSV в Excel.
Вы забираете данные из API, получаете аккуратный массив JSON, а потом кто-то просит прислать всё это «таблицей». Этот зазор, JSON у вас в терминале и CSV у коллеги в почте, и есть та задача, ради которой делают такую конвертацию. Звучит как пустяк, и для аккуратных данных так и есть. Сложности начинаются, когда данные неаккуратные.
Зачем это вообще нужно
Чаще всего это не какой-то большой конвейер данных. Всё мельче и досаднее:
- менеджеру продукта надо отсортировать 200 записей из API в Excel, а не вглядываться в них в редакторе кода;
- разовый экспорт из инструмента, который умеет только JSON, а нужен он в Google Таблицах;
- быстро глянуть глазами: CSV открывается в таблице, и столбец просматриваешь за пару секунд, чего не скажешь о вложенных скобках.
Можно каждый раз писать скрипт с csv.DictWriter или однострочник на jq. Но для одного массива, который вы видели пять минут назад, открыть конвертер JSON в CSV, вставить и скопировать результат быстрее, чем вспоминать синтаксис jq. (Я синтаксис jq не помню никогда.)
Что конвертируется чисто
Массив плоских объектов — идеальный случай. Каждый объект становится строкой, каждый ключ — столбцом:
[
{ "id": 1, "name": "Ada", "active": true },
{ "id": 2, "name": "Linus", "active": false }
]
Три столбца, две строки, заголовок на месте. Конвертер сначала проходит по всем объектам и собирает полный набор ключей: если у одной записи есть поле phone, а у следующей нет, столбец phone всё равно появится. Пустая ячейка останется пустой, а не сдвинет остальную строку вбок. Эта мелочь важнее, чем кажется: один пропущенный ключ — и CSV-файл тихо ломается, а значения с этой строки уезжают под чужие заголовки.
Где начинается каша: вложенные данные
Реальные ответы API вложенные. У заказа есть объект customer, у пользователя — массив roles. CSV плоский. Затолкать объект в одну ячейку честно не выйдет, так что остаётся два компромисса:
- сериализовать вложенную часть обратно в текст JSON и положить его в ячейку. Ничего не теряется, но получается JSON внутри CSV, читать который неприятно;
- сначала развернуть, превратив
customer.emailв отдельный столбец.
Этот инструмент идёт первым путём: вложенное значение попадает в ячейку как текст JSON. Если нужен customer.email отдельным столбцом, разверните JSON перед вставкой. Сохранить данные и оставить выбор за вами лучше, чем молча выбросить объект customer.
Ловушка с разделителем
Вот из-за чего теряют полдня. Вы делаете идеальный файл с запятыми, открываете его в Excel — и все значения сваливаются в один столбец. Ничего не сломалось. Excel читает файл с тем разделителем списка, который задан в региональных настройках, а во многих странах Европы это точка с запятой, а не запятая.
Лечится это подгонкой файла под того, кто его открывает. Смените разделитель на точку с запятой и сконвертируйте заново или возьмите табуляцию (TSV): она обходит спор «запятая против точки с запятой» стороной, потому что табы внутри самих данных почти не встречаются. В конвертере есть все три варианта — выбирайте тот, который ждёт ваша таблица.
Запятые и кавычки внутри значений
Ещё одно, на чём спотыкаются наивные конвертеры, — значение, в котором уже есть запятая, например Smith, Jane. В сыром виде эта запятая читается как новый столбец. Правило CSV простое: поле берут в двойные кавычки, а если кавычка в значении уже есть, её удваивают. Конвертер делает это за вас по стандарту RFC 4180, поэтому адрес или фраза со знаками препинания остаются в одной ячейке.
Вставьте свой массив в конвертер JSON в CSV, выберите разделитель и скопируйте таблицу прямо в Google Таблицы. Ничего не загружается на сервер, ничего не нужно устанавливать.