Преобразование ссылок уценки из встроенных в ссылки

У меня есть файл журнала изменений, отформатированный с использованием уценки Github.

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

This is some [example](http://www.stackoverflow.com) line of text.

Со временем, по мере того, как файл увеличивался в размере, он стал немного беспорядочным, в основном из-за такого способа вставки ссылок.

Я хочу преобразовать все ссылки из встроенных в справочные (см. описание каждого), то есть преобразовать приведенную выше строку в следующую:

This is some [example][1] line of text.

[1]: http://www.stackoverflow.com

Поскольку файл довольно большой и содержит много встроенных ссылок, мне было интересно, есть ли какой-нибудь автоматизированный способ сделать это. Я использую Sublime Text 3 для редактирования, но я не смог найти подходящий пакет для этой задачи. Возможно, какое-то умное регулярное выражение?


person Gabriel    schedule 18.06.2015    source источник
comment
Ожидаете ли вы, что инструмент будет объединять несколько вхождений одного и того же URL с одним и тем же ссылочным номером?   -  person reto    schedule 18.06.2015
comment
@reto хорошо, это не повредит, но я был бы готов сам исправить эти случаи, если бы это было настолько хорошо, насколько это возможно.   -  person Gabriel    schedule 18.06.2015
comment
Поставляется ли Sublime Text 3 с собственным скриптом или макроязыком, или у него есть интерфейс с внешним языком, таким как Perl, Python, Javascript или Visual Basic для приложений?   -  person Jongware    schedule 18.06.2015
comment
@Jongware, насколько я могу судить, Sublime 3 поддерживает регулярные выражения, вот и все. Я не думаю, что у него есть собственный скриптовый язык, по крайней мере, насколько мне известно. Я думаю, вы можете быть первым пользователем SO, с которым я столкнулся, с такой высокой репутацией, который не знаком с Sublime Text. Вы пользователь vi/emacs?   -  person Gabriel    schedule 18.06.2015
comment
Я твердо привержен графическим интерфейсам. В Windows я использую TextPad, в Mac — TextWrangler. Хотя ни один из них не предоставляет (очень хороший) язык сценариев, они могут запускать консольные программы и записывать их вывод, поэтому я бы пошел дальше и написал собственный инструмент на C только для этого. Требуемый уровень хранения/подсчета/извлечения выходит за рамки того, что может (и должен) делать GREP.   -  person Jongware    schedule 18.06.2015
comment
@Gabriel: я мог бы протестировать Sublime. Только для справки: он действительно напрямую поддерживает один из наиболее мощных языков: Python.   -  person Jongware    schedule 18.06.2015


Ответы (3)


Это большое требование!

Я только что создал новую программу Node.js (я знаю, что это не графический интерфейс, но кажется, что больше людей хотели бы иметь возможность), чтобы сделать это на GitHub.

Вот также код:

// node main.js test.md result.md

var fs = require('fs')
fs.readFile(process.argv[2], 'utf8', function (err, markdown) {
    if (err) {
        return console.log(err);
    }
    var counter = 1;
    var matches = {};
    var matcher = /\[.*?\]\((.*?)\)/g;
    while (match = matcher.exec(markdown)) {
        if (!matches[match[1]]) matches[match[1]] = counter++;
    }
    console.log(matches);
    Object.keys(matches).forEach(function(url) {
        var r = new RegExp("(\\[.*?\\])\\(" + url + "\\)", "g");
        markdown = markdown.replace(r, "$1[" + matches[url] + "]");
        markdown += "\n[" + matches[url] + "]: " + url;
    });

    fs.writeFile(process.argv[3], markdown, 'utf8', function (err) {
        if (err) return console.log(err);
    });

});
person bjfletcher    schedule 18.06.2015
comment
Не могли бы вы добавить опцию для форматирования числа (например, с тремя ведущими нулями и т. д.)? Будет ли он обрабатывать одни и те же ссылки, чтобы иметь один и тот же ссылочный номер? На самом деле редактор StackOverflow делает это очень хорошо. - person Royi; 18.05.2021

Сохраните это как mdrelink.py в папке «Пакеты», и вы сможете запустить его с помощью

view.run_command('mdrelink');

из командной консоли.

Я думаю, что правильно понял порядок — реверсирование необходимо, потому что в противном случае это приведет к беспорядку в уже кэшированных индексах следующих элементов. Он также должен автоматически пропускать уже используемые номера ссылок. Мой первый Python и мой первый плагин Sublime, так что будьте со мной нежны.

import sublime, sublime_plugin

class mdrelinkCommand(sublime_plugin.TextCommand):
    def run(self, edit):
        oldlinks = []
        self.view.find_all("^\s*(\[\d+\]):", sublime.IGNORECASE, "\\1", oldlinks)
        newlinkpos = self.view.find_all("\[.+?\](\(.+?\))")
        orgtext = []
        self.view.find_all("(\[.+?\])\(.+?\)", sublime.IGNORECASE, "\\1", orgtext)
        orglink = []
        self.view.find_all("\[.+?\]\((.+?)\)", sublime.IGNORECASE, "\\1", orglink)
        orglink.reverse()
        self.view.insert(edit, self.view.size(), '\n\n')
        counter = 1
        newnumbers = []
        for r in newlinkpos:
            while '['+str(counter)+']' in oldlinks:
                 counter += 1
            oldlinks.append('['+str(counter)+']')
            line = '[' + str(counter)+']: '+ orglink.pop() + '\n'
            newnumbers.append('  ['+str(counter)+']')
            self.view.insert(edit, self.view.size(), line)
        for r in reversed(newlinkpos):
            self.view.replace(edit, r, orgtext.pop()+newnumbers.pop())
person Jongware    schedule 18.06.2015
comment
И вам потребовалось всего пару часов, чтобы вы перестали использовать Sublime и написали для него плагин :) Вам следует подумать о загрузке этого на packagecontrol. io, где находятся все пакеты Sublime, и их можно легко установить с помощью диспетчера пакетов. Я попробую это, как только смогу. Спасибо Jongware! - person Gabriel; 19.06.2015
comment
У кого-нибудь получилось? Кажется, это не работает для меня. - person Royi; 18.05.2021

Наткнулся на этот вопрос благодаря Google. Может быть, это может помочь другим:

Мой ответ не относится к Sublime, но если вы уже используете JavaScript (Node), я бы использовал синтаксический анализатор MD и преобразователь CST, например примечание.

Например, чтобы преобразовать все встроенные ссылки в README.md в ссылки в стиле ссылок с числовым возрастанием, вы можете запустить следующее:

sudo npm install -g remark-reference-links remark-cli
npx remark README.md -o --use reference-links

Или, если вам нужны ссылки в стиле ссылок, полученные из исходного uri:

sudo npm install -g remark-defsplit remark-cli
npx remark README.md -o --use defsplit

Опция --use remark-cli плохо сочетается с npx@6, но, возможно, ее можно сократить до временной однострочника с npx@7. То же самое может быть достигнуто с некоторой комбинацией плагинов редактора на основе замечаний. Надеюсь, эта информация поможет таким людям, как я, не тратить целый день на сборку ненадежного решения на основе регулярных выражений :)

person Xunnamius    schedule 01.01.2021