К сожалению, встроенного механизма для распространения и установки дополнительного софта в OS Inferno нет. Если вы написали модуль для Limbo или полноценное приложение, и хотите им поделиться, то вариантов его распространения немного:
Как вы понимаете, первый вариант — это, фактически, не вариант. :) Это возврат назад, в пещеры. Второй вариант используется, например, для всего софта в репозитории mjl. Но и у этого подхода есть неприятные ограничения, вызванные тем, что ваши файлы в результате просто копируются в системные каталоги
Я хочу предложить альтернативный подход, разработанный по мотивам DJB'шного slashpackage. Update: этот подход был недавно принят разработчиками инферно, так что его уже можно считать не альтернативным, а официальным. :)
Все 3rd-party модули/приложения при таком подходе должны искать свои файлы и файлы других не стандартных модулей/приложений внутри каталога
При таком подходе, для установки нового модуля/приложения общесистемно (т.е. от root) достаточно одной команды! Например, если модуль/приложение выложен в репозиторий Mercurial на Google Code:
Установка обычным пользователем локально требует двух команд (предполагается, что в домашнем каталоге пользователя заранее создан подкаталог opt/powerman/):
Дело в том, что репозиторий уже содержит откомпилированные .dis-файлы в подкаталогах
Для того, чтобы ваше приложение использовало не ту версию 3rd-party модуля/приложения, которая по умолчанию находится в
Для компиляции и установки (например, если вы внесли локальные изменения в код 3rd-party модуля/приложения) достаточно запустить
Зависит от способа распространения пакета, но в общем виде сводится к одной-двум командам. Например, для того же Mercurial всё сводится к обычным
в каталоге
Проще некуда. Думаю, вы уже догадались, как это делается, но не могу отказать себе в удовольствии это написать:
О, это сложная операция, без базы данных никак — чем мы хуже rpm/apt/portage? :)
Как видите, управлять такими пакетами пользователю действительно просто и удобно. Теперь давайте посмотрим, как их использовать.
Длинновато? Можно укоротить с помощью функций sh (определения функций прописать один раз в profile):
Update: Ещё один способ описан ниже, см. /opt/setup.sh.
Это сразу заработает если модули установлены локально, т.е. в подкаталог
Чтобы создать пакет устанавливаемый в
Все пути относительные, например:
Update!
Ещё один вариант использования 3rd-party модулей и приложений заключается в том, чтобы подключить их с помощью bind из
Update2!
Улучшенная версия описанного выше
Кроме этого, разработана подборка mkfile-ов аналогичных стандартным, но поддерживающим работу с /opt-проектами, и рекомендованных для использования в ваших проектах если они либо используют /opt-модули либо сами устанавливаются в /opt: inferno-opt-mkfiles.
Несколько простых модулей/приложений написанных в этом стиле можно найти поискав «inferno contrib» на Google Code.
Update: Выложен пример /opt-проекта для использования в качестве шаблона для быстрого старта своих проектов: inferno-opt-skel.
Русское описание языка Limbo
Русская wiki по OS Inferno, переводы документации
- просто выложить ваши файлы на любом сайте, и предоставить пользователям вручную устанавливать их в свою систему куда и как угодно
- использовать такие же mkfile/mkconfig файлы какие используются стандартными модулями и приложениями в
/appl/
Как вы понимаете, первый вариант — это, фактически, не вариант. :) Это возврат назад, в пещеры. Второй вариант используется, например, для всего софта в репозитории mjl. Но и у этого подхода есть неприятные ограничения, вызванные тем, что ваши файлы в результате просто копируются в системные каталоги
/dis/
, /module/
, etc. (точно так же, как стандартные модули и приложения из /appl/
):- если используется *nix как host OS, и Inferno установлена общесистемно root-ом или менеджером пакетов вашего дистрибутива, то для установки дополнительных модулей/приложений потребуются права root (либо
sudo mk
в host OS, либоsudo emu
и нативныйmk
) - глобальная установка неудобна, если хочется для своего приложения использовать модифицированную версию этих модулей/приложений
- глобальная установка неудобна, если разным приложениям нужны разные версии одного и того же модуля (mjl решает эту проблему традиционным для *nix способом добавляя номер major версии к имени модуля, что не очень элегантно и приводит к именам вроде «util0.m»)
- деинсталляция превращается в нетривиальную операцию, что в конечном итоге приводит к замусориванию системных каталогов
- имена модулей/приложений разных разработчиков могут конфликтовать (впрочем, эта проблема есть и в *nix/win, и её можно обойти используя подкаталоги в
/dis/
и/module/
с именем разработчика или его сайта)
Я хочу предложить альтернативный подход, разработанный по мотивам DJB'шного slashpackage. Update: этот подход был недавно принят разработчиками инферно, так что его уже можно считать не альтернативным, а официальным. :)
Структура каталогов
- Создаём глобальный каталог для всего 3rd-party софта
/opt/
. Update: каталог уже существует в текущей версии инферно. - В
/opt/
создаются отдельные подкаталоги для каждого разработчика/организации, а в них подкаталоги для каждого модуля/приложения — чтобы избежать конфликтов имён между разными разработчиками (напр./opt/powerman/hashtable/
). - В каталоге с модулем/приложением создаётся структура каталогов аналогичная системным:
dis/
dis/lib/
module/
appl/cmd/
appl/lib/
- и т.д. при необходимости
Все 3rd-party модули/приложения при таком подходе должны искать свои файлы и файлы других не стандартных модулей/приложений внутри каталога
/opt/
.Управление пакетами
Установка
При таком подходе, для установки нового модуля/приложения общесистемно (т.е. от root) достаточно одной команды! Например, если модуль/приложение выложен в репозиторий Mercurial на Google Code:
# hg clone https://inferno-contrib-hashtable.googlecode.com/hg/ $INFERNO_ROOT/opt/powerman/hashtable
Установка обычным пользователем локально требует двух команд (предполагается, что в домашнем каталоге пользователя заранее создан подкаталог opt/powerman/):
$ hg clone https://inferno-contrib-hashtable.googlecode.com/hg/ opt/powerman/hashtable
; bind opt /opt
Дело в том, что репозиторий уже содержит откомпилированные .dis-файлы в подкаталогах
dis/
и dis/lib/
, и при этом подходе после копирования каталога с модулем/приложением в /opt/
его .dis-файлы автоматически оказываются именно там, где они и должны быть после «установки».Выбор конкретной версии/использование модифицированной версии
Для того, чтобы ваше приложение использовало не ту версию 3rd-party модуля/приложения, которая по умолчанию находится в
/opt/
, достаточно перед запуском вашего приложения подключить в /opt/
нужную ему версию (а благодаря namespaces в Inferno это не повлияет на работу других приложений, которым нужна как раз версия по умолчанию):; bind ./my-modified-hashtable/ /opt/powerman/hashtable/
; ./my-app
(Пере)сборка пакета
Для компиляции и установки (например, если вы внесли локальные изменения в код 3rd-party модуля/приложения) достаточно запустить
mk install
в его каталоге (например, /opt/powerman/hashtable/
). При этом откомпилированные dis-файлы установятся в подкаталог dis/
этого модуля/приложения.Обновление
Зависит от способа распространения пакета, но в общем виде сводится к одной-двум командам. Например, для того же Mercurial всё сводится к обычным
$ hg pull
$ hg update
в каталоге
opt/powerman/hashtable/
. При этом из репозитория подтянутся в т.ч. обновлённые .dis-файлы в opt/powerman/hashtable/dis/
, и это и будет по сути обновлением пакета.Деинсталляция
Проще некуда. Думаю, вы уже догадались, как это делается, но не могу отказать себе в удовольствии это написать:
; rm -r /opt/powerman/hashtable
Получить список установленного 3rd-party софта
; ls /opt/*
Получить список файлов, входящих в пакет
О, это сложная операция, без базы данных никак — чем мы хуже rpm/apt/portage? :)
; fs print /opt/powerman/hashtable/
Использование этих модулей/приложений
Как видите, управлять такими пакетами пользователю действительно просто и удобно. Теперь давайте посмотрим, как их использовать.
Приложения
; /opt/powerman/retrymount/dis/retrymount
Длинновато? Можно укоротить с помощью функций sh (определения функций прописать один раз в profile):
; fn retrymount { /opt/powerman/retrymount/dis/retrymount $* }
; retrymount
Update: Ещё один способ описан ниже, см. /opt/setup.sh.
Модули
include "opt/powerman/hashtable/module/hashtable.m";
load HashTable HashTable->PATH;
Это сразу заработает если модули установлены локально, т.е. в подкаталог
opt/
. Если модули установлены глобально в /opt/
, то нужно запускать limbo с дополнительным параметром -I/
для нативного limbo, или -I$INFERNO_ROOT
при запуске limbo из host OS. Это тоже можно настроить однократно, например для нативного limbo:; fn limbo { builtin limbo -I/ $* }
Разработка этих модулей/приложений
Чтобы создать пакет устанавливаемый в
/opt/
нужно соблюдать несколько простых правил:module/hashtable.m-файл:
PATH: con "/opt/powerman/hashtable/dis/lib/hashtable.dis";
appl/{lib,cmd}/*.b-файл:
include "../../module/hashtable.m";
load HashTable HashTable->PATH;
mkfile:
Все пути относительные, например:
MODULES=\
../../module/hashtable.m\
DISBIN=../../dis/lib
/opt/setup.sh
Update!
Ещё один вариант использования 3rd-party модулей и приложений заключается в том, чтобы подключить их с помощью bind из
/opt/
в стандартные каталоги. Как сделать это просто и универсально пока не совсем понятно, но есть частичное решение. Показанный ниже скрипт (я его обычно держу в /opt/setup.sh
) подключит все команды и man-страницы из /opt/*
в /dis/
и /man/
. Таким образом, команды можно будет запускать просто по имени, без полного пути вроде /opt/powerman/retrymount/dis/retrymount
и документацию на 3rd-party приложения и модули просматривать штатными средствами.#!/dis/sh -n
load std
for d in /opt/*/man/* /opt/*/*/man/* {
or {ftest -d $d} {raise continue}
n := `{basename $d}
bind -b $d /man/$n
}
for d in /opt/*/dis/* /opt/*/*/dis/* {
or {ftest -d $d} {raise continue}
n := `{basename $d}
and {~ $n lib} {raise continue}
and {~ $n cmd} {n=''}
bind -b $d /dis/$n
}
Update2!
Улучшенная версия описанного выше
/opt/setup.sh
теперь выложена в виде проекта inferno-opt-setup. Функциональность разделена на два скрипта: /opt/setup/cmd
и /opt/setup/man
, которые можно использовать независимо.Кроме этого, разработана подборка mkfile-ов аналогичных стандартным, но поддерживающим работу с /opt-проектами, и рекомендованных для использования в ваших проектах если они либо используют /opt-модули либо сами устанавливаются в /opt: inferno-opt-mkfiles.
Примеры
Несколько простых модулей/приложений написанных в этом стиле можно найти поискав «inferno contrib» на Google Code.
Update: Выложен пример /opt-проекта для использования в качестве шаблона для быстрого старта своих проектов: inferno-opt-skel.
Ссылки
Русское описание языка Limbo
Русская wiki по OS Inferno, переводы документации