Skip to content

Commit

Permalink
feat: add mkGodot function (#3)
Browse files Browse the repository at this point in the history
  • Loading branch information
florianvazelle authored Jan 17, 2025
1 parent 938f98a commit 65c57ae
Show file tree
Hide file tree
Showing 11 changed files with 1,340 additions and 100 deletions.
11 changes: 9 additions & 2 deletions .github/workflows/test.yaml
Original file line number Diff line number Diff line change
@@ -1,14 +1,21 @@
name: Test

on: [push, pull_request]
on:
workflow_dispatch:
# Ensure the build works on main
push:
branches: [main]
tags: ['*']
# Ensure the build works on each pull request
pull_request:

jobs:
test:
runs-on: ubuntu-24.04
steps:
- uses: actions/checkout@v4

- uses: cachix/install-nix-action@V27
- uses: cachix/install-nix-action@v30
with:
nix_path: nixpkgs=channel:nixos-unstable

Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/update.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ jobs:
steps:
- uses: actions/checkout@v4

- uses: cachix/install-nix-action@V27
- uses: cachix/install-nix-action@v30
with:
nix_path: nixpkgs=channel:nixos-unstable

Expand Down
91 changes: 75 additions & 16 deletions default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -5,27 +5,70 @@
inherit (pkgs) lib;
sources = builtins.fromJSON (lib.strings.fileContents ./sources.json);

# mkBinaryInstall makes a derivation that installs Godot from a binary.
mkBinaryInstall = {
url,
# mkExportTemplates makes a derivation that installs pre-compiled Godot Export Templates.
mkExportTemplates = {
version,
url,
sha512,
}:
pkgs.stdenv.mkDerivation {
inherit version;

pname = "godot";
pname = "godot-export-templates";
src = pkgs.fetchurl {inherit url sha512;};
dontConfigure = true;
dontBuild = true;
dontFixup = true;

strictDeps = true;
nativeBuildInputs = [pkgs.unzip];

unpackPhase = ''
unzip $src -d $out
interpreter=$(cat $NIX_CC/nix-support/dynamic-linker)
patchelf --set-interpreter $interpreter $out/templates/linux_*
'';

meta = {
homepage = "https://godotengine.org";
description = "Free and Open Source 2D and 3D game engine";
license = lib.licenses.mit;
platforms = lib.platforms.all;
maintainers = [lib.maintainers.florianvazelle];
};
};

# Godot Export Templates packages that are tagged releases
exportTemplatesPackages =
lib.attrsets.mapAttrs
(_k: v: mkExportTemplates {inherit (v.export_templates) version url sha512;})
(
lib.attrsets.filterAttrs
(_k: v: (builtins.hasAttr system v) && (v.${system}.url != null) && (v.${system}.sha512 != null))
sources
);

# mkEditor makes a derivation that installs pre-compiled Godot Editor.
mkEditor = {
version,
url,
sha512,
}: let
drv = pkgs.stdenv.mkDerivation {
inherit version;

pname = "godot-editor";
src = pkgs.fetchurl {inherit url sha512;};

strictDeps = true;
nativeBuildInputs = [pkgs.unzip];

unpackPhase = ''
unzip $src -d $out
'';

installPhase = ''
mkdir -p $out/bin
cp $out/Godot_v${version}* $out/bin/godot
rm $out/Godot_v${version}*
'';

meta = {
Expand All @@ -36,24 +79,40 @@
maintainers = [lib.maintainers.florianvazelle];
};
};
in
pkgs.buildFHSUserEnv {
name = "godot";
inherit version;
targetPkgs = _pkgs: [drv];
runScript = "godot";
};

# The packages that are tagged releases
taggedPackages =
# Godot Editor packages that are tagged releases
editorPackages =
lib.attrsets.mapAttrs
(k: v: mkBinaryInstall {inherit (v.${system}) version url sha512;})
(_k: v: let
editor = mkEditor {inherit (v.${system}) version url sha512;};
in
editor
// {
"mkGodot" = pkgs.callPackage ./lib/mkGodot.nix {
godot = editor;
exportTemplates = "${exportTemplatesPackages.${v.${system}.version}}/templates";
};
})
(
lib.attrsets.filterAttrs
(k: v: (builtins.hasAttr system v) && (v.${system}.url != null) && (v.${system}.sha512 != null))
(_k: v: (builtins.hasAttr system v) && (v.${system}.url != null) && (v.${system}.sha512 != null))
sources
);

# This determines the latest released version.
# This determines the latest Godot Editor released version.
latest = lib.lists.last (
builtins.sort
(x: y: (builtins.compareVersions x y) < 0)
(builtins.attrNames taggedPackages)
(builtins.attrNames editorPackages)
);
in
# We want the packages but also add a "default" that just points to the
# latest released version.
taggedPackages // {"default" = taggedPackages.${latest};}
# We want packages but also add a "default" that just points to the
# latest Godot Editor released version.
editorPackages // { "default" = editorPackages.${latest}; }
23 changes: 22 additions & 1 deletion flake.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

15 changes: 11 additions & 4 deletions flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,22 @@
inputs = {
nixpkgs.url = "github:NixOS/nixpkgs/nixos-24.11";
flake-utils.url = "github:numtide/flake-utils";
treefmt-nix.url = "github:numtide/treefmt-nix";
treefmt-nix.inputs.nixpkgs.follows = "nixpkgs";
};

outputs = {
self,
nixpkgs,
flake-utils,
treefmt-nix,
...
}: let
systems = ["i686-linux" "x86_64-linux" "aarch64-linux" "x86_64-darwin" "aarch64-darwin"];
outputs = flake-utils.lib.eachSystem systems (system: let
pkgs = nixpkgs.legacyPackages.${system};

# Eval the treefmt modules from ./treefmt.nix
treefmtEval = treefmt-nix.lib.evalModule pkgs ./treefmt.nix;
in rec {
# The packages exported by the Flake:
# - default - latest released version
Expand All @@ -29,15 +34,17 @@
};

# nix fmt
formatter = pkgs.alejandra;
formatter = treefmtEval.config.build.wrapper;
});
in
outputs
// {
# Overlay that can be imported so you can access the packages
# using godotpkgs.latest or whatever you'd like.
overlays.default = final: prev: {
# using godotPkgs.latest or whatever you'd like.
overlays.default = _final: prev: {
godotpkgs = outputs.packages.${prev.system};
mkNixosPatch = prev.callPackage ./lib/mkNixosPatch.nix {};
mkPlug = prev.callPackage ./lib/mkPlug.nix {};
};
};
}
75 changes: 75 additions & 0 deletions lib/mkGodot.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
# This modules create a Godot project derivation.
{
lib,
stdenv,
buildEnv,
makeWrapper,
godot,
exportTemplates, # absolute path to the nix store
}: {
pname,
version,
src,
preset,
addons ? [],
preBuildPhase ? "",
preInstallPhase ? "",

}: let
addonsEnv = buildEnv {
name = "addons";
paths = addons;
};

