Next: , Previous: , Up: Программный интерфейс   [Contents][Index]


9.10 Деривации

Действия низкоуровневой сборки и среда, в которой они выполняются, представлены через derivations. Derivation содержит следующую информацию:

Derivation’ы позволяют клиентам демона передавать действия сборки в store. Они существуют в двух формах: как представление в памяти, как на стороне клиента, так и на стороне демона, и в виде файлов в хранилище, имена которых заканчиваются на .drv - эти файлы называются derivation paths. Derivation paths могут быть переданы в процедуру build-derivations для выполнения действий сборки, которые они предписывают (see Хранилище).

Такие операции, как загрузка файлов и проверка версий, для которых заранее известен ожидаемый хэш содержимого, моделируются как fixed-output derivations. В отличие от обычных дериваций, выходные данные деривации с фиксированным выходом не зависят от его входных данных - например, загрузка исходного кода дает тот же результат независимо от метода загрузки и используемых инструментов.

Outputs of derivations—то есть результаты сборки—имеют множество references, в соответствии с указаниями RPC references или команды guix gc --references (see Вызов guix gc). References - это набор run-time зависимостей результатов сборки. References - это подмножество входных данных derivation; это подмножество автоматически вычисляется демоном сборки путем сканирования всех файлов в выходных данных.

Модуль (guix diverations) предоставляет представление derivation’ов в виде Scheme объектов, а также процедуры для создания derivation’ов и других манипуляций с ними. Самым низкоуровневым примитивом для создания derivation’а является процедура derivation:

Scheme Procedure: derivation store name builder args [#:outputs '(\"out\")] [#:hash #f] [#:hash-algo #f] [#:recursive? #f] [#:inputs '()] [#:env-vars '()]  [#:system

(%current-system)] [#:references-graphs #f]  [#:allowed-references #f] [#:disallowed-references #f]  [#:leaked-env-vars #f] [#:local-build? #f]  [#:substitutable? #t] [#:properties ’()] Собрать производную с заданными аргументами и вернуть полученный объект <derivation>.

Когда заданы hash и hash-algo, создается fixed-output derivation - то есть результат, который известен заранее, например, загрузка файла. Кроме того, если recursive? истинна, то этот фиксированный вывод может быть исполняемым файлом или каталогом, а hash должен быть хешем архива, содержащего этот вывод.

Когда links-graphs истинна, данная переменная должна быть списком из пар имя файла и путь к store. В этом случае граф ссылок каждого store path экспортируется в среду сборки в соответствующий файл в простом текстовом формате.

Когда allowed-links истинна, данная переменная должна быть списком store item’ов или выходных данных, на которые может ссылаться выход derivation’а. Аналогично, disallowed-links, если она истинна, данная переменная должна быть списком сущностей, на которые не могут ссылаться выходные данные.

Когда leaked-env-vars истинна, данная переменная должна быть списком строк, обозначающих переменные среды, которым разрешено “просачиваться” из среды демона в среду сборки. Это применимо только к fixed-output derivation’ам, т.е. когда hash истинна. Основное использование - разрешить передачу таких переменных, как http_proxy, derivation’ам, которые загружают файлы.

Когда local-build? истинна, объявить, что производная не является хорошим кандидатом для offload и должна быть собрана локально (see Использование функционала разгрузки). Это справедливо для небольших derivation’ов, когда затраты на передачу данных перевешивают выгоды.

Когда substitutable? ложно, объявить, что substitutes derivation’ов не должны использоваться (see Подстановки). Это полезно, например, при создании пакетов, которые фиксируют подробности набора команд центрального процессора.

properties должна быть списком ассоциаций, описывающих “свойства” derivation’а. При выводе они сохраняются как есть, без интерпретации.

Вот пример со shell скриптом в качестве его builder’а, предполагая, что store является открытым соединением с демоном, а bash указывает на исполняемый файл Bash в store:

(use-modules (guix utils)
             (guix store)
             (guix derivations))

(let ((builder   ; add the Bash script to the store
        (add-text-to-store store "my-builder.sh"
                           "echo hello world > $out\n" '())))
  (derivation store "foo"
              bash `("-e" ,builder)
              #:inputs `((,bash) (,builder))
              #:env-vars '(("HOME" . "/homeless"))))
 #<derivation /gnu/store/…-foo.drv => /gnu/store/…-foo>

Как можно догадаться, этот примитив неудобно использовать напрямую. Конечно, лучший подход - писать скрипты сборки на Scheme! Лучше всего для этого написать код сборки как “G-выражение” и передать его в gexp->derivation. Для получения дополнительной информации, see G-Expressions.

Когда-то давно gexp->derivation не существовала, и построение derivation’ов с помощью кода сборки, написанного на Scheme, достигалось с помощью build-expression->derivation, описанной ниже. Эта процедура теперь устарела и заменена более приятным gexp->derivation.

Scheme Procedure: build-expression->derivation store name exp  [#:system (%current-system)] [#:inputs '()] [#:outputs '(\"out\")] [#:hash #f] [#:hash-algo #f]  [#:recursive? #f]

[#:env-vars ’()] [#:modules ’()]  [#:references-graphs #f] [#:allowed-references #f]  [#:disallowed-references #f]  [#:local-build? #f] [#:substitutable? #t] [#:guile-for-build #f] Возвращает derivation, которая исполняет Scheme выражение exp как builder для derivation’а name. inputs должна быть списком кортежей (name drv-path sub-drv); когда sub-drv опущена, предполагается "out". modules - это список имен модулей Guile из текущего пути поиска, которые будут скопированы в store, скомпилированы и станут доступными в пути загрузки во время выполнения exp—например, ((guix build utils) (guix build gnu-build-system)).

exp выполняется в среде, где %output привязан к списку пар output/path, а где %build-inputs привязан к списку пар строка/output-path сделаными из input. Необязательно, env-vars - это список пар строк, определяющих имя и значение переменных среды, видимых builder’у. Builder завершает работу, передавая результат exp в exit; таким образом, когда exp возвращает #f, сборка считается неудачной.

exp собирается с использованием guile-for-build (derivation). Когда guile-for-build опущена или равна #f, вместо этого используется значение fluid’а %guile-for-build.

См. в процедуре derivation значение references-graphs, allowed-references, disallowed-references, local-build? и substitutable?.

Вот пример single-output derivation’а, которая создает каталог, содержащий один файл:

(let ((builder '(let ((out (assoc-ref %outputs "out")))
                  (mkdir out)    ; create /gnu/store/…-goo
                  (call-with-output-file (string-append out "/test")
                    (lambda (p)
                      (display '(hello guix) p))))))
  (build-expression->derivation store "goo" builder))

 #<derivation /gnu/store/…-goo.drv => …>

Next: Устройство склада, Previous: Хранилище, Up: Программный интерфейс   [Contents][Index]