Bug 55811 - abort: path contains illegal component: .hg/branch
Summary: abort: path contains illegal component: .hg/branch
Status: CLOSED NOTABUG
Alias: None
Product: Sisyphus
Classification: Development
Component: etckeeper (show other bugs)
Version: unstable
Hardware: x86_64 Linux
: P5 normal
Assignee: Vitaly Chikunov
QA Contact: qa-sisyphus
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2025-08-30 18:03 MSK by Анатолий Кирсанов
Modified: 2025-09-04 16:16 MSK (History)
3 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Анатолий Кирсанов 2025-08-30 18:03:25 MSK
При коммите (ежедневный, при установке/удалении пакетов) получаю ошибку:

abort: path contains illegal component: .hg/branch
abort: path contains illegal component: .hg/undo.backup.branch.bck

(использую mercurial, его неплохо знаю, привык, нравится - все по инструкции к etckeeper)

Ошибка известна в другом дистрибутиве.
https://bugs.launchpad.net/ubuntu/+source/etckeeper/+bug/1115335

Непосредственная причина ошибки - передача на анализ файла в hg status ДО фильтрации в exclude_internal. Это про /etc/etckeeper/pre-commit.d/20warn-problem-files

Для решения предлагается (вместо того, что там написано в ветке для hg)
hardlinks=$(find . -type f ! -links 1 | exclude_internal | xargs hg status -n ) || true

Тут также используется xargs, вместо -exec (команда find). xargs, или что-то похожее по смыслу, здесь неизбежен, если нужно сначала найти файлы, потом отфильтровать внутренние, а потом получить статус в репозитарии. Именно hg status на неподходящем файле пишет в поток ошибок "path contains illegal component".

У меня болячка при применении этого "патча" решилась. Но я не провоцировал etckeeper нарваться на жесткие ссылки в положенных местах.

Для справки, в оригинале 20warn-problem-files было:
hardlinks=$(find . -type f ! -links 1 -exec hg status {} \; | exclude_internal ) || true
Comment 1 Vladislav Glinkin 2025-09-01 18:19:57 MSK
Версия пакета: etckeeper-1.18.23-alt1

Шаги воспроизведения:
1) # apt-get install mercurial etckeeper
2) # sed -i 's|VCS="git"|#VCS="git"|; s|#VCS="hg"|VCS="hg"|' /etc/etckeeper/etckeeper.conf
3) # etckeeper init
4) # etckeeper commit "Initial commit"
5) Установить/удалить пакет с конфигурационными файлами в /etc (nginx, к примеру)

Фактический результат:
abort: path contains illegal component: .hg/undo.backup.branch.bck
abort: path contains illegal component: .hg/branch

В логах при создании коммита

Ожидаемый результат:
Отсутствие данных сообщений

Предложенное исправление работает
Comment 2 Vitaly Chikunov 2025-09-01 23:56:30 MSK
/etc/etckeeper/etckeeper.conf:

 # Uncomment the following to avoid special file warning
 # (the option is enabled automatically for daily autocommits regardless).
 #AVOID_SPECIAL_FILE_WARNING=1
Comment 3 Анатолий Кирсанов 2025-09-02 00:21:12 MSK
(Ответ для Vitaly Chikunov на комментарий #2)
>  #AVOID_SPECIAL_FILE_WARNING=1
Специальный файл - это более широкое понятие (устройство, сокет ....).
Точно следует использовать костыли вместо приведения в порядок поиска жестких ссылок?
Comment 4 Анатолий Кирсанов 2025-09-02 01:13:42 MSK
Проверил использование этой переменной в etckeeper.

Это не решение проблемы, а полное отключение вывода найденных жестких ссылок и специальных файлов.

Сама переменная AVOID_SPECIAL_FILE_WARNING не дает вывести штатное предупреждение (что уже вредительство). Но ошибки при поиске жестких ссылок (пресловутый hg status) все равно должны быть (сам не проверял, по коду видно).

Этот чудный совет я видел при поиске решения раньше. Не удивлюсь, что его сейчас дают и нейросети.
Comment 5 Vitaly Chikunov 2025-09-02 01:56:37 MSK
1. Апстриму багрепортили два раза этот баг и он советовал только лишь менять эту настройку. Так что это его решение не фиксить, а отключать "WARNING". Возможно, тут можно с ним обсудить его подходы к разработке https://etckeeper.branchable.com/forum/

При этом, это пугающее абортом сообщение не баг, а лишь такой варнинг и регресса нет (список хардлинканых файлов правильно выводится).

2. Да можно ваше решение применить. Но, его надо исправить, чтоб исключить появившиеся corner cases:

1) если список пуст, то hg status все равно запустится и выведется общий hg status включающий и файлы без хардлинков (баг - выведутся лишние файлы), 
2) когда много аргументов передается в hg status, то если среди них будет любой вызывающий abort, то остальные файлы тоже не выведутся (а раньше они выводились, это регресс),
3) hg status при abort завершается с exit code 255, что для xargs специальный код возврата, который терминирует его выполнение и остальные файлы с stdin тоже не обработаются (это регресс).

Вот исправление

hardlinks=$(find . -type f ! -links 1 | exclude_internal | xargs -r -n1 sh -c 'hg status -n "$1" || exit 1' sh) || true

3. Но, на самом деле, все это over-engineering, достаточно - перенаправить вывод 2>/dev/null таким образом ошибки hg status просто не выведутся - они возникают только для файлов, которые не будут трекаться (внутренних/специальных файлов), а задача скрипта вывести варнинг для файлов которые *будут* трекаться о том что хардлинки в них могут не сохраниться в vcs.
Comment 6 Vitaly Chikunov 2025-09-02 02:21:11 MSK
Вот тестовое задание если захотите сами протестировать

  apt-repo test 393764
Comment 7 Vitaly Chikunov 2025-09-02 02:29:02 MSK
Вот тестовое задание для p11 (предыдущее было для Сизифа):

  apt-repo test 393765
Comment 8 Vitaly Chikunov 2025-09-02 03:52:04 MSK
Или если хочется оставить возможность hd status вывести теоретически полезную ошибку, то другой вариант, который исключает только содержимое .hg

  hardlinks=$(find . -path ./.hg -prune -o -type f ! -links 1 -exec hg status {} \; | exclude_internal ) || true
Comment 9 Анатолий Кирсанов 2025-09-04 16:16:19 MSK
(Ответ для Vitaly Chikunov на комментарий #7)
> Вот тестовое задание для p11 (предыдущее было для Сизифа):
> 
>   apt-repo test 393765

Спасибо. Поставил задачку.
Там тоже самое исправление, которое Вы описали самым последним (find . -path ./.hg -prune).

Да, ошибка при коммите , с которой я начинал, пропала. Нет теперь упоминаний о нехороших файлах в .hg.

Решил устроить провокацию и создал файл /etc/test-config.dummy и жесткую ссылку на него /etc/test-config.hard.dummy

# ls -l /etc/test-config.*
-rw-r--r-- 2 root root 0 сен  3 20:02 /etc/test-config.dummy
-rw-r--r-- 2 root root 0 сен  3 20:02 /etc/test-config.hard.dummy

В ежедневный коммит эти файлы попали:

# hg log -v -r tip
changeset:   12:7533df74157a
tag:         tip
user:        @example.com
date:        Thu Sep 04 04:02:36 2025 +0300
files:       .etckeeper test-config.dummy test-config.hard.dummy
описание:
daily autocommit

Но предупреждения о том, что в /etc затесались жесткие ссылки не было.