Add support for building minecraft modpacks

This commit is contained in:
Tristan Daniël Maat 2021-04-25 04:50:30 +01:00
parent b474f7e97c
commit a9e3610744
Signed by: tlater
GPG key ID: 49670FD774E43268
6 changed files with 121 additions and 11 deletions

View file

@ -21,7 +21,7 @@
}; };
}; };
outputs = { nixpkgs, nixos-hardware, flake-utils, tlaternet-webserver outputs = { self, nixpkgs, nixos-hardware, flake-utils, tlaternet-webserver
, tlaternet-templates, ... }@inputs: , tlaternet-templates, ... }@inputs:
let let
overlays = [ overlays = [
@ -30,14 +30,18 @@
tlaternet-webserver.legacyPackages.${prev.system}.packages; tlaternet-webserver.legacyPackages.${prev.system}.packages;
tlaternet-templates = tlaternet-templates =
tlaternet-templates.legacyPackages.${prev.system}.packages; tlaternet-templates.legacyPackages.${prev.system}.packages;
local = import ./pkgs { pkgs = prev; }; local = import ./pkgs {
pkgs = prev;
local-lib = self.lib.${prev.system};
};
}) })
]; ];
in { in {
nixosConfigurations = { nixosConfigurations = {
tlaternet = nixpkgs.lib.nixosSystem { tlaternet = let system = "x86_64-linux";
system = "x86_64-linux"; in nixpkgs.lib.nixosSystem {
inherit system;
modules = [ modules = [
({ modulesPath, ... }: { ({ modulesPath, ... }: {
@ -52,8 +56,9 @@
]; ];
}; };
vm = nixpkgs.lib.nixosSystem { vm = let system = "x86_64-linux";
system = "x86_64-linux"; in nixpkgs.lib.nixosSystem {
inherit system;
modules = [ modules = [
({ modulesPath, ... }: { ({ modulesPath, ... }: {
@ -88,6 +93,14 @@
''; '';
}; };
packages = import ./pkgs { inherit pkgs; }; packages = import ./pkgs {
inherit pkgs;
local-lib = self.lib.${system};
};
lib = import ./lib {
inherit pkgs inputs;
lib = nixpkgs.lib;
};
}); });
} }

8
lib/default.nix Normal file
View file

@ -0,0 +1,8 @@
{ inputs, lib, pkgs, ... }:
let
inherit (lib) makeExtensible foldr attrValues;
tlater-lib = makeExtensible (self:
let callLibs = file: import file { inherit self lib pkgs inputs; };
in { minecraft = callLibs ./minecraft.nix; });
in tlater-lib.extend (self: super: foldr (a: b: a // b) { } (attrValues super))

30
lib/minecraft.nix Normal file
View file

@ -0,0 +1,30 @@
{ lib, pkgs, ... }:
{
# Make a modpack given its mod inputs.
#
# Mods should be attrsets in this format:
# {
# project = "";
# id = "";
# filename = "";
# sha256 = "";
# }
#
# This may be nice to read from a json ;)
#
mkModpack = { name, version, mods }:
pkgs.stdenv.mkDerivation {
inherit name version;
srcs = map pkgs.local.fetchFromCurseForge mods;
sourceRoot = "src/";
preUnpack = "mkdir -p src/";
unpackCmd = "cp $curSrc src/";
installPhase = ''
mkdir -p $out/mods/
cp * $out/mods
'';
};
}

View file

@ -0,0 +1,23 @@
{ lib, fetchurl }:
with builtins;
{ project, id, filename, ... }@args:
let
# I think this is supposed to be some weak automation
# protection. This split "id" is simply part of the download URL.
#
# Note that if it's zero-prefixed we need to remove the zeroes. It's
# really an odd one...
a = head (match "0*([[:digit:]]+)" (substring 0 4 id));
b = head (match "0*([[:digit:]]+)" (substring 4 7 id));
url = "https://media.forgecdn.net/files/${a}/${b}/${filename}";
otherArgs = removeAttrs args [ "project" "id" "filename" ];
in fetchurl (otherArgs // {
inherit url;
# Rename files to avoid names incompatible with the nix store
name = "${project}.jar";
})

View file

@ -1,6 +1,12 @@
{ pkgs, ... }: { pkgs, local-lib, ... }:
{ let
inherit (pkgs.lib) callPackageWith;
callPackage = callPackageWith (pkgs // { inherit local-lib; });
in {
# Forge # Forge
forge-server = pkgs.callPackage ./minecraft/forge-server.nix { }; forge-server = callPackage ./minecraft/forge-server.nix { };
# Build support
fetchFromCurseForge = callPackage ./build-support/fetchFromCurseForge.nix { };
} }

View file

@ -1,4 +1,5 @@
{ lib, stdenv, fetchurl, jre_headless, runtimeShell }: { lib, stdenv, fetchurl, busybox, coreutils, jre_headless, runtimeShell
, mods ? null, config ? null, defaultconfigs ? null }:
let let
name = "forge-server"; name = "forge-server";
@ -45,6 +46,35 @@ in stdenv.mkDerivation rec {
#!${runtimeShell} #!${runtimeShell}
set -eu set -eu
# Delete any previous mods directory so that it can be updated
${busybox}/bin/rm -fr mods
${lib.optionalString (mods != null) ''
# Copy the specified mods into the directory. Note that, sadly,
# forge doesn't support symlinks here.
${busybox}/bin/mkdir -p mods
${busybox}/bin/cp -r '${mods}/mods/'*.jar mods
''}
# Delete any previous config directories so that they can be updated
${busybox}/bin/rm -fr config defaultconfigs
${lib.optionalString (config != null) ''
# Copy the specified configs into the directory. Forge (and
# mods) will try to write here, so we cannot symlink.
${busybox}/bin/mkdir -p config
${busybox}/bin/cp -r '${config}'/* config
${busybox}/bin/chmod -R u+w config
''}
${lib.optionalString (defaultconfigs != null) ''
# Copy the specified configs into the directory. Forge (and
# mods) will try to write here, so we cannot symlink.
${busybox}/bin/mkdir -p defaultconfigs
${busybox}/bin/cp -r '${defaultconfigs}'/* defaultconfigs
${busybox}/bin/chmod -R u+w defaultconfigs
''}
exec ${jre_headless}/bin/java \$@ -jar $out'/lib/forge/forge-${version}.jar' nogui exec ${jre_headless}/bin/java \$@ -jar $out'/lib/forge/forge-${version}.jar' nogui
EOF EOF