Причудливая подстановка строк для требований оставить комментарии к тому же отступу на python - PullRequest
0 голосов
/ 28 апреля 2020

Я пишу удобный инструмент для себя, чтобы оставлять комментарии в файле pyproject.yaml перед каждым требованием.

Так что это должно выглядеть примерно так.

[tool.poetry.dependencies]
django = "3.0.5"
djangorestframework = "3.11.0"              # Rest api [ https://www.django-rest-framework.org ]
psycopg2-binary = "2.8.4"                   # PostgreSQL driver
redis = "3.4.1"                             # The Python interface to the Redis key-value store 

Я знаю, как сделать это простым, некрасивым способом, но, вероятно, вы можете прийти с чем-то сексуальным и умным?

Я думал о:

new_text = re.sub('^(django[\s|=].*").*', r"\1                 # COMMENTS HERE", text, flags=re.MULTILINE)

Где вместо django будет, конечно, имя пакета ... Но, похоже, нет способа сохранить тот же отступ, потому что я не могу получить длина подходящей строки там. А также я не могу просто использовать toml parser и переписывать файл с нуля, потому что я хочу сохранить существующие комментарии, которые не связаны с требованиями.

Я попробовал другой подход. Но мне это тоже не нравится.

poetry = parsed_toml['tool']['poetry']
    for dep_type in ('dependencies', 'dev-dependencies'):
        for dependency, version in poetry[dep_type].items():
            char_length = len(dependency + version)
            text = re.sub(f'^{dependency}.*{version}.*', f'{dependency} = "{version}" {" " * (45 - char_length)} # Comment', text, flags=re.MULTILINE)

Я также хочу сделать эту замену с меньшей возможной итерацией. Так что если у вас есть какие-либо яркие идеи, пожалуйста, поделитесь:)

1 Ответ

1 голос
/ 28 апреля 2020

Вы можете получить длину совпадения, используя функцию замены:

import re

text = '''\
[tool.poetry.dependencies]
django = "3.0.5"
djangorestframework = "3.11.0"              # Rest api [ https://www.django-rest-framework.org ]
psycopg2-binary = "2.8.4"                   # PostgreSQL driver
redis = "3.4.1"                             # The Python interface to the Redis key-value store
'''

def repl(m):
    return f'{m.group(1):44s}# COMMENTS HERE' # pad match out to 44 spaces before comment

text = re.sub('^(django[\s|=].*").*$', repl, text, flags=re.MULTILINE)

print(text)

Вывод:

[tool.poetry.dependencies]
django = "3.0.5"                            # COMMENTS HERE
djangorestframework = "3.11.0"              # Rest api [ https://www.django-rest-framework.org ]
psycopg2-binary = "2.8.4"                   # PostgreSQL driver
redis = "3.4.1"                             # The Python interface to the Redis key-value store
...