godotVersionFfolder = lib.replaceStrings ["-"] ["."] godot.version;
in
stdenv.mkDerivation rec {
inherit pname version src;

nativeBuildInputs = addons;
buildInputs = [godot makeWrapper];

postPatch = ''
patchShebangs scripts
'';

buildPhase = ''
runHook preBuild
${preBuildPhase}
export HOME=$(mktemp -d)
# Remove custom_template path if it doesn't point to the nix store
sed -i -e '/custom_template/!b' -e '/\/nix\/store/b' -e 's/"[^"]*"/""/g' -e 't' export_presets.cfg
mkdir -p $HOME/.local/share/godot/export_templates
ln -s ${exportTemplates} $HOME/.local/share/godot/export_templates/${godotVersionFfolder}
cp -r ${addonsEnv}/* ./addons
godot --headless --import
mkdir -p ./build
godot --headless --export-release "${preset}" ./build/${pname}.x86_64
runHook postBuild
'';

installPhase = ''
runHook preInstall
${preInstallPhase}
install -D -m 755 -t $out/share/${pname} ./build/${pname}.x86_64
install -D -m 644 -t $out/share/${pname} ./build/${pname}.pck
install -d -m 755 $out/bin
makeWrapper $out/share/${pname}/${pname}.x86_64 $out/bin/${pname} \
--add-flags "--main-pack" \
--add-flags "$out/share/${pname}/${pname}.pck"
patchelf --set-interpreter /lib64/ld-linux-x86-64.so.2 $out/share/${pname}/${pname}.x86_64
runHook postInstall
'';
}
54 changes: 54 additions & 0 deletions lib/mkNixosPatch.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
# This modules patch a given Godot project derivation, to make it runnable on Nixos.
{
stdenv,
copyDesktopItems,
installShellFiles,
autoPatchelfHook,
xorg,
vulkan-loader,
libGL,
libxkbcommon,
alsa-lib,
}: {
pname,
version,
src,
}:
stdenv.mkDerivation rec {
inherit pname version src;

nativeBuildInputs = [
autoPatchelfHook
installShellFiles
copyDesktopItems
];

runtimeDependencies = [
vulkan-loader
libGL
xorg.libX11
xorg.libXcursor
xorg.libXinerama
xorg.libXext
xorg.libXrandr
xorg.libXrender
xorg.libXi
xorg.libXfixes
libxkbcommon
alsa-lib
];

postPatch = ''
patchShebangs scripts
'';

installPhase = ''
runHook preInstall
mkdir $out
mv bin/* bin/${pname} || true # Rename fails if pname is the same
cp -r * $out
runHook postInstall
'';
}
Loading

0 comments on commit 65c57ae

Please sign in to comment.