Что такое grep и как его знание помогает backend-разработчику?

Ответ

grep (Global Regular Expression Print) — это мощная утилита командной строки в UNIX-подобных системах для поиска текстовых данных по шаблону (регулярному выражению) внутри файлов или в потоке ввода/вывода.

Почему это важно для Backend-разработчика: Это один из основных инструментов для:

  • Анализа логов: Быстрый поиск ошибок, трассировок запросов по ID, IP-адресу или сообщению.
  • Поиска по кодовой базе: Найти все места использования функции, переменной или конфигурационного параметра.
  • Работы с выводом других команд: docker ps | grep my-container для поиска конкретного контейнера.

Часто используемые флаги:

  • -i — игнорировать регистр.
  • -v — инвертировать поиск (вывести строки, не содержащие шаблон).
  • -r или -R — рекурсивный поиск по всем файлам в директории.
  • -n — показывать номера строк с совпадениями.
  • -C <N> (Context) — показать N строк до и после совпадения.

Примеры:

# Найти все строки со словом "ERROR" в лог-файле
grep "ERROR" /var/log/app.log

# Рекурсивно найти все вызовы функции "ConnectDB" в текущей директории, игнорируя регистр
grep -ri "ConnectDB" .

# Показать 2 строки до и после найденной ошибки
grep -C 2 "panic: runtime error" /var/log/app.log

Аналог в Go: В Go для подобной функциональности используется пакет regexp. Он позволяет компилировать регулярные выражения и применять их к строкам или потокам данных.

package main

import (
    "fmt"
    "regexp"
)

func main() {
    logData := `
    [2023-10-27 10:00:00] INFO: User logged in
    [2023-10-27 10:01:15] ERROR: Failed to connect to database
    [2023-10-27 10:01:15] DEBUG: Connection string: user:pass@tcp(127.0.0.1:3306)/db
    [2023-10-27 10:02:00] INFO: Request processed
    `

    // Создаем регулярное выражение, аналог grep "ERROR"
    re, err := regexp.Compile(`.*ERROR.*`)
    if err != nil {
        panic(err)
    }

    // Ищем все совпадения в строке
    matches := re.FindAllString(logData, -1)

    for _, match := range matches {
        fmt.Println(match) // Выведет: [2023-10-27 10:01:15] ERROR: Failed to connect to database
    }
}

Ответ 18+ 🔞

А, ну ты глянь, какой инструмент-то, ёпта! grep — это типа твой личный детектив в мире UNIX, который по регуляркам ищет всякую хуйню в файлах или в том, что ему в пасть льётся. Без него на бэкенде — как без рук, внатуре.

Нахуя это тебе, собственно? Ну, представь, у тебя сервак плюётся логами, а тебе надо найти, где конкретно он обосрался. Или в тонне кода найти все вызовы какой-нибудь ёбанной функции sendToBlackHole. Вот grep — твой лучший друг, а иногда и единственный, блядь.

Основные примочки (флаги):

  • -i — похуй на большие и маленькие буквы, ищет всё.
  • -v — выведет всё, что НЕ подходит под шаблон. Инверсный поиск, мать его.
  • -r — полезет во все папки и подпапки, как маньяк с фонариком.
  • -n — покажет номера строк, где нашёл. Чтобы ты знал, куда тыкать.
  • -C <N> — покажет N строк ДО и ПОСЛЕ найденного. Контекст, блядь, это важно!

Примеры из жизни, чтобы не быть мудаком:

# Ищешь все "ERROR" в логах, потому что день не задался
grep "ERROR" /var/log/my_app.log

# Рекурсивно ищешь во всём проекте, где ты использовал эту чёртову "MagicConstant", и не важно, как ты её написал
grep -ri "MagicConstant" .

# Нашёл ошибку, но хочешь понять, что происходило до и после. Покажи 3 строки вокруг!
grep -C 3 "panic: runtime error" /var/log/app.log

А как это выглядит на Go, спросишь? Ну, в Go за регулярки отвечает пакет regexp. Не такой лаконичный, как в консоли, но мощный, блядь.

package main

import (
    "fmt"
    "regexp"
)

func main() {
    // Допустим, это наши кривые логи
    logData := `
    [2023-10-27 10:00:00] INFO: User logged in
    [2023-10-27 10:01:15] ERROR: Failed to connect to database
    [2023-10-27 10:01:15] DEBUG: Connection string: user:pass@tcp(127.0.0.1:3306)/db
    [2023-10-27 10:02:00] INFO: Request processed
    `

    // Компилируем регулярку — аналог нашего grep "ERROR"
    re, err := regexp.Compile(`.*ERROR.*`)
    if err != nil {
        // Если регулярку криво написал — получишь по ебалу паникой
        panic(err)
    }

    // Ищем все совпадения
    matches := re.FindAllString(logData, -1)

    // Выводим, что нашли
    for _, match := range matches {
        fmt.Println(match) // Выведет ту самую строку с ERROR, ебать её в сраку
    }
}

Вот и весь сказ. Выучи grep — и жизнь станет чуть менее пиздецовой, когда придётся копаться в тоннах текста.