регулярное выражение, удалить все перед первым подчеркиванием

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

У меня есть строка grafana-stack_alloy и мне нужно всё, что после первого подчеркивания alloy.

Я хочу получить результат как группу $1. Попробовал это, но неудачно. (?:)?([^_]+)*$.

Может кто-то помочь мне решить эту проблему?

Я тестирую это:

        правило {
        действие        = "заменить"
        исходные_метки = [
            "__meta_docker_container_label_com_docker_swarm_service_name",
        ]
        регулярное выражение        = "^(?:;*)?([^;]+).*$" работает, но неверно
        //регулярное выражение      = "[^_]+.$" ----> не работает
        //регулярное выражение      = "([^_]+)$" ----> не работает
        замена  = argument.namespace.value + "/$1"
        целевая_метка = "работа"
    }

Это связано с агентом Grafana с relabel-regex:
Grafana prometheus.relabel, который использует RE2 от Google в качестве своего движка регулярных выражений.

Спасибо заранее

Эти выражения получат всё после последнего подчеркивания.

_([^_]+)$

или

^.*_([^_]+)$

Если вы хотите всё после первого подчеркивания:

^[^_]*_(.+)$

или измените первый * на +, если не хотите ведущих подчеркиваний.

Если вы также хотите устранить второе подчеркивание в двойном подчеркивании, но получить всё после этого, попробуйте

^[^_]*_+(.+)$

Если вы хотите более специфичное соответствие, возможно, вам нужно

grafana-stack_([^_]+)$

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

Что касается Grafana, использующей диалект регулярных выражений Golang, вам нужно изменить регулярное выражение на:

([^_])*$

Смотрите онлайн-демо объяснения

Официальная документация также упоминает Golang:

expression должна быть строкой Go RE2 regex.

Так как “замена” выглядит так:

замена  = argument.namespace.value + "/$1"

Это подразумевает, что то, что совпадает с регулярным выражением, заменяется этим.

В grafana-stack_alloy ваше ([^_]+)$ регулярное выражение правильно совпадет с частью alloy после _ и захватит её в $1, но поскольку всё регулярное выражение совпадает только с этим, после замены вы получите:

grafana-stack_<argument.namespace.value>/alloy

Если вы хотите, чтобы результат после замены был только <argument.namespace.value>/alloy, тогда вам нужно, чтобы регулярное выражение совпадало с целым входом, а из этого захватывалась часть после _.

Поскольку RE2 поддерживает жадный оператор повторения *?, это можно сделать просто так:

^.*?_(.*)$

Якоря (^, $) даже не нужны, так как это регулярное выражение гарантированно совпадает с целым входом, если он содержит хотя бы одно _ (и вообще не совпадает с якорем или без, если нет _).

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

Вопрос, который вы подняли, касается удаления всего текста перед первым символом подчеркивания в строке, такой как grafana-stack_alloy, с использованием регулярных выражений (regex), а также правильного формирования выражения для применения в контексте Grafana Agent. Давайте подробно рассмотрим, как это можно сделать правильно.

Понимание задачи

У вас есть строка:

grafana-stack_alloy

И вам нужно извлечь часть после первого символа подчеркивания (_), в данном случае — это alloy. Затем необходимо вернуть результат в формате групповой замены (в вашем случае — $1).

Правильное регулярное выражение

Исходя из ваших требований, подходящим регулярным выражением будет:

^[^_]*_(.+)$

Объяснение регулярного выражения:

  • ^ — обозначает начало строки.
  • [^_]* — находит любое количество символов, которые не являются подчеркиванием (это практика локации до первого символа _).
  • _ — подчеркивание, которое мы используем как разделитель.
  • (.+)$ — захватывает все символы после первого _ до конца строки. Здесь (.+) — это группа, которая будет содержать все, что следует после подчеркивания, а $ обозначает конец строки.

Применение в Grafana Agent

В контексте Grafana Agent, можно использовать следующее выражение для правильной замены:

rule {
    action        = "replace"
    source_labels = [
        "__meta_docker_container_label_com_docker_swarm_service_name",
    ]
    regex         = "^[^_]*_(.+)$"
    replacement   = argument.namespace.value + "/$1"
    target_label  = "job"
}

Примечания по тестированию

  • Если в строке отсутствует символ подчеркивания, регулярное выражение не сработает. Убедитесь, что тестируемые строки всегда содержат хотя бы один символ _. При отсутствии _ результат будет пустым, и действия по замене могут не сработать.
  • Проверяйте вашу регулярку на различных строках, чтобы убедиться, что она обрабатывает как ожидается, например:

    input: grafana-stack_alloy -> output: <argument.namespace.value>/alloy
    input: example_test_case -> output: <argument.namespace.value>/test_case

Заключение

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

Если будут дополнительные вопросы или нюансы, не стесняйтесь обращаться!

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

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