Бот GitHub «permanent link» незаметно исказил смысл моего поста

Около года назад я опубликовал сообщение на платформе Discourse GitHub, в котором привёл множество ссылок вида «https://github.com/OWNER/REPO/tree/BRANCH/path», чтобы обсудить, как GitHub.com обрабатывает такие URL. Моё сообщение сразу же было отредактировано системой с сообщением «Ссылка на GitHub заменена на постоянную ссылку», что, судя по всему, вызвано плагином discourse-github. Хотя замена названия ветки на постоянную ссылку на конкретный коммит может быть полезной функцией в типичном случае, когда пост цитирует определённый код, в специальном случае обсуждения обработки URL GitHub это редактирование уничтожило смысл моего сообщения. Мне повезло, что я сразу заметил правку бота, и после нескольких раундов борьбы с ним я в конце концов нашёл обходной путь: добавление тега <span>, чтобы предотвратить совпадение шаблона бота, например:

https://github.com/OWNER/REPO/tree/<span>BRANCH</span>/PATH

Однако другие авторы могут не заметить правку бота и оставить пост, который запутает читателей.

Какое лучшее решение, чтобы избежать нежелательных правок постоянных ссылок GitHub в конкретном сообщении? В целом, я считаю, что ботам не следует автоматически редактировать посты, рискуя испортить их. Безопаснее было бы (1) спрашивать автора при сохранении поста, нужно ли редактировать ссылки, или (2) заставлять бота добавлять постоянную ссылку, не удаляя исходную. (Кажется, я видел подобных ботов на других сайтах, возможно, на Reddit, которые добавляют информацию, не удаляя существующую.) Если разработчики Discourse считают эти варианты слишком некрасивыми или слишком трудоёмкими для редкого случая использования, можно рассмотреть другие варианты: (3) показывать уведомление после сохранения поста со ссылкой на информацию о том, как автор может избежать таких правок при необходимости — либо (a) в виде отдельного баннера в интерфейсе, либо (b) просто строки текста, добавленной ботом в конец поста.

Я не уверен, какой дизайн будет наиболее разумным для того, чтобы автор мог отказаться от таких правок. Настройки исключения на уровне всего сайта в плагине discourse-github, основанные на целевой ссылке, не подходят для этой цели. Возможно, мой текущий обходной путь с тегом <span> будет достаточным. Даже если в Discourse ничего не изменится, я надеюсь, что этот пост поможет другим авторам, которые заметят проблему, легче найти обходной путь.

Примечание: ранее я поднимал эту тему на форуме GitHub, так как предполагал, что бот «постоянной ссылки» специфичен для экземпляра GitHub, но один из комментаторов сообщил мне, что это общая функция Discourse, поэтому я поднимаю этот вопрос здесь.

Спасибо за внимание!

2 лайка

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

Вот несколько примеров, которые можно использовать в качестве тестовых случаев для её исправления:

  1. Простая ссылка, созданная путём вставки URL. Я ожидаю, что она будет переписана, и так оно и есть: subdomain-static/forums-enhancements.js at master · ClassicPress/subdomain-static · GitHub
  2. Markdown-ссылка вида [url](url). Я ожидаю, что эта ссылка не будет переписана, поскольку я явно указал и текст, и URL. Вместо этого переписывается текст ссылки, а URL ссылки остаётся без изменений. Это ошибка: https://github.com/ClassicPress/subdomain-static/blob/master/forums-enhancements.js
  3. URL, заключённый в обратные кавычки. Это не ссылка и не должна переписываться, но переписывается: https://github.com/ClassicPress/subdomain-static/blob/master/forums-enhancements.js
  4. URL в блоке кода, оформленном тройными обратными кавычками. Это не ссылка и не должна переписываться, но переписывается:
    https://github.com/ClassicPress/subdomain-static/blob/master/forums-enhancements.js
    

Я считаю, что должна переписываться только ссылка из пункта (1). Это сделало бы поведение более предсказуемым и переписывало бы только «простые» ссылки. Ссылки, для которых использована конкретная структура Markdown (что можно рассматривать как способ выразить определённое намерение), должны оставаться без изменений.

1 лайк

Похоже, что эта функция не включена на meta.discourse.org?

Кстати, я не согласен: я считаю, что в (2) правка: общем случае [text](URL) (назовём его 2a) URL ссылки должен переписываться так же, как и в пункте (1). (Я согласен, что текущее поведение, при котором переписывается текст, но не URL, совершенно неработоспособно.) Я выбираю между вариантами (1) и (2a) исходя из того, полезно ли или отвлекает ли читателя видимость URL, а не исходя из каких-либо намерений относительно того, должна ли ссылка указывать на версию кода на момент написания или на момент чтения. Конечно, я осведомлён о проблеме постоянных ссылок, поэтому, когда мне нужна постоянная ссылка, я создаю её сам. Но в более общем смысле, если администратор Discourse решает включить бот постоянных ссылок, то, presumably, это потому, что он считает, что большинство его пользователей не осознают риск того, что ссылки на основе имен веток могут устареть, и я не думаю, что использование синтаксиса ссылок Markdown служит сколько-нибудь значимым сигналом того, что конкретный пользователь осведомлён о проблеме, но хочет отказаться от переписывания именно этой ссылки.

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

Да, именно так. В настоящее время нет способа его переопределить. Написание [url](url) (текст ссылки и URL идентичны) определённо стало бы сигналом для бота, что эту ссылку не следует переписывать, поскольку другого повода писать её именно так нет.

Она есть, если вы хотите задать ссылке собственный заголовок, а не полагаться на тот, который будет выведен из целевого URL, то есть [заголовок](url). Присвоение ссылке заголовка не указывает на предпочтение переписывания URL, поэтому я согласен с @mattmccutchen, что варианты 1 и 2 должны вести себя одинаково в отношении переписывания URL.

Можно привести аргумент, что полное совпадение заголовка с URL служит указанием на то, что его не следует переписывать, но что, если пользователь хочет указать заголовок и при этом не хочет переписывать URL? Должен существовать какой-то другой способ это указать.

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

Встроенное изображение можно изменить в размере следующим образом:
![заголовок|100x200](url)

Таким образом, плагин discourse-github мог бы (предположительно) быть настроен на поиск чего-то подобного:
[заголовок|github-no-rewrite](url)

Ах, я не понял, что ваш пункт (2) относится только к частному случаю, когда текст и URL совпадают. Моё утверждение касалось общего случая, когда текст и URL могут различаться; назовём это теперь (2a).

В случае (2) я согласен, что странно переписывать URL, но не текст, оставляя их несогласованными. Однако, на мой взгляд, можно с тем же успехом утверждать, что если мы хотим избежать несогласованности, лучший способ — переписать и URL, и текст, а не оставить их без изменений. Поэтому я не считаю убедительным аргумент о том, чтобы рассматривать (2) как исключение. Поскольку у нас должно быть исключение, работающее для (2a), я склонен просто позволить пользователям использовать то же исключение и для (2), не усложняя дизайн. (Кажется, это также была идея Саймона Мэннинга?)

Не уверен, что правильно понимаю это (или возможно ли это), но можно ли использовать экранирование пробелом, как в Inline PDF Previews - #45 by Johani? То есть [ text]( url) не переписывал бы ни текст, ни URL, а всё остальное автоматически изменялось бы?

Эта версия должна остаться без изменений и не быть переписана, позвольте мне посмотреть:

https://github.com/correctcomputation/checkedc-clang/blob/master-post-microsoft/clang/docs/checkedc/Setup-and-Build.md

записан как:

<https://github.com/correctcomputation/checkedc-clang/blob/master-post-microsoft/clang/docs/checkedc/Setup-and-Build.md>

Это не валидный тест, поскольку переписывание постоянных ссылок GitHub полностью отключено в этом экземпляре Discourse. (Интересно, что это говорит о данной функции, если она отключена на «официальном» экземпляре :upside_down_face:)

Если бы вы написали этот пример как тестовый случай для replace_github_non_permalinks.rb / replace_github_non_permalinks_spec.rb, то, я думаю, вы обнаружили бы, что эта ссылка также была бы переписана.

1 лайк