mirror of
https://github.com/nix-community/nixos-generators.git
synced 2024-11-30 01:39:36 +03:00
177 lines
3.8 KiB
Bash
Executable File
177 lines
3.8 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
set -euo pipefail
|
|
|
|
## Configuration
|
|
|
|
readonly libexec_dir="${0%/*}"
|
|
readonly format_dir=$libexec_dir/formats
|
|
|
|
configuration=${NIXOS_CONFIG:-$libexec_dir/configuration.nix}
|
|
flake_uri=
|
|
flake_attr=
|
|
format_path=
|
|
target_system=
|
|
cores=
|
|
run=
|
|
nix_args=(
|
|
"$libexec_dir/nixos-generate.nix"
|
|
)
|
|
has_outlink=false
|
|
nix_build_args=()
|
|
|
|
## Functions
|
|
|
|
showUsage() {
|
|
cat <<USAGE
|
|
Usage: $0 [options]
|
|
|
|
Options:
|
|
|
|
* --help: shows this help
|
|
* -c, --configuration PATH:
|
|
select the nixos configuration to build. Default: $configuration
|
|
* --flake URI:
|
|
selects the nixos configuration to build, using flake uri like "~/dotfiles#my-config"
|
|
* -f, --format NAME: select one of the pre-determined formats
|
|
* --format-path PATH: pass a custom format
|
|
* --list: list the available built-in formats
|
|
* --run: runs the configuration in a VM
|
|
only works for the "vm" and "vm-no-gui" formats
|
|
* --show-trace: show more detailed nix evaluation location information
|
|
* --system: specify the target system (eg: x86_64-linux)
|
|
* -o, --out-link: specify the outlink location for nix-build
|
|
* --cores : to control the maximum amount of parallelism. (see nix-build documentation)
|
|
* --option : Passed to to nix-build (see nix-build documentation).
|
|
* -I KEY=VALUE: Add a key to the Nix expression search path.
|
|
USAGE
|
|
}
|
|
|
|
listFormats() {
|
|
for format in "$format_dir"/*.nix; do
|
|
basename "$format" ".nix"
|
|
done
|
|
}
|
|
|
|
abort() {
|
|
echo "aborted: $*" >&2
|
|
exit 1
|
|
}
|
|
|
|
## Main ##
|
|
|
|
while [[ $# -gt 0 ]]; do
|
|
case "$1" in
|
|
-c | --configuration)
|
|
configuration=$2
|
|
shift
|
|
;;
|
|
--flake)
|
|
# Note: The reason I'm using awk over cut is because cutting with an
|
|
# out-of-bounds field will return the last in-bound field instead of empty
|
|
# string.
|
|
flake="$(echo "$2" | awk -F'#' '{ print $1; }')"
|
|
|
|
flake_uri="$(nix flake metadata --json -- "$flake" | jq -r .url)"
|
|
flake_attr="$(echo "$2" | awk -F'#' '{ print $2; }')"
|
|
shift
|
|
;;
|
|
--cores)
|
|
cores=$2
|
|
shift
|
|
;;
|
|
--option)
|
|
nix_build_args+=("$1" "$2" "$3")
|
|
shift 2
|
|
;;
|
|
-f | --format)
|
|
format_path=$format_dir/$2.nix
|
|
shift
|
|
;;
|
|
--format-path)
|
|
format_path=$2
|
|
shift
|
|
;;
|
|
--help)
|
|
showUsage
|
|
exit
|
|
;;
|
|
--list)
|
|
listFormats
|
|
exit
|
|
;;
|
|
--run)
|
|
run=1
|
|
# default to the VM format
|
|
if [[ -z $format_path ]]; then
|
|
format_path=$format_dir/vm.nix
|
|
fi
|
|
;;
|
|
--show-trace)
|
|
nix_args+=(--show-trace)
|
|
;;
|
|
--system)
|
|
target_system=$2
|
|
shift
|
|
;;
|
|
-I)
|
|
nix_args+=(-I "$2")
|
|
shift
|
|
;;
|
|
-o | --out-link)
|
|
nix_build_args+=(--out-link "$2")
|
|
has_outlink=true
|
|
shift
|
|
;;
|
|
*)
|
|
abort "unknown option $1"
|
|
;;
|
|
esac
|
|
shift
|
|
done
|
|
|
|
if ! $has_outlink; then
|
|
nix_build_args+=(--no-out-link)
|
|
fi
|
|
|
|
if [[ -z $format_path ]]; then
|
|
abort "missing format. use --help for more details"
|
|
fi
|
|
|
|
if [[ ! -f $format_path ]]; then
|
|
abort "format file not found: $format_path"
|
|
fi
|
|
|
|
nix_args+=(--argstr formatConfig "$(realpath "$format_path")")
|
|
|
|
if [[ -z "$flake_uri" ]]; then
|
|
nix_args+=(
|
|
-I "nixos-config=$configuration"
|
|
)
|
|
else
|
|
nix_args+=(
|
|
--argstr flakeUri "$flake_uri"
|
|
--argstr flakeAttr "${flake_attr:-"$(hostname)"}"
|
|
)
|
|
fi
|
|
|
|
if [[ -n $target_system ]]; then
|
|
nix_args+=(--argstr system "$target_system")
|
|
fi
|
|
|
|
if [[ -n $cores ]]; then
|
|
nix_args+=(--cores "$cores")
|
|
fi
|
|
|
|
formatAttr=$(nix-instantiate "${nix_args[@]}" --eval --json -A config.formatAttr | jq -r .)
|
|
filename=$(nix-instantiate "${nix_args[@]}" --eval --json -A config.filename | jq -r .)
|
|
|
|
out=$(nix-build "${nix_args[@]}" "${nix_build_args[@]}" -A "config.system.build.$formatAttr")
|
|
|
|
if [[ -z $run ]]; then
|
|
# show the first file, ignoring nix-support
|
|
find "$out" -wholename "$filename" -type f -print -quit
|
|
else
|
|
runner=$(find "$out"/bin -type l -print -quit)
|
|
exec "$runner"
|
|
fi
|