{ description = "A naersk based rust flake"; inputs = { utils.url = "github:numtide/flake-utils"; naersk = { url = "github:nix-community/naersk"; inputs.nixpkgs.follows = "nixpkgs"; }; index = { flake = false; url = "github:rust-lang/crates.io-index"; }; }; outputs = { self, nixpkgs, utils, naersk, index, }: let crate = self.lib.crate "bat"; pname = crate.latest.name; filterAttrs = pred: set: builtins.removeAttrs set (builtins.filter (name: !pred name set.${name}) (builtins.attrNames set)); forPkgs = pkgs: rec { # # `nix build` # packages.${pname} = crate.latest.package { inherit pkgs; }; # # `nix run` # apps.${pname} = utils.lib.mkApp { # drv = packages.${pname}; # }; # defaultApp = apps.${pname}; }; forSystem = system: forPkgs nixpkgs.legacyPackages."${system}"; in (utils.lib.eachDefaultSystem forSystem) // rec { packages.crates_io = let traverse = path: levels: let entries = (builtins.readDir path); filterTy = t: builtins.attrNames (filterAttrs (_: ty: ty == t) entries); dirs = filterTy "directory"; crateDirs = builtins.filter (dir: (builtins.substring 0 1 dir) != ".") dirs; files = filterTy "regular"; in if levels == 0 then map (name: "${path}/${name}") files else builtins.concatLists (map (dir: traverse "${path}/${dir}" (levels - 1)) crateDirs); cratePaths = traverse "${index}" 2; crateVersions = path: let meta = builtins.readFile path; metaLines = builtins.split "\n" meta; versionsLines = builtins.filter (l: builtins.isString l && builtins.stringLength l > 10) metaLines; versionsMeta = map builtins.fromJSON versionsLines; versions = map ( meta: let inherit (meta) vers; in { name = vers; value = meta // { build = lib.buildCrate meta; }; } ) versionsMeta; in ( (builtins.listToAttrs versions) // { "latest" = (builtins.elemAt versions (builtins.length versions - 1)).value; } ); crateNames = map baseNameOf cratePaths; in builtins.listToAttrs ( map (path: { name = baseNameOf (builtins.unsafeDiscardStringContext path); value = crateVersions path; }) cratePaths ); lib = rec { config = builtins.fromJSON (builtins.readFile "${index}/config.json"); buildCrate = meta: extra@{ pkgs, ... }: let naersk-lib = naersk.lib."${pkgs.system}"; in naersk-lib.buildPackage ( (removeAttrs extra [ "pkgs" ]) // { root = pkgs.runCommandLocal "unpack-${meta.name}" { } '' mkdir -p $out tar xzvf ${meta.tarball} -C $out --strip-components=1 ''; } ); crate = name: let dbg = val: builtins.trace val val; strlen = builtins.stringLength; substr = builtins.substring; path = if strlen name < 4 then "${toString (strlen name)}/${substr 0 1 name}/${name}" else "${substr 0 2 name}/${substr 2 2 name}/${name}"; versions = builtins.foldl' ( p: i: let meta = i // rec { url = "${config.dl}/${name}/${i.vers}/download"; package = buildCrate meta; tarball = builtins.fetchurl { inherit url; sha256 = i.cksum; }; }; in p // { latest = meta; "${i.vers}" = meta; } ) { } ( map builtins.fromJSON ( builtins.filter (s: builtins.isString s && strlen s > 0) ( builtins.split "\n" (builtins.readFile "${index}/${path}") ) ) ); in versions; }; }; }