Skip to content

Instantly share code, notes, and snippets.

@ckauhaus
Created August 10, 2017 16:45
Show Gist options
  • Save ckauhaus/808cbea9e41d99ae63208c02f245b0e6 to your computer and use it in GitHub Desktop.
Save ckauhaus/808cbea9e41d99ae63208c02f245b0e6 to your computer and use it in GitHub Desktop.
Proposal for a new Nix Rust build expression
{ pkgs ? import <nixpkgs> {}
, stdenv ? pkgs.stdenv
, rust ? pkgs.rust
, rustRegistry ? pkgs.rustPlatform.rustRegistry
}:
# Builds a Rust package from src with all dependendies found in Cargo.lock.
# Don't forget to update the cargoDepsSha256 checksum when updating the sources.
# Due to the nature of fixed-output derivations strange compile errors may
# happen otherwise.
{ name
, release ? true
, src
, cargoDepsSha256
, buildInputs ? []
, ... } @ args:
let
frozenFlag = if rustRegistry != null then "--frozen" else "--locked";
# Creates a "local-registry" directory which contains all dependendies needed
# to compile `src`. Fixed output derivation to keep sandboxes happy.
cargoLocalRegistry = src: sha256: rustRegistry: stdenv.mkDerivation {
SSL_CERT_FILE = "${pkgs.cacert}/etc/ssl/certs/ca-bundle.crt";
inherit src;
name = "${name}-cargo-deps";
buildInputs = [ rust.cargo ];
phases = [ "unpackPhase" "installPhase" "fixupPhase" ];
installPhase = ''
export CARGO_HOME=$PWD
cat <<__EOF__ > $CARGO_HOME/config
[source.crates-io]
replace-with = "nix-registry"
[source.nix-registry]
registry = "file://${rustRegistry}"
__EOF__
cargo fetch --locked
mkdir $out
cp $CARGO_HOME/registry/cache/*/*.crate $out
ln -s ${rustRegistry} $out/index
'';
fixupPhase = ''
# git repos contain different bits all the time
rm -rf $CARGO_HOME/registry/index/*/.git
'';
preferLocalBuild = true;
outputHashMode = "recursive";
outputHashAlgo = "sha256";
outputHash = sha256;
};
in stdenv.mkDerivation ({
RUST_BACKTRACE = 1;
} // args // {
inherit src;
buildInputs = buildInputs ++ [
rust.rustc
rust.cargo
];
postUnpack = if rustRegistry == null then ''
export CARGO_HOME=$sourceRoot/.cargo
'' else ''
export CARGO_HOME=$PWD/.cargo
mkdir -p $CARGO_HOME
cat <<__EOF__ > $CARGO_HOME/config
[source.crates-io]
replace-with = "nix-local-registry"
[source.nix-local-registry]
local-registry = "${cargoLocalRegistry src cargoDepsSha256 rustRegistry}"
[build]
jobs = $NIX_BUILD_CORES
__EOF__
'';
buildPhase = ''
runHook preBuild
cargo build ${if release then "--release" else ""} ${frozenFlag}
runHook postBuild
'';
checkPhase = ''
runHook preCheck
cargo test ${frozenFlag}
runHook PostCheck
'';
installPhase = ''
runHook preInstall
(
cd target/${if release then "release" else "debug"}
find . -maxdepth 1 -type f -perm -0100 \
-print0 | xargs -0r install -D -t $out/bin
find . -maxdepth 1 -type f \
-name '*.rlib' -o -name '*.so' -o -name '.a' -o -name '*.dylib' \
-print0 | xargs -0r install -D -t $out/lib
)
runHook postInstall
'';
distPhase = ''
runHook preDist
mkdir -p $out/tarballs
tar cf $out/tarballs/${name}.tar `find . -maxdepth 1 -not -name . -not -name target -not -name .hg\* -not -name .cargo`
runHook postDist
'';
})
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment