{ description = "Methanium Template"; inputs = { nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; rust-overlay.url = "github:oxalica/rust-overlay"; }; outputs = inputs@{ self, nixpkgs, rust-overlay, ... }: let systems = [ "aarch64-darwin" "aarch64-linux" "x86_64-darwin" "x86_64-linux" ]; forAllSystems = nixpkgs.lib.genAttrs systems; pkgsFor = system: import nixpkgs { inherit system; overlays = [ rust-overlay.overlays.default ]; }; in { packages = forAllSystems ( system: let pkgs = pkgsFor system; root = toString ./.; rustToolchain = pkgs.rust-bin.stable.latest.default.override { targets = [ "wasm32-unknown-unknown" ]; }; source = pkgs.lib.cleanSourceWith { src = ./.; filter = path: _type: let relative = pkgs.lib.removePrefix "${root}/" (toString path); in !(pkgs.lib.hasPrefix "node_modules/" relative) && !(pkgs.lib.hasPrefix "apps/web/node_modules/" relative) && !(pkgs.lib.hasPrefix "apps/web/dist/" relative) && relative != "node_modules" && relative != "apps/web/node_modules" && relative != "apps/web/dist" && relative != "result"; }; nativeBuildInputs = [ pkgs.cacert pkgs.git pkgs.nodejs pkgs.pnpm pkgs.wasm-pack rustToolchain ]; webDeps = pkgs.stdenvNoCC.mkDerivation { pname = "methanium-template-web-deps"; version = "0.1.0"; src = source; nativeBuildInputs = [ pkgs.cacert pkgs.git pkgs.nodejs pkgs.pnpm pkgs.wasm-pack rustToolchain ]; outputHashAlgo = "sha256"; outputHashMode = "recursive"; outputHash = "sha256-ihavd0hJDptdyEtjWjVgghwAl/rn6aUdQ9CT3B4if3E="; dontFixup = true; __structuredAttrs = true; unsafeDiscardReferences.out = true; buildPhase = '' runHook preBuild export HOME="$TMPDIR/home" export CARGO_HOME="$TMPDIR/cargo" mkdir -p "$HOME" pnpm install --frozen-lockfile patchShebangs node_modules pnpm build runHook postBuild ''; installPhase = '' runHook preInstall mkdir -p "$out/apps/web" cp -a node_modules "$out/node_modules" cp -a apps/web/node_modules "$out/apps/web/node_modules" cp -a "$CARGO_HOME" "$out/cargo" cp -a "$HOME/.cache/.wasm-pack" "$out/wasm-pack" runHook postInstall ''; }; web = pkgs.stdenvNoCC.mkDerivation { pname = "methanium-template-web"; version = "0.1.0"; src = source; inherit nativeBuildInputs; buildPhase = '' runHook preBuild cp -a ${webDeps}/node_modules . cp -a ${webDeps}/apps/web/node_modules apps/web/node_modules cp -a ${webDeps}/cargo "$TMPDIR/cargo" chmod -R u+w node_modules apps/web/node_modules "$TMPDIR/cargo" export HOME="$TMPDIR/home" export CARGO_HOME="$TMPDIR/cargo" export CARGO_NET_OFFLINE=true mkdir -p "$HOME/.cache" cp -a ${webDeps}/wasm-pack "$HOME/.cache/.wasm-pack" chmod -R u+w "$HOME/.cache/.wasm-pack" pnpm build runHook postBuild ''; installPhase = '' runHook preInstall cp -r apps/web/dist "$out" runHook postInstall ''; }; in { default = web; web = web; } ); devShells = forAllSystems ( system: let pkgs = pkgsFor system; rustToolchain = pkgs.rust-bin.stable.latest.default.override { extensions = [ "rust-src" ]; targets = [ "wasm32-unknown-unknown" ]; }; in { default = pkgs.mkShell { packages = [ pkgs.nodejs pkgs.pnpm pkgs.wasm-pack rustToolchain ]; }; } ); checks = forAllSystems (system: { inherit (self.packages.${system}) web; }); nixosModules.default = { config, lib, pkgs, ... }: let cfg = config.services.methanium-template; in { options.services.methanium-template = { enable = lib.mkEnableOption "the Methanium frontend"; package = lib.mkOption { type = lib.types.package; default = self.packages.${pkgs.stdenv.hostPlatform.system}.default; defaultText = lib.literalExpression "self.packages.${pkgs.stdenv.hostPlatform.system}.default"; description = "Static frontend package to serve."; }; hostName = lib.mkOption { type = lib.types.str; default = "localhost"; description = "nginx virtual host name."; }; openFirewall = lib.mkOption { type = lib.types.bool; default = false; description = "Whether to open TCP port 80 in the firewall."; }; }; config = lib.mkIf cfg.enable { services.nginx = { enable = true; virtualHosts.${cfg.hostName} = { root = cfg.package; locations."/".tryFiles = "$uri $uri/ /index.html"; }; }; networking.firewall.allowedTCPPorts = lib.mkIf cfg.openFirewall [ 80 ]; }; }; }; }