Skip to content

Commit

Permalink
Merge pull request #432 from nix-community/refactor/use-mkshell-rust
Browse files Browse the repository at this point in the history
  • Loading branch information
yusdacra authored Dec 21, 2022
2 parents 5fef684 + faa2b46 commit 39c64b4
Show file tree
Hide file tree
Showing 5 changed files with 88 additions and 156 deletions.
16 changes: 0 additions & 16 deletions flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -122,22 +122,6 @@
"lib/setupHooks/installCargoArtifactsHook.sh"
"LICENSE"
];
devshell = [
"modules/back-compat.nix"
"modules/commands.nix"
"modules/default.nix"
"modules/devshell.nix"
"modules/env.nix"
"modules/modules.nix"
"modules/modules-docs.nix"
"nix/ansi.nix"
"nix/mkNakedShell.nix"
"nix/source.nix"
"nix/strOrPackage.nix"
"nix/writeDefaultShellScript.nix"
"extra/language/c.nix"
"LICENSE"
];
};

# An interface to access files of external projects.
Expand Down
4 changes: 0 additions & 4 deletions src/modules/externals/implementation.nix
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,6 @@
in {
config = {
externals = {
devshell = {
makeShell = import "${externalSources.devshell}/modules" pkgs;
imports.c = "${externalSources.devshell}/extra/language/c.nix";
};
crane = let
importLibFile = name: import "${externalSources.crane}/lib/${name}.nix";

Expand Down
30 changes: 20 additions & 10 deletions src/subsystems/rust/builders/build-rust-package/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -71,27 +71,37 @@
args = buildArgs;
});

mkShellForPkg = pkg:
pkgs.callPackage ../devshell.nix {
inherit externals;
drv = pkg;
};

allPackages =
l.mapAttrs
(name: version: {"${version}" = buildPackage name version;})
args.packages;

allDevshells =
mkShellForDrvs = drvs:
pkgs.callPackage ../devshell.nix {
name = "devshell";
inherit drvs;
};

pkgShells =
l.mapAttrs
(name: version: mkShellForPkg allPackages.${name}.${version})
(
name: version: let
pkg = allPackages.${name}.${version};
in
mkShellForDrvs [pkg]
)
args.packages;

allPackagesList =
l.mapAttrsToList
(name: version: allPackages.${name}.${version})
args.packages;
in {
packages = allPackages;
devShells =
allDevshells
pkgShells
// {
default = allDevshells.${defaultPackageName};
default = mkShellForDrvs allPackagesList;
};
};
}
43 changes: 25 additions & 18 deletions src/subsystems/rust/builders/crane/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -131,35 +131,42 @@
in
build;

mkShellForPkg = pkg: let
pkgDeps = pkg.passthru.dependencies;
depsShell = pkgs.callPackage ../devshell.nix {
inherit externals;
drv = pkgDeps;
};
mainShell = pkgs.callPackage ../devshell.nix {
inherit externals;
drv = pkg;
};
shell = depsShell.combineWith mainShell;
in
shell;

allPackages =
l.mapAttrs
(name: version: {"${version}" = buildPackage name version;})
args.packages;

allDevshells =
mkShellForDrvs = drvs:
pkgs.callPackage ../devshell.nix {
name = "devshell";
inherit drvs;
};

pkgShells =
l.mapAttrs
(name: version: mkShellForPkg allPackages.${name}.${version})
(
name: version: let
pkg = allPackages.${name}.${version};
in
mkShellForDrvs [pkg.passthru.dependencies pkg]
)
args.packages;

allPackagesList = l.flatten (
l.mapAttrsToList
(
name: version: let
pkg = allPackages.${name}.${version};
in [pkg.passthru.dependencies pkg]
)
args.packages
);
in {
packages = allPackages;
devShells =
allDevshells
pkgShells
// {
default = allDevshells.${defaultPackageName};
default = mkShellForDrvs allPackagesList;
};
};
}
151 changes: 43 additions & 108 deletions src/subsystems/rust/builders/devshell.nix
Original file line number Diff line number Diff line change
@@ -1,129 +1,64 @@
{
# args
drv,
# d2n
externals,
drvs,
name,
# nixpkgs
lib,
stdenv,
libiconv,
mkShell,
...
}: let
l = lib // builtins;

# function to merge two devshells
mergeShellConfig = base: other: let
c = base.config;
oc = other.config;
i = base.imports or [];
oi = other.imports or [];
hasCConfig = config: (config ? language) && (config.language ? c);
in {
config =
c
// oc
// {
packages = l.unique ((c.packages or []) ++ (oc.packages or []));
commands = l.unique ((c.commands or []) ++ (oc.commands or []));
env = l.unique ((c.env or []) ++ (oc.env or []));
devshell =
(c.devshell or {})
// (oc.devshell or {})
// {
startup = (c.devshell.startup or {}) // (oc.devshell.startup or {});
};
}
// l.optionalAttrs (hasCConfig c || hasCConfig oc) {
language.c = let
cConf = c.language.c or {};
ocConf = oc.language.c or {};
in {
compiler = ocConf.compiler or cConf.compiler;
libraries =
l.unique ((cConf.libraries or []) ++ (ocConf.libraries or []));
includes =
l.unique ((cConf.includes or []) ++ (ocConf.includes or []));
};
};
imports = l.unique (i ++ oi);
};
# creates a shell from a config
mkShell = config: let
shell = (externals.devshell.makeShell {configuration = config;}).shell;
in
shell
// {
passthru.config = config;
combineWith = other:
mkShell (mergeShellConfig config other.passthru.config);
addConfig = otherConfig:
mkShell (mergeShellConfig config {config = otherConfig;});
};
# convenience utils for converting a nix attribute to a shell env
# TODO: we could probably replace this with something from nixpkgs?
toStr = v:
if l.isBool v
then l.boolToString v
else l.toString v;
toShellEnv = v:
if l.isList v
then "( ${l.concatStringsSep " " (l.map (v: ''"${toStr v}"'') v)} )"
else l.toString v;
# illegal env names to be removed and not be added to the devshell
illegalEnvNames = [
"name"
"pname"
"version"
"all"
"args"
"drvPath"
"drvAttrs"
"outPath"
"stdenv"
"cargoArtifacts"
"dream2nixVendorDir"
"cargoVendorDir"
];
isIllegalEnv = name: l.any (oname: name == oname) illegalEnvNames;
inputs = (drv.buildInputs or []) ++ (drv.nativeBuildInputs or []);
rustToolchain = drv.passthru.rustToolchain;
# the config we will use
conf = {
config =
{
packages = inputs;
commands = [
{
package = rustToolchain.cargoHostTarget or rustToolchain.cargo;
name = "cargo";
category = "rust";
help = "Rust build tool";
}
];
env =
# filter out attrsets, functions and illegal environment vars
l.filter
(env: (env != null) && (! isIllegalEnv env.name))
(
l.mapAttrsToList
(
n: v:
if ! (l.isAttrs v || l.isFunction v)
then {
name = n;
value = toShellEnv v;
}
else null
)
drv
);
}
# only add c stuff *if* the stdenv has a c compiler
# if the user wants to use stdenvNoCC this allows them to do it easily
// l.optionalAttrs (drv.stdenv ? cc) {
language.c = {
compiler = drv.stdenv.cc;
libraries = inputs ++ (lib.optional stdenv.isDarwin libiconv);
includes = inputs;
};
};
imports = [externals.devshell.imports.c];
};
isIllegalEnv = name: l.elem name illegalEnvNames;
getEnvs = drv:
# filter out attrsets, functions and illegal environment vars
l.filterAttrs
(name: env: (env != null) && (! isIllegalEnv name))
(
l.mapAttrs
(
n: v:
if ! (l.isAttrs v || l.isFunction v)
then v
else null
)
drv
);
combineEnvs = envs:
l.foldl'
(
all: env:
all
// env
// {
buildInputs = (all.buildInputs or []) ++ (env.buildInputs or []);
nativeBuildInputs = (all.nativeBuildInputs or []) ++ (env.nativeBuildInputs or []);
}
)
{}
envs;
_shellEnv = combineEnvs (l.map getEnvs drvs);
shellEnv =
_shellEnv
// {
inherit name;
passthru.env = _shellEnv;
};
in
mkShell conf
(mkShell.override {stdenv = (l.head drvs).stdenv;}) shellEnv

0 comments on commit 39c64b4

Please sign in to comment.