`libalternatives` в openSUSE: майбутнє управління альтернативами

⏱ 5 min read • TECH

Управління декількома версіями одного інструмента - правильний шлях для сучасних дистрибутивів.


Table of Contents

  1. Вступ: навіщо потрібен механізм альтернатив
  2. Чому update-alternatives вже не задовольняє сучасні потреби
  3. Що таке libalternatives
  4. Порівняння: update-alternatives vs libalternatives
  5. Команди alts: довідник
  6. Висновки
  7. Швидка шпаргалка

Вступ: навіщо потрібен механізм альтернатив

update-alternatives - це класичний Linux-інструмент для управління симлінками команд, що мають декілька встановлених реалізацій. Кожен пакет реєструє себе як альтернативу для певної ролі (editor, java, python тощо), а система зберігає симлінки в /etc/alternatives/, вказуючи на поточну альтернативу з найвищим пріоритетом.

Спочатку це була Debian-тулза, але її швидко підхопили всі популярні дистрибутиви. Проте, з розвитком сучасних файлових систем і архітектур дистрибутивів, classic approach почав виявляти свої обмеження.


Чому update-alternatives вже не задовольняє сучасні потреби

Насправді, для більшості дистрибутивів він працює добре. Всіх, крім одного. openSUSE, з його унікальною архітектурою на базі Btrfs та snapshots, зіткнувся з фундаментальною проблемою.

Проблема 1: лише одна активна альтернатива

Симлінк може вказувати тільки на одну ціль. Для простих випадків (наприклад, вибір між vim і nano) цього достатньо. Однак коли мова йде про розробку, де одночасно встановлені Node.js 18, 20 і 22, виникають проблеми.

Сценарій:

  • Ви явно запускаєте програму через node18
  • Вона викликає дочірній процес через #!/usr/bin/node
  • Дочірній процес запускається на Node.js 22 (бо симлінк /usr/bin/node вказує на неї)
  • Результат: непередбачувана поведінка і важкі для діагностики помилки

Проблема 2: відсутність юзер-левел налаштувань

update-alternatives - це інструмент системного адміністратора. Звичайний користувач без прав root не може змінити налаштування для свого облікового запису. Єдиний обхідний шлях - ручні симлінки у ~/.local/bin, що не є універсальним рішенням.

Проблема 3: /var і снапшоти (головна проблема для openSUSE)

Ось де openSUSE зіткнувся з архітектурним обмеженням:

  • update-alternatives зберігає свій стан у /var/lib/alternatives/
  • У openSUSE коренева файлова система (/) снапшотується через Btrfs
  • /var навмисно винесений в окремий btrfs-subvolume, який не входить до снапшоту

Наслідки: Коли ви встановлюєте пакет, RPM-скрипти викликають update-alternatives, який записує стан у /var/lib/alternatives/. Цей запис існує поза снапшотом. Якщо ви виконуєте rollback системи до попереднього снапшоту - /var залишається з новим станом, а стан пакетів у снапшоті розходиться зі станом alternatives. Система стає неконсистентною.

Для звичайного Tumbleweed-робочого столу це може бути неприємністю. Для MicroOS або будь-якої image-based системи - це концептуальна несумісність. Коли ОС побудована навколо атомарних оновлень і гарантованих rollback’ів, механізм, що зберігає стан за межами снапшотів, є архітектурним протиріччям.


Що таке libalternatives

libalternatives - це інноваційний підхід, запропонований Adam Majer у 2021 році в розсилці openSUSE Factory. Основна ідея: перенести логіку вибору версії з «магічного симлінка» в бібліотеку часу виконання.

Архітектура

Компонентupdate-alternativeslibalternatives
ТипІнструмент часу встановленняБібліотека часу виконання
Модифікація стануТак (під час встановлення пакета)Ні (тільки читання під час виконання)
Збереження конфігурації/var/lib/alternatives//usr/share/libalternatives/

Технічна реалізація

  1. Конфігураційні файли: Пакет розміщує в /usr/share/libalternatives/<ім'я_програми>/<пріоритет>.conf файл з описом альтернативи. Наприклад:

    /usr/share/libalternatives/java/3000.conf

    з вмістом:

    binary=/usr/lib64/jvm/graalvm-jdk-25.0.1+8.1/bin/java
    group=java,keytool,rmiregistry
  2. Бінарники: Самі бінарники (/usr/bin/java, /usr/bin/node тощо) стають симлінками на /usr/bin/alts

  3. Механізм роботи: Коли ви запускаєте java, насправді виконується alts, який:

    • Через argv[0] розуміє, яку програму викликали
    • Читає конфігураційні файли з /usr/share/libalternatives/java/
    • Враховує системні та користувацькі уподобання (за пріоритетами)
    • Передає виклик потрібному бінарнику через exec()

Переваги архітектури

  • Конфігурація у складі пакета: Файли в /usr/share/ є частиною пакета і входять до знімку файлової системи
  • Атомарність: Rollback повертає все в узгоджений стан, включно зі станом альтернатив
  • Ніяких записів у /var/: Уникнення проблеми з снапшотами

Ієрархія пріоритетів

libalternatives використовує прозору ієрархію:

юзер → адміністратор → пакет

Юзерські налаштування (у ~/.config/libalternatives/) мають найвищий пріоритет. Системний адміністратор може встановити одне значення, пакет - запропонувати інше, але вибір користувача переважить обидва.

Важливо: Користувач вибирає пріоритет (числове значення), а не шлях до бінарника. Пріоритети визначаються пакетами у їхніх конфігураційних файлах.


Порівняння: update-alternatives vs libalternatives

Аспектupdate-alternativeslibalternatives
ТипІнструмент часу встановленняБібліотека часу виконання
Збереження стану/var/lib/alternatives//usr/share/libalternatives/
Сумісність зі снапшотамиНі (стан поза снапшотом)Так (стан у складі снапшота)
Юзер-левел налаштуванняНі (потрібен root)Так (~/.config/libalternatives/)
Overhead при запускуНі (прямий симлінк)Так (читання конфігурації + exec())
Сумісність з іншими дистрибутивамиТак (стандарт de-facto)Ні (тільки openSUSE)
Управління slave linksТак (через --slave)Так (через конфігураційні файли, параметр group)
Рівень controlСистемнийСистемний + користувацький

Команди alts: довідник

Управління libalternatives здійснюється через команду alts. На відміну від update-alternatives, де вказується шлях до бінарника, у libalternatives вибирається пріоритет альтернативи.

КомандаОписПриклад
alts -lПоказує всі зареєстровані програмиalts -l
alts -l <name>Показує всі доступні альтернативи для вказаної програмиalts -l java
alts -t <name>Показує поточну цільову альтернативу для програмиalts -t java
alts -u -n <name> -p <priority>Встановлює альтернативу для поточного користувачаalts -u -n java -p 3000
sudo alts -s -n <name> -p <priority>Встановлює системний defaultsudo alts -s -n java -p 3105
alts -u -n <name>Скидає користувацьке перевизначення до системного defaultalts -u -n java

Опції командного рядка

ОпціяОпис
-hВивести довідку
-l[<name>]Список програм або альтернатив для вказаної програми
-t <name>Показати цільовий бінарник для програми
-uКористувацьке перевизначення (default для не-root)
-sСистемне перевизначення (default для root)
-n <program>Назва програми для перевизначення
-p <priority>Пріоритет альтернативи (число)

Примітка: Юзерські налаштування зберігаються у ~/.config/libalternatives/ і мають найвищий пріоритет. Системні налаштування зберігаються у /etc/libalternatives/.

Важливо: Пріоритети визначаються пакетами у конфігураційних файлах /usr/share/libalternatives/<name>/<priority>.conf. Користувач може вибрати лише існуючий пріоритет, а не довільно вказати шлях до бінарника.


Висновки

libalternatives - це символічний крок openSUSE у напрямку сучасної архітектури дистрибутивів. Він вирішує конкретну проблему сумісності зі снапшотами, яка критична для image-based систем типу MicroOS.

Поточний статус у openSUSE

Згідно з офіційною документацією, проекту пропонує три стратегії для мейнтейнерів пакетів:

  1. Міграція на libalternatives - для ключових пакетів (Java, Node.js тощо)
  2. Використання Provides/Conflicts - для взаємовиключних пакетів
  3. Залишити update-alternatives - якщо альтернативи не підходять

На практиці пакети мігрують поступово. Java вже перейшла на libalternatives, інші знаходяться в процесі.

Важливо: update-alternatives нікуди не зникне і залишиться доступним у openSUSE. Проте, для ключових пакетів libalternatives поступово стає стандартом.

Поширення поза openSUSE

Поза openSUSE ситуація стабільна. update-alternatives залишається де-факто стандартом:

  • Вбудований у Debian Policy
  • присутній у RHEL/CentOS
  • Використовується у Fedora

Навряд чи інші дистрибутиви підуть шляхом SUSE в найближчому майбутньому.


Швидка шпаргалка

# Перегляд усіх зареєстрованих програм
alts -l

# Перегляд усіх альтернатив для java
alts -l java

# Перегляд поточної альтернативи для java
alts -t java

# Встановлення для поточного користувача (вибираємо пріоритет 3000)
alts -u -n java -p 3000

# Встановлення системного default (потрібен sudo)
sudo alts -s -n java -p 3105

# Скидання до системного default (видаляє користувацьке перевизначення)
alts -u -n java

# Перевірка, яка версія java насправді запускається
alts -t java
java -version

# Перегляд конфігураційних файлів для java
ls -la /usr/share/libalternatives/java/
cat /usr/share/libalternatives/java/3000.conf

Примітка: Щоб дізнатися доступні пріоритети для програми, використайте alts -l <name>. Пріоритети відображаються у форматі Priority: XXXX.

Comments

© 2025 CodeByMe.de | Engineering