Как получить целые скобки строки с, возможно, бесконечным уровнем скобок внутри

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

Я на самом деле пытаюсь деобфусцировать js-файл с помощью python, и у меня есть такая строка, которую я хочу "удалить":

String.fromCharCode
        (
            (010 * 12 + 6),
            (06 * (0x1 * (1 * 0xa + 6) + 1) + 12),
            (4 * 27 + 3),
            (01 * 0x3b + 50),
            (1 * 0x34 + 15),
            (1 * (1 * (3 * ((0x1 * 8 + 7) * 1 + 0) + 8) + 24) + 27),
            (0x1 * (2 * 0x25 + 7) + 16),
            (1 * 0112 + 40),
            (1 * 0x2c + 23),
            (0x3 * 042 + 9),
            (1 * ((05 * 4 + 1) * 03 + 0) + 37),
            (0x2 * (1 * 0x1f + 4) + 31)
        )

Когда я запускаю: re.findall(r"String.fromCharCode((.+?))", content) он возвращает мне String.fromCharCode((03 * (07 * 4 + 3) вначале. Так что похоже моя строка кода ищет только первое вхождение закрытой круглой скобки. Я не пробовал ответить по вышеуказанной ссылке, но кажется, что она не является «бесконечной», мы должны знать заранее количество уровней.

И то, что я хочу получить, это все круглые скобки, как это: ((010 * 12 + 6),(06 * (0x1 * (1 * 0xa + 6) + 1) + 12),(4 * 27 + 3),(01 * 0x3b + 50),(1 * 0x34 + 15),(1 * (1 * (3 * ((0x1 * 8 + 7) * 1 + 0) + 8) + 24) + 27),(0x1 * (2 * 0x25 + 7) + 16),(1 * 0112 + 40),(1 * 0x2c + 23),(0x3 * 042 + 9),(1 * ((05 * 4 + 1) * 03 + 0) + 37),(0x2 * (1 * 0x1f + 4) + 31))

РЕДАКТИРОВАТЬ:

Чтобы уточнить, в коде есть много других вхождений " String.fromCharCode ", который находится выше. Если бы я должен был удалить ? в коде регулярного выражения он получит весь код.

EDIT2:

Я сделал вещь: https://pastebin.com/BVtD8R51 Кажется, работает.

Всего 2 ответа


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

String.fromCharCode[^()]*
(
    (
        (?:[^()]|(?1))*
    )
)

Смотрите демо на regex101.com .


Который в Python может быть:

import regex as re

rx = re.compile(r'''
    String.fromCharCode[^()]*
    (
        (
            (?:[^()]|(?1))*
        )
    )
''', re.VERBOSE)

for snippet in rx.finditer(your_string_here):
    print(snippet.group(0))

Квалификатор + в python по умолчанию жадный, поэтому он будет соответствовать как можно больше. Вы добавили ? после того, что делает его не жадным. Взять ? out, и он должен полностью соответствовать следующей закрывающей скобке, но он также будет совпадать и дальше, если он сможет найти другие закрывающие скобки дальше в вашем входе, даже если он находится вне закрывающей скобки fromCharCode .


Есть идеи?

10000