Как преобразовать значение timestamp в число, а затем преобразовать в читаемый формат для человека.

Вопрос или проблема

У меня есть строковый ключ с меткой времени, который мне нужно преобразовать в число, потому что strftime выдает ошибку, что оно должно быть числом.

journalctl -n1 --output=json | jq '.__REALTIME_TIMESTAMP | tonumber |= (. / 1000 | strftime("%Y-%m-%d")), .MESSAGE'

но я получаю ошибки выражения недопустимого пути. Предполагаю, что синтаксис у меня неправильный.

В конечном итоге я хочу отобразить ключ __REALTIME_TIMESTAMP в читаемом формате и ключ MESSAGE.

Я не уверен, что вы имеете в виду с |= здесь.

Это может работать так:

$ journalctl -n1 --output=json |
    jq '(.__REALTIME_TIMESTAMP | tonumber/1000000 | strftime("%Y-%m-%d %H:%M:%S")), .MESSAGE'
"2023-11-11 21:44:27"
"[session uid=1000 pid=1420] Activation via systemd failed for unit 'gvfs-daemon.service': Unit gvfs-daemon.service is masked."

Или отформатированный / необработанный вывод:

$ journalctl -n1 --output=json | 
    jq -r '(.__REALTIME_TIMESTAMP | tonumber/1000000 | strftime("[%Y-%m-%d %H:%M:%S]: ")) + .MESSAGE'
[2023-11-11 21:44:27]: [session uid=1000 pid=1420] Activation via systemd failed for unit 'gvfs-daemon.service': Unit gvfs-daemon.service is masked.

То же самое, но с показом миллисекунд

  • используя @tsv для показа вывода строка за строкой
  • используя переключатель -f для команды journalctl
journalctl -axf --output=json |
    jq  -r  '[
        ( .__REALTIME_TIMESTAMP | tonumber/ 1000000 | strftime("%F %T") )+"."+(
          .__REALTIME_TIMESTAMP | tonumber / 1000000 | tostring | split(".")[1] ),
       .MESSAGE, .PRIORITY, .SYSLOG_FACILITY, .SYSLOG_IDENTIFIER, ._UID, ._GID
     ] | @tsv'
2025-02-03 20:38:33.233387  gkr-pam: unlocked login keyring 6       10      mate-screensaver-dialog 1000    1000
2025-02-03 22:16:18.29829   [session uid=1000 pid=4069173] Successfully activated service 'org.freedesktop.Notifications'   6       3       dbus-daemon        1000    1000
2025-02-04 12:03:10.427966  <WpPortalPermissionStorePlugin:0x5592194d1ce0> Failed to call Lookup: GDBus.Error:org.freedesktop.portal.Error.NotFound: No entry for camera       4                       1000    1000

В конвейере вы должны использовать stdbuf:

while IFS=$'\t' read -r date message priority facility syslogid uid gid;do
    printf '\e[%sm%-26s %3d %6d %6d %s\e[0m\n' $((priority >= 5 ? 0 : 31 )) \
        "$date" "$priority" "$uid" "$gid" "$message"
done < <(
    journalctl -axf --output=json |
        stdbuf -o0 jq  -r  '[
           ( .__REALTIME_TIMESTAMP | tonumber/ 1000000 | strftime("%F %T") )+"."+(
             .__REALTIME_TIMESTAMP | tonumber / 1000000 | tostring | split(".")[1] ),
          .MESSAGE, .PRIORITY, .SYSLOG_FACILITY, .SYSLOG_IDENTIFIER, ._UID, ._GID
        ] | @tsv'
)

Будет печатать красным строки с приоритетом меньше 5.

.

Ответ или решение

Вопрос о том, как преобразовать временную метку (timestamp) в число и сделать её читаемой для человека, является важной задачей для многих специалистов в области IT, особенно при работе с журналами системных сообщений. В данном случае используется команда journalctl для получения записей журнала в формате JSON и инструмент jq для разбора и обработки данных. Задача усложняется наличием строки временной метки, которую необходимо корректно преобразовать в числовое значение перед применением функции strftime. Давайте разберем этот процесс подробнее.

Теория

Временные метки обычно хранятся в UNIX-формате времени, что представляет собой количество секунд с 1 января 1970 года (эпоха Unix). В некоторых системах, таких как система журналов Linux, временные метки могут быть представлены в миллисекундах или даже наносекундах, что требует соответствующего деления на 1000 или 1000000 для получения секунд.

Инструмент jq предоставляет возможность обрабатывать JSON-данные с использованием различных функций, включая tonumber для преобразования строки в число и strftime для форматирования числового значения времени в человечески-понятный формат.

Пример

Рассмотрим следующее выражение:

journalctl -n1 --output=json |
    jq '(.__REALTIME_TIMESTAMP | tonumber/1000000 | strftime("%Y-%m-%d %H:%M:%S")), .MESSAGE'

Это выражение выполняет следующую последовательность действий:

  1. journalctl -n1 --output=json: Запрашивает последнюю запись журнала в формате JSON.
  2. .__REALTIME_TIMESTAMP | tonumber/1000000: Находит ключ __REALTIME_TIMESTAMP, преобразует его значение из строки в число и делит его на 1000000 для получения секунд.
  3. strftime("%Y-%m-%d %H:%M:%S"): Форматирует полученное числовое значение времени в читаемый для человека формат даты и времени (YYYY-MM-DD HH:MM:SS).
  4. .MESSAGE: Извлекает сообщение из журнала для отображения.

Применение

Таким образом, для корректного отображения временной метки и сообщения необходимо соблюдать синтаксис jq и последовательность преобразований. Пример выше показывает один из возможных путей решения задачи. Стоит обратить внимание на детализацию временной метки с миллисекундами, что может быть выполнено с использованием дополнительных функций и методов обработки, как показано в следующем примере:

journalctl -axf --output=json |
    jq -r '[
        (.__REALTIME_TIMESTAMP | tonumber/1000000 | strftime("%F %T")) + "." + 
        (.__REALTIME_TIMESTAMP | tonumber % 1000 | tostring | split(".")[1]), 
        .MESSAGE
    ] | @tsv'

Здесь ключ __REALTIME_TIMESTAMP обрабатывается аналогичным образом, но добавляется форматирование для вывода миллисекунд, которые извлекаются с помощью операции получения остатка от деления и дальнейшего преобразования.

Заключение

В заключении, правильная обработка временных меток требует понимания структуры данных, инструментов и команд, используемых для их обработки. В данном контексте, jq предоставляет мощный функционал для трансформации JSON-данных, что позволяет адаптировать временные метки и делать их читаемыми для конечного пользователя. Этот подход является полезным не только для специалистов по IT, но и для всех, кто взаимодействует с логами и системными данными в своей работе. Важно учитывать нюансы преобразования и соблюдать предложенные шаги для достижения нужного результата.

Оцените материал
Добавить комментарий

Капча загружается...