Clone of https://github.com/NixOS/nixpkgs.git (to stress-test knotserver)
at python-updates 125 lines 3.6 kB view raw
1{ 2 lib, 3 # Build helpers 4 stdenv, 5 runCommand, 6 vmTools, 7 writeClosure, 8 writeDirectReferencesToFile, 9 writeScript, 10 writeStringReferencesToFile, 11 # Native build inputs 12 buildPackages, 13 e2fsprogs, 14 util-linux, 15 # Build inputs 16 bashInteractive, 17 runtimeShell, 18 singularity, 19}: 20 21let 22 defaultSingularity = singularity; 23in 24lib.makeExtensible (final: { 25 buildImage = 26 { 27 name, 28 contents ? [ ], 29 diskSize ? 1024, 30 memSize ? 1024, 31 runAsRoot ? null, 32 runScript ? "#!${stdenv.shell}\nexec /bin/sh", 33 singularity ? defaultSingularity, 34 }: 35 let 36 projectName = singularity.projectName or "singularity"; 37 runAsRootFile = buildPackages.writers.writeBash "run-as-root.sh" '' 38 set -e 39 ${runAsRoot} 40 ''; 41 runScriptFile = writeScript "run-script.sh" '' 42 #!/bin/sh 43 set -e 44 ${runScript} 45 ''; 46 runScriptReferences = 47 if builtins ? getContext then 48 lib.splitString "\n" (writeStringReferencesToFile runScriptFile.text).text 49 else 50 [ (writeDirectReferencesToFile runScriptFile) ]; 51 result = vmTools.runInLinuxVM ( 52 runCommand "${projectName}-image-${name}.sif" 53 { 54 __structuredAttrs = true; 55 nativeBuildInputs = [ 56 singularity 57 e2fsprogs 58 util-linux 59 ]; 60 strictDeps = true; 61 inherit contents; 62 layerClosure = writeClosure ([ bashInteractive ] ++ runScriptReferences ++ contents); 63 preVM = vmTools.createEmptyImage { 64 size = diskSize; 65 fullName = "${projectName}-run-disk"; 66 # Leaving "$out" for the Singularity/Container image 67 destination = "disk-image"; 68 }; 69 inherit memSize; 70 } 71 '' 72 mkdir workspace 73 mkfs -t ext3 -b 4096 /dev/${vmTools.hd} 74 mount /dev/${vmTools.hd} workspace 75 mkdir -p workspace/img 76 cd workspace/img 77 mkdir proc sys dev 78 79 # Run root script 80 ${lib.optionalString (runAsRoot != null) '' 81 mkdir -p ./${builtins.storeDir} 82 mount --rbind "${builtins.storeDir}" ./${builtins.storeDir} 83 unshare -imnpuf --mount-proc chroot ./ ${runAsRootFile} 84 umount -R ./${builtins.storeDir} 85 ''} 86 87 # Build /bin and copy across closure 88 mkdir -p bin ./${builtins.storeDir} 89 # Loop over the line-separated paths in $layerClosure 90 while IFS= read -r f; do 91 cp -ar "$f" "./$f" 92 done < "$layerClosure" 93 94 for c in "''${contents[@]}"; do 95 for f in "$c"/bin/* ; do 96 if [ ! -e "bin/$(basename "$f")" ] ; then 97 ln -s "$f" bin/ 98 fi 99 done 100 done 101 102 # Link /bin/sh 103 if [ ! -e bin/sh ]; then 104 ln -s ${lib.getExe bashInteractive} bin/sh 105 fi 106 mkdir -p .singularity.d 107 108 # Create runscript 109 cp "${runScriptFile}" .singularity.d/runscript 110 111 # Fill out .singularity.d 112 mkdir -p .singularity.d/env 113 touch .singularity.d/env/94-appsbase.sh 114 115 cd .. 116 mkdir -p /var/lib/${projectName}/mnt/session 117 echo "root:x:0:0:System administrator:/root:/bin/sh" > /etc/passwd 118 echo > /etc/resolv.conf 119 TMPDIR="$(pwd -P)" ${projectName} build "$out" ./img 120 '' 121 ); 122 123 in 124 result; 125})