push sheeet
Some checks failed
Periodic Merges (6h) / master → staging-nixos (push) Failing after 12m50s
Periodic Merges (6h) / master → staging-next (push) Failing after 12m54s
Periodic Merges (24h) / merge-base(master,staging) → haskell-updates (push) Failing after 11m54s
Periodic Merges (6h) / staging-next → staging (push) Failing after 12m13s
Periodic Merges (24h) / staging-next-25.05 → staging-25.05 (push) Failing after 13m24s
Periodic Merges (24h) / release-25.05 → staging-next-25.05 (push) Failing after 14m28s

This commit is contained in:
Dark Steveneq
2025-10-09 14:15:47 +02:00
commit 646b892680
49168 changed files with 5897842 additions and 0 deletions

View File

@@ -0,0 +1 @@
azure

View File

@@ -0,0 +1,42 @@
# azure
## Demo
Here's a demo of this being used: https://asciinema.org/a/euXb9dIeUybE3VkstLWLbvhmp
## Usage
This is meant to be an example image that you can copy into your own
project and modify to your own needs. Notice that the example image
includes a built-in test user account, which by default uses your
`~/.ssh/id_ed25519.pub` as an `authorized_key`.
Build and upload the image
```shell
$ ./upload-image.sh ./examples/basic/image.nix
...
+ attr=azbasic
+ nix-build ./examples/basic/image.nix --out-link azure
/nix/store/qdpzknpskzw30vba92mb24xzll1dqsmd-azure-image
...
95.5 %, 0 Done, 0 Failed, 1 Pending, 0 Skipped, 1 Total, 2-sec Throughput (Mb/s): 932.9565
...
/subscriptions/aff271ee-e9be-4441-b9bb-42f5af4cbaeb/resourceGroups/nixos-images/providers/Microsoft.Compute/images/azure-image-todo-makethisbetter
```
Take the output, boot an Azure VM:
```
img="/subscriptions/.../..." # use output from last command
./boot-vm.sh "${img}"
...
=> booted
```
## Future Work
1. If the user specifies a hard-coded user, then the agent could be removed.
Probably has security benefits; definitely has closure-size benefits.
(It's likely the VM will need to be booted with a special flag. See:
https://github.com/Azure/azure-cli/issues/12775 for details.)

View File

@@ -0,0 +1,36 @@
#!/usr/bin/env bash
set -euo pipefail
set -x
image="${1}"
location="westus2"
group="nixos-test-vm"
vm_size="Standard_D2s_v3"; os_size=42;
# ensure group
az group create --location "westus2" --name "${group}"
group_id="$(az group show --name "${group}" -o tsv --query "[id]")"
# (optional) identity
if ! az identity show -n "${group}-identity" -g "${group}" &>/dev/stderr; then
az identity create --name "${group}-identity" --resource-group "${group}"
fi
# (optional) role assignment, to the resource group, bad but not really great alternatives
identity_id="$(az identity show --name "${group}-identity" --resource-group "${group}" -o tsv --query "[id]")"
principal_id="$(az identity show --name "${group}-identity" --resource-group "${group}" -o tsv --query "[principalId]")"
until az role assignment create --assignee "${principal_id}" --role "Owner" --scope "${group_id}"; do sleep 1; done
# boot vm
az vm create \
--name "${group}-vm" \
--resource-group "${group}" \
--assign-identity "${identity_id}" \
--size "${vm_size}" \
--os-disk-size-gb "${os_size}" \
--image "${image}" \
--admin-username "${USER}" \
--location "westus2" \
--storage-sku "Premium_LRS" \
--ssh-key-values "$(ssh-add -L)"

View File

@@ -0,0 +1,7 @@
export group="${AZURE_RESOURCE_GROUP:-"azure"}"
export location="${AZURE_LOCATION:-"westus2"}"
img_file=$(echo azure/*.vhd)
img_name="$(basename "${img_file}")"
img_name="${img_name%".vhd"}"
export img_name="${img_name//[._]/-}"

View File

@@ -0,0 +1,15 @@
let
pkgs = (import ../../../../../../default.nix { });
machine = import (pkgs.path + "/nixos/lib/eval-config.nix") {
system = "x86_64-linux";
modules = [
(
{ config, ... }:
{
imports = [ ./system.nix ];
}
)
];
};
in
machine.config.system.build.azureImage

View File

@@ -0,0 +1,38 @@
{ pkgs, modulesPath, ... }:
let
username = "azurenixosuser";
in
{
imports = [
"${modulesPath}/virtualisation/azure-common.nix"
"${modulesPath}/virtualisation/azure-image.nix"
];
## NOTE: This is just an example of how to hard-code a user.
## The normal Azure agent IS included and DOES provision a user based
## on the information passed at VM creation time.
users.users."${username}" = {
isNormalUser = true;
home = "/home/${username}";
description = "Azure NixOS Test User";
openssh.authorizedKeys.keys = [ (builtins.readFile ~/.ssh/id_ed25519.pub) ];
};
nix.settings.trusted-users = [ username ];
virtualisation.azureImage.diskSize = 2500;
boot.kernelPackages = pkgs.linuxPackages_latest;
# test user doesn't have a password
services.openssh.passwordAuthentication = false;
security.sudo.wheelNeedsPassword = false;
environment.systemPackages = with pkgs; [
git
file
htop
wget
curl
];
}

View File

@@ -0,0 +1,16 @@
{
pkgs ? import ../../../../default.nix { },
}:
pkgs.stdenv.mkDerivation {
name = "nixcfg-azure-devenv";
nativeBuildInputs = with pkgs; [
azure-cli
bash
cacert
azure-storage-azcopy
];
AZURE_CONFIG_DIR = "/tmp/azure-cli/.azure";
}

View File

@@ -0,0 +1,58 @@
#!/usr/bin/env bash
set -euo pipefail
set -x
image_nix="${1:-"./examples/basic/image.nix"}"
nix-build "${image_nix}" --out-link "azure"
group="nixos-images"
location="westus2"
img_name="nixos-image"
img_file="$(readlink -f ./azure/disk.vhd)"
if ! az group show -n "${group}" &>/dev/null; then
az group create --name "${group}" --location "${location}"
fi
# note: the disk access token song/dance is tedious
# but allows us to upload direct to a disk image
# thereby avoid storage accounts (and naming them) entirely!
if ! az disk show -g "${group}" -n "${img_name}" &>/dev/null; then
bytes="$(stat -c %s ${img_file})"
size="30"
az disk create \
--resource-group "${group}" \
--name "${img_name}" \
--for-upload true --upload-size-bytes "${bytes}"
timeout=$(( 60 * 60 )) # disk access token timeout
sasurl="$(\
az disk grant-access \
--access-level Write \
--resource-group "${group}" \
--name "${img_name}" \
--duration-in-seconds ${timeout} \
| jq -r '.accessSas'
)"
azcopy copy "${img_file}" "${sasurl}" \
--blob-type PageBlob
az disk revoke-access \
--resource-group "${group}" \
--name "${img_name}"
fi
if ! az image show -g "${group}" -n "${img_name}" &>/dev/null; then
diskid="$(az disk show -g "${group}" -n "${img_name}" -o json | jq -r .id)"
az image create \
--resource-group "${group}" \
--name "${img_name}" \
--source "${diskid}" \
--os-type "linux" >/dev/null
fi
imageid="$(az image show -g "${group}" -n "${img_name}" -o json | jq -r .id)"
echo "${imageid}"

View File

@@ -0,0 +1,8 @@
#! /bin/sh -eu
export NIX_PATH=nixpkgs=$(dirname $(readlink -f $0))/../../../..
export NIXOS_CONFIG=$(dirname $(readlink -f $0))/../../../modules/virtualisation/azure-image.nix
export TIMESTAMP=$(date +%Y%m%d%H%M)
nix-build '<nixpkgs/nixos>' \
-A config.system.build.azureImage --argstr system x86_64-linux -o azure -j 10

View File

@@ -0,0 +1,22 @@
#! /bin/sh -e
export STORAGE=${STORAGE:-nixos}
export THREADS=${THREADS:-8}
azure-vhd-utils-for-go upload --localvhdpath azure/disk.vhd --stgaccountname "$STORAGE" --stgaccountkey "$KEY" \
--containername images --blobname nixos-unstable-nixops-updated.vhd --parallelism "$THREADS" --overwrite

View File

@@ -0,0 +1,32 @@
# nix-build '<nixpkgs/nixos>' -A config.system.build.cloudstackImage --arg configuration "{ imports = [ ./nixos/maintainers/scripts/cloudstack/cloudstack-image.nix ]; }"
{
config,
lib,
pkgs,
...
}:
{
imports = [
../../../modules/virtualisation/cloudstack-config.nix
../../../modules/image/file-options.nix
];
system.nixos.tags = [ "cloudstack" ];
image.extension = "qcow2";
system.build.image = config.system.build.cloudstackImage;
system.build.cloudstackImage = import ../../../lib/make-disk-image.nix {
inherit lib config pkgs;
inherit (config.virtualisation) diskSize;
baseName = config.image.baseName;
format = "qcow2";
configFile = pkgs.writeText "configuration.nix" ''
{
imports = [ <nixpkgs/nixos/modules/virtualisation/cloudstack-config.nix> ];
}
'';
};
}

View File

@@ -0,0 +1,36 @@
# Amazon images
AMIs are regularly uploaded from Hydra. This automation lives in
https://github.com/NixOS/amis
## How to upload an AMI for testing
If you want to upload an AMI from changes in a local nixpkgs checkout.
```bash
nix-build nixos/release.nix -A amazonImage
export AWS_REGION=us-west-2
export AWS_PROFILE=my-profile
nix run nixpkgs#upload-ami -- --image-info ./result/nix-support/image-info.json
```
## How to build your own NixOS config into an AMI
Use `nixos-rebuild build-image` as follows:
```bash
NIXOS_CONFIG="$(pwd)/my-config.nix" nixos-rebuild build-image --image-variant amazon
export AWS_REGION=us-west-2
export AWS_PROFILE=my-profile
nix run github:NixOS/amis#upload-ami -- --image-info ./result/nix-support/image-info.json
```
## Roadmap
* @arianvp is planning to drop zfs support unless someone else picks it up
* @arianvp is planning to rewrite the image builder to use the repart-based image builder.
* @arianvp is planning to perhaps rewrite `upload-ami` to use coldnsap
* @arianvp is planning to move `upload-ami` tooling into nixpkgs once it has stabilized. And only keep the Github Action in separate repo

View File

@@ -0,0 +1,12 @@
{
imports = [ ./amazon-image.nix ];
ec2.zfs = {
enable = true;
datasets = {
"tank/system/root".mount = "/";
"tank/system/var".mount = "/var";
"tank/local/nix".mount = "/nix";
"tank/user/home".mount = "/home";
};
};
}

View File

@@ -0,0 +1,204 @@
{
config,
lib,
pkgs,
...
}:
let
inherit (lib)
mkOption
optionalString
types
versionAtLeast
;
inherit (lib.options) literalExpression;
cfg = config.amazonImage;
amiBootMode = if config.ec2.efi then "uefi" else "legacy-bios";
in
{
imports = [
../../../modules/virtualisation/amazon-image.nix
../../../modules/virtualisation/disk-size-option.nix
../../../modules/image/file-options.nix
(lib.mkRenamedOptionModuleWith {
sinceRelease = 2411;
from = [
"amazonImage"
"sizeMB"
];
to = [
"virtualisation"
"diskSize"
];
})
(lib.mkRenamedOptionModuleWith {
sinceRelease = 2505;
from = [
"amazonImage"
"name"
];
to = [
"image"
"baseName"
];
})
];
# Amazon recommends setting this to the highest possible value for a good EBS
# experience, which prior to 4.15 was 255.
# https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/nvme-ebs-volumes.html#timeout-nvme-ebs-volumes
config.boot.kernelParams =
let
timeout =
if versionAtLeast config.boot.kernelPackages.kernel.version "4.15" then "4294967295" else "255";
in
[ "nvme_core.io_timeout=${timeout}" ];
options.amazonImage = {
contents = mkOption {
example = literalExpression ''
[ { source = pkgs.memtest86 + "/memtest.bin";
target = "boot/memtest.bin";
}
]
'';
default = [ ];
description = ''
This option lists files to be copied to fixed locations in the
generated image. Glob patterns work.
'';
};
format = mkOption {
type = types.enum [
"raw"
"qcow2"
"vpc"
];
default = "vpc";
description = "The image format to output";
};
};
# Use a priority just below mkOptionDefault (1500) instead of lib.mkDefault
# to avoid breaking existing configs using that.
config.virtualisation.diskSize = lib.mkOverride 1490 (4 * 1024);
config.virtualisation.diskSizeAutoSupported = !config.ec2.zfs.enable;
config.system.nixos.tags = [ "amazon" ];
config.system.build.image = config.system.build.amazonImage;
config.image.extension = if cfg.format == "vpc" then "vhd" else cfg.format;
config.system.build.amazonImage =
let
configFile = pkgs.writeText "configuration.nix" ''
{ modulesPath, ... }: {
imports = [ "''${modulesPath}/virtualisation/amazon-image.nix" ];
${optionalString config.ec2.efi ''
ec2.efi = true;
''}
${optionalString config.ec2.zfs.enable ''
ec2.zfs.enable = true;
networking.hostId = "${config.networking.hostId}";
''}
}
'';
zfsBuilder = import ../../../lib/make-multi-disk-zfs-image.nix {
inherit
lib
config
configFile
pkgs
;
inherit (cfg) contents format;
name = config.image.baseName;
includeChannel = true;
bootSize = 1000; # 1G is the minimum EBS volume
rootSize = config.virtualisation.diskSize;
rootPoolProperties = {
ashift = 12;
autoexpand = "on";
};
datasets = config.ec2.zfs.datasets;
postVM = ''
extension=''${rootDiskImage##*.}
friendlyName=$out/${config.image.baseName}
rootDisk="$friendlyName.root.$extension"
bootDisk="$friendlyName.boot.$extension"
mv "$rootDiskImage" "$rootDisk"
mv "$bootDiskImage" "$bootDisk"
mkdir -p $out/nix-support
echo "file ${cfg.format} $bootDisk" >> $out/nix-support/hydra-build-products
echo "file ${cfg.format} $rootDisk" >> $out/nix-support/hydra-build-products
${pkgs.jq}/bin/jq -n \
--arg system_version ${lib.escapeShellArg config.system.nixos.version} \
--arg system ${lib.escapeShellArg pkgs.stdenv.hostPlatform.system} \
--arg root_logical_bytes "$(${pkgs.qemu_kvm}/bin/qemu-img info --output json "$rootDisk" | ${pkgs.jq}/bin/jq '."virtual-size"')" \
--arg boot_logical_bytes "$(${pkgs.qemu_kvm}/bin/qemu-img info --output json "$bootDisk" | ${pkgs.jq}/bin/jq '."virtual-size"')" \
--arg boot_mode "${amiBootMode}" \
--arg root "$rootDisk" \
--arg boot "$bootDisk" \
'{}
| .label = $system_version
| .boot_mode = $boot_mode
| .system = $system
| .disks.boot.logical_bytes = $boot_logical_bytes
| .disks.boot.file = $boot
| .disks.root.logical_bytes = $root_logical_bytes
| .disks.root.file = $root
' > $out/nix-support/image-info.json
'';
};
extBuilder = import ../../../lib/make-disk-image.nix {
inherit
lib
config
configFile
pkgs
;
inherit (cfg) contents format;
inherit (config.image) baseName;
name = config.image.baseName;
fsType = "ext4";
partitionTableType = if config.ec2.efi then "efi" else "legacy+gpt";
inherit (config.virtualisation) diskSize;
postVM = ''
mkdir -p $out/nix-support
echo "file ${cfg.format} $diskImage" >> $out/nix-support/hydra-build-products
${pkgs.jq}/bin/jq -n \
--arg system_version ${lib.escapeShellArg config.system.nixos.version} \
--arg system ${lib.escapeShellArg pkgs.stdenv.hostPlatform.system} \
--arg logical_bytes "$(${pkgs.qemu_kvm}/bin/qemu-img info --output json "$diskImage" | ${pkgs.jq}/bin/jq '."virtual-size"')" \
--arg boot_mode "${amiBootMode}" \
--arg file "$diskImage" \
'{}
| .label = $system_version
| .boot_mode = $boot_mode
| .system = $system
| .logical_bytes = $logical_bytes
| .file = $file
| .disks.root.logical_bytes = $logical_bytes
| .disks.root.file = $file
' > $out/nix-support/image-info.json
'';
};
in
if config.ec2.zfs.enable then zfsBuilder else extBuilder;
meta.maintainers = with lib.maintainers; [ arianvp ];
}

View File

@@ -0,0 +1,35 @@
#!/usr/bin/env nix-shell
#! nix-shell -i bash -p google-cloud-sdk
set -euo pipefail
BUCKET_NAME="${BUCKET_NAME:-nixos-cloud-images}"
TIMESTAMP="$(date +%Y%m%d%H%M)"
export TIMESTAMP
nix-build '<nixpkgs/nixos/lib/eval-config.nix>' \
-A config.system.build.googleComputeImage \
--arg modules "[ <nixpkgs/nixos/modules/virtualisation/google-compute-image.nix> ]" \
--argstr system x86_64-linux \
-o gce \
-j 10
img_path=$(echo gce/*.tar.gz)
img_name=${IMAGE_NAME:-$(basename "$img_path")}
img_id=$(echo "$img_name" | sed 's|.raw.tar.gz$||;s|\.|-|g;s|_|-|g')
img_family=$(echo "$img_id" | cut -d - -f1-4)
if ! gsutil ls "gs://${BUCKET_NAME}/$img_name"; then
gsutil cp "$img_path" "gs://${BUCKET_NAME}/$img_name"
gsutil acl ch -u AllUsers:R "gs://${BUCKET_NAME}/$img_name"
gcloud compute images create \
"$img_id" \
--source-uri "gs://${BUCKET_NAME}/$img_name" \
--family="$img_family"
gcloud compute images add-iam-policy-binding \
"$img_id" \
--member='allAuthenticatedUsers' \
--role='roles/compute.imageUser'
fi

View File

@@ -0,0 +1,34 @@
# Edit this configuration file to define what should be installed on
# your system. Help is available in the configuration.nix(5) man page
# and in the NixOS manual (accessible by running nixos-help).
{ modulesPath, ... }:
{
imports = [
# Include the default incus configuration.
"${modulesPath}/virtualisation/lxc-container.nix"
# Include the container-specific autogenerated configuration.
./incus.nix
];
networking = {
dhcpcd.enable = false;
useDHCP = false;
useHostResolvConf = false;
};
systemd.network = {
enable = true;
networks."50-eth0" = {
matchConfig.Name = "eth0";
networkConfig = {
DHCP = "ipv4";
IPv6AcceptRA = true;
};
linkConfig.RequiredForOnline = "routable";
};
};
system.stateVersion = "@stateVersion@"; # Did you read the comment?
}

View File

@@ -0,0 +1,46 @@
{ lib, pkgs, ... }:
{
imports = [ ../../../modules/virtualisation/lxc-container.nix ];
virtualisation.lxc.templates.nix = {
enable = true;
target = "/etc/nixos/incus.nix";
template = ./nix.tpl;
when = [
"create"
"copy"
];
};
# copy the config for nixos-rebuild
system.activationScripts.config =
let
config = pkgs.replaceVars ./incus-container-image-inner.nix {
stateVersion = lib.trivial.release;
};
in
''
if [ ! -e /etc/nixos/configuration.nix ]; then
install -m 0644 -D ${config} /etc/nixos/configuration.nix
fi
'';
networking = {
dhcpcd.enable = false;
useDHCP = false;
useHostResolvConf = false;
};
systemd.network = {
enable = true;
networks."50-eth0" = {
matchConfig.Name = "eth0";
networkConfig = {
DHCP = "ipv4";
IPv6AcceptRA = true;
};
linkConfig.RequiredForOnline = "routable";
};
};
}

View File

@@ -0,0 +1,34 @@
# Edit this configuration file to define what should be installed on
# your system. Help is available in the configuration.nix(5) man page
# and in the NixOS manual (accessible by running nixos-help).
{ modulesPath, ... }:
{
imports = [
# Include the default incus configuration.
"${modulesPath}/virtualisation/incus-virtual-machine.nix"
# Include the container-specific autogenerated configuration.
./incus.nix
];
networking = {
dhcpcd.enable = false;
useDHCP = false;
useHostResolvConf = false;
};
systemd.network = {
enable = true;
networks."50-enp5s0" = {
matchConfig.Name = "enp5s0";
networkConfig = {
DHCP = "ipv4";
IPv6AcceptRA = true;
};
linkConfig.RequiredForOnline = "routable";
};
};
system.stateVersion = "@stateVersion@"; # Did you read the comment?
}

View File

@@ -0,0 +1,47 @@
{ lib, pkgs, ... }:
{
imports = [ ../../../modules/virtualisation/incus-virtual-machine.nix ];
virtualisation.lxc.templates.nix = {
enable = true;
target = "/etc/nixos/incus.nix";
template = ./nix.tpl;
when = [
"create"
"copy"
];
};
# copy the config for nixos-rebuild
system.activationScripts.config =
let
config = pkgs.replaceVars ./incus-virtual-machine-image-inner.nix {
stateVersion = lib.trivial.release;
};
in
''
if [ ! -e /etc/nixos/configuration.nix ]; then
install -m 0644 -D ${config} /etc/nixos/configuration.nix
fi
'';
# Network
networking = {
dhcpcd.enable = false;
useDHCP = false;
useHostResolvConf = false;
};
systemd.network = {
enable = true;
networks."50-enp5s0" = {
matchConfig.Name = "enp5s0";
networkConfig = {
DHCP = "ipv4";
IPv6AcceptRA = true;
};
linkConfig.RequiredForOnline = "routable";
};
};
}

View File

@@ -0,0 +1,12 @@
{
lib,
config,
pkgs,
...
}:
# WARNING: THIS CONFIGURATION IS AUTOGENERATED AND WILL BE OVERWRITTEN AUTOMATICALLY
{
networking.hostName = "{{ container.name }}";
}

View File

@@ -0,0 +1,24 @@
#! /usr/bin/env bash
set -euo pipefail
export NIX_PATH=nixpkgs=$(dirname $(readlink -f $0))/../../../..
export NIXOS_CONFIG=$(dirname $(readlink -f $0))/../../../modules/virtualisation/oci-image.nix
if (( $# < 1 )); then
(
echo "Usage: create-image.sh <architecture>"
echo
echo "Where <architecture> is one of:"
echo " x86_64-linux"
echo " aarch64-linux"
) >&2
fi
system="$1"; shift
nix-build '<nixpkgs/nixos>' \
-A config.system.build.OCIImage \
--argstr system "$system" \
--option system-features kvm \
-o oci-image

View File

@@ -0,0 +1,100 @@
#! /usr/bin/env bash
set -euo pipefail
script_dir="$(dirname $(readlink -f $0))"
nixpkgs_root="$script_dir/../../../.."
export NIX_PATH="nixpkgs=$nixpkgs_root"
cat - <<EOF
This script will locally build a NixOS image and upload it as a Custom Image
using oci-cli. Make sure that an API key for the tenancy administrator has been
added to '~/.oci'.
For more info about configuring oci-cli, please visit
https://docs.cloud.oracle.com/iaas/Content/API/Concepts/apisigningkey.htm#Required_Keys_and_OCIDs
EOF
qcow="oci-image/nixos.qcow2"
if [ ! -f "$qcow" ]; then
echo "OCI image $qcow does not exist"
echo "Building image with create-image.sh for 'x86_64-linux'"
"$script_dir/create-image.sh" x86_64-linux
[ -f "$qcow" ] || { echo "Build failed: image not present after build"; exit 1; }
else
echo "Using prebuilt image $qcow"
fi
cli="$(
nix-build '<nixpkgs>' \
--no-out-link \
-A oci-cli
)"
PATH="$cli/bin:$PATH"
bucket="_TEMP_NIXOS_IMAGES_$RANDOM"
echo "Creating a temporary bucket"
root_ocid="$(
oci iam compartment list \
--all \
--compartment-id-in-subtree true \
--access-level ACCESSIBLE \
--include-root \
--raw-output \
--query "data[?contains(\"id\",'tenancy')].id | [0]"
)"
bucket_ocid=$(
oci os bucket create \
-c "$root_ocid" \
--name "$bucket" \
--raw-output \
--query "data.id"
)
# Clean up bucket on script termination
trap 'echo Removing temporary bucket; oci os bucket delete --force --name "$bucket"' INT TERM EXIT
echo "Uploading image to temporary bucket"
oci os object put -bn "$bucket" --file "$qcow"
echo "Importing image as a Custom Image"
bucket_ns="$(oci os ns get --query "data" --raw-output)"
image_id="$(
oci compute image import from-object \
-c "$root_ocid" \
--namespace "$bucket_ns" \
--bucket-name "$bucket" \
--name nixos.qcow2 \
--operating-system NixOS \
--source-image-type QCOW2 \
--launch-mode PARAVIRTUALIZED \
--display-name NixOS \
--raw-output \
--query "data.id"
)"
cat - <<EOF
Image created! Please mark all available shapes as compatible with this image by
visiting the following link and by selecting the 'Edit Details' button on:
https://cloud.oracle.com/compute/images/$image_id
EOF
# Workaround until https://github.com/oracle/oci-cli/issues/399 is addressed
echo "Sleeping for 15 minutes before cleaning up files in the temporary bucket"
sleep $((15 * 60))
echo "Deleting image from bucket"
par_id="$(
oci os preauth-request list \
--bucket-name "$bucket" \
--raw-output \
--query "data[0].id"
)"
if [[ -n $par_id ]]; then
oci os preauth-request delete \
--bucket-name "$bucket" \
--par-id "$par_id"
fi
oci os object delete -bn "$bucket" --object-name nixos.qcow2 --force

View File

@@ -0,0 +1,139 @@
# nix-build '<nixpkgs/nixos>' -A config.system.build.openstackImage --arg configuration "{ imports = [ ./nixos/maintainers/scripts/openstack/openstack-image.nix ]; }"
{
config,
lib,
pkgs,
...
}:
let
inherit (lib) mkOption types;
copyChannel = true;
cfg = config.openstackImage;
imageBootMode = if config.openstack.efi then "uefi" else "legacy-bios";
in
{
imports = [
../../../modules/virtualisation/openstack-config.nix
../../../modules/virtualisation/disk-size-option.nix
../../../modules/image/file-options.nix
(lib.mkRenamedOptionModuleWith {
sinceRelease = 2411;
from = [
"openstackImage"
"sizeMB"
];
to = [
"virtualisation"
"diskSize"
];
})
(lib.mkRenamedOptionModuleWith {
sinceRelease = 2505;
from = [
"openstackImage"
"name"
];
to = [
"image"
"baseName"
];
})
]
++ (lib.optional copyChannel ../../../modules/installer/cd-dvd/channel.nix);
options.openstackImage = {
ramMB = mkOption {
type = types.int;
default = (3 * 1024);
description = "RAM allocation for build VM";
};
format = mkOption {
type = types.enum [
"raw"
"qcow2"
];
default = "qcow2";
description = "The image format to output";
};
};
config = {
documentation.enable = copyChannel;
openstack = {
efi = true;
zfs = {
enable = true;
datasets = {
"tank/system/root".mount = "/";
"tank/system/var".mount = "/var";
"tank/local/nix".mount = "/nix";
"tank/user/home".mount = "/home";
};
};
};
# Use a priority just below mkOptionDefault (1500) instead of lib.mkDefault
# to avoid breaking existing configs using that.
virtualisation.diskSize = lib.mkOverride 1490 (8 * 1024);
virtualisation.diskSizeAutoSupported = false;
image.extension = cfg.format;
system.nixos.tags = [
"openstack"
"zfs"
];
system.build.image = config.system.build.openstackImage;
system.build.openstackImage = import ../../../lib/make-single-disk-zfs-image.nix {
inherit lib config;
inherit (cfg) contents format;
name = config.image.baseName;
pkgs = import ../../../.. { inherit (pkgs) system; }; # ensure we use the regular qemu-kvm package
configFile = pkgs.writeText "configuration.nix" ''
{ modulesPath, ... }: {
imports = [ "''${modulesPath}/virtualisation/openstack-config.nix" ];
openstack.zfs.enable = true;
}
'';
includeChannel = copyChannel;
bootSize = 1000;
memSize = cfg.ramMB;
rootSize = config.virtualisation.diskSize;
rootPoolProperties = {
ashift = 12;
autoexpand = "on";
};
datasets = config.openstack.zfs.datasets;
postVM = ''
extension=''${rootDiskImage##*.}
friendlyName=$out/${config.image.baseName}
rootDisk="$friendlyName.$extension"
mv "$rootDiskImage" "$rootDisk"
mkdir -p $out/nix-support
echo "file ${cfg.format} $rootDisk" >> $out/nix-support/hydra-build-products
${pkgs.jq}/bin/jq -n \
--arg system_label ${lib.escapeShellArg config.system.nixos.label} \
--arg system ${lib.escapeShellArg pkgs.stdenv.hostPlatform.system} \
--arg root_logical_bytes "$(${pkgs.qemu_kvm}/bin/qemu-img info --output json "$rootDisk" | ${pkgs.jq}/bin/jq '."virtual-size"')" \
--arg boot_mode "${imageBootMode}" \
--arg root "$rootDisk" \
'{}
| .label = $system_label
| .boot_mode = $boot_mode
| .system = $system
| .disks.root.logical_bytes = $root_logical_bytes
| .disks.root.file = $root
' > $out/nix-support/image-info.json
'';
};
};
}

View File

@@ -0,0 +1,42 @@
# nix-build '<nixpkgs/nixos>' -A config.system.build.openstackImage --arg configuration "{ imports = [ ./nixos/maintainers/scripts/openstack/openstack-image.nix ]; }"
{
config,
lib,
pkgs,
...
}:
let
copyChannel = true;
format = "qcow2";
in
{
imports = [
../../../modules/virtualisation/openstack-config.nix
../../../modules/image/file-options.nix
]
++ (lib.optional copyChannel ../../../modules/installer/cd-dvd/channel.nix);
documentation.enable = copyChannel;
image.extension = format;
system.nixos.tags = [ "openstack" ];
system.build.image = config.system.build.openstackImage;
system.build.openstackImage = import ../../../lib/make-disk-image.nix {
inherit
lib
config
copyChannel
format
;
inherit (config.image) baseName;
additionalSpace = "1024M";
pkgs = import ../../../.. { inherit (pkgs) system; }; # ensure we use the regular qemu-kvm package
configFile = pkgs.writeText "configuration.nix" ''
{
imports = [ <nixpkgs/nixos/modules/virtualisation/openstack-config.nix> ];
}
'';
};
}