diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..3550a30 --- /dev/null +++ b/.envrc @@ -0,0 +1 @@ +use flake diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..6a48c42 --- /dev/null +++ b/flake.nix @@ -0,0 +1,115 @@ +{ + description = "Imphnen Frontend Service - Nx Monorepo"; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + flake-utils.url = "github:numtide/flake-utils"; + }; + + outputs = { self, nixpkgs, flake-utils }: + flake-utils.lib.eachDefaultSystem (system: + let + pkgs = import nixpkgs { inherit system; }; + + # NPM dependencies hash (update with: nix run nixpkgs#prefetch-npm-deps -- package-lock.json) + npmDepsHash = "sha256-dKBi3bM/cpzK70s62tJTI1j/lhVlojAX2IkyNK0oICI="; + + # Import helpers + mkViteApp = import ./nix/mkViteApp.nix { + inherit pkgs npmDepsHash; + src = ./.; + }; + + landingApp = import ./nix/landing.nix { + inherit pkgs npmDepsHash; + src = ./.; + }; + + in { + packages = { + # Static Vite apps + backoffice = mkViteApp { name = "backoffice"; buildScript = "backoffice:build"; }; + gacha = mkViteApp { name = "gacha"; buildScript = "gacha:build"; }; + dimentorin = mkViteApp { name = "dimentorin"; buildScript = "dimentorin:build"; }; + hackathon = mkViteApp { name = "hackathon"; buildScript = "hackathon:build"; }; + + # Next.js app + landing = landingApp; + + # Default package + default = self.packages.${system}.landing; + }; + + # Development shell + devShells.default = pkgs.mkShell { + buildInputs = with pkgs; [ + nodejs_22 + nodePackages.npm + bun + + # Useful dev tools + git + jq + ]; + + shellHook = '' + echo "🚀 Imphnen Frontend Development Shell" + echo "Node.js: $(node --version)" + echo "npm: $(npm --version)" + echo "" + echo "Available commands:" + echo " npm install - Install dependencies" + echo " nx dev - Start development server" + echo " nx build - Build an app" + echo "" + echo "Apps: landing, backoffice, gacha, dimentorin, hackathon" + echo "" + echo "Build packages with:" + echo " nix build .#landing" + echo " nix build .#backoffice" + echo " nix build .#gacha" + echo " nix build .#dimentorin" + echo " nix build .#hackathon" + ''; + }; + } + ) // { + # NixOS modules for deployment + nixosModules = { + landing = import ./nix/modules/landing.nix { inherit self; }; + + backoffice = import ./nix/modules/static-app.nix { inherit self; } { appName = "backoffice"; }; + gacha = import ./nix/modules/static-app.nix { inherit self; } { appName = "gacha"; }; + dimentorin = import ./nix/modules/static-app.nix { inherit self; } { appName = "dimentorin"; }; + hackathon = import ./nix/modules/static-app.nix { inherit self; } { appName = "hackathon"; }; + + # All-in-one module that enables all apps + all = { config, lib, pkgs, ... }: { + imports = [ + self.nixosModules.landing + self.nixosModules.backoffice + self.nixosModules.gacha + self.nixosModules.dimentorin + self.nixosModules.hackathon + ]; + }; + }; + + # Overlay for easy integration + overlays.default = final: prev: { + imphnen = { + landing = self.packages.${final.system}.landing; + backoffice = self.packages.${final.system}.backoffice; + gacha = self.packages.${final.system}.gacha; + dimentorin = self.packages.${final.system}.dimentorin; + hackathon = self.packages.${final.system}.hackathon; + # Function to build hackathon with custom environment variables (e.g., Supabase) + mkHackathonWithEnv = envVars: import ./nix/mkViteApp.nix { + pkgs = final; + src = self; + npmDepsHash = "sha256-dKBi3bM/cpzK70s62tJTI1j/lhVlojAX2IkyNK0oICI="; + } { name = "hackathon"; buildScript = "hackathon:build"; inherit envVars; }; + }; + }; + }; +} diff --git a/nix/example-infrastructure.nix b/nix/example-infrastructure.nix new file mode 100644 index 0000000..592b744 --- /dev/null +++ b/nix/example-infrastructure.nix @@ -0,0 +1,89 @@ +# Example: How to use in imphnen-infrastructure +# +# In your imphnen-infrastructure flake.nix: +# +# { +# inputs = { +# nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; +# imphnen-frontend = { +# url = "github:your-org/imphnen-frontend-service"; +# # Or use local path during development: +# # url = "path:/path/to/imphnen-frontend-service"; +# }; +# }; +# +# outputs = { self, nixpkgs, imphnen-frontend, ... }: { +# nixosConfigurations.your-server = nixpkgs.lib.nixosSystem { +# system = "x86_64-linux"; +# modules = [ +# # Import all modules at once +# imphnen-frontend.nixosModules.all +# +# # Or import individually: +# # imphnen-frontend.nixosModules.landing +# # imphnen-frontend.nixosModules.backoffice +# +# ./your-server-config.nix +# ]; +# }; +# }; +# } +# +# Then in your-server-config.nix: + +{ config, pkgs, ... }: + +{ + # Enable Landing (Next.js) - runs as systemd service + services.imphnen-landing = { + enable = true; + port = 3000; + hostname = "0.0.0.0"; + openFirewall = true; + # environmentFile = /run/secrets/landing-env; # For secrets + }; + + # Enable Backoffice (Static) - served by nginx + services.imphnen-backoffice = { + enable = true; + domain = "backoffice.imphnen.dev"; + enableSSL = true; + }; + + # Enable Gacha (Static) + services.imphnen-gacha = { + enable = true; + domain = "gacha.imphnen.dev"; + enableSSL = true; + }; + + # Enable Dimentorin (Static) + services.imphnen-dimentorin = { + enable = true; + domain = "dimentorin.imphnen.dev"; + enableSSL = true; + }; + + # Enable Hackathon (Static) + services.imphnen-hackathon = { + enable = true; + domain = "hackathon.imphnen.dev"; + enableSSL = true; + }; + + # Nginx reverse proxy for landing (if needed) + services.nginx.virtualHosts."imphnen.dev" = { + forceSSL = true; + enableACME = true; + locations."/" = { + proxyPass = "http://127.0.0.1:3000"; + proxyWebsockets = true; + }; + }; + + # Enable ACME for SSL + security.acme = { + acceptTerms = true; + defaults.email = "admin@imphnen.dev"; + }; +} diff --git a/nix/landing.nix b/nix/landing.nix new file mode 100644 index 0000000..3e347a9 --- /dev/null +++ b/nix/landing.nix @@ -0,0 +1,50 @@ +# Next.js Landing App Package +{ pkgs, src, npmDepsHash }: + +pkgs.buildNpmPackage { + pname = "imphnen-landing"; + version = "0.0.1"; + inherit src npmDepsHash; + + nativeBuildInputs = with pkgs; [ + nodejs_22 + nodePackages.npm + python3 # Required for node-gyp (sharp, etc.) + ]; + + buildPhase = '' + runHook preBuild + export NX_DAEMON=false + export HOME=$TMPDIR + npm run landing:build + runHook postBuild + ''; + + installPhase = '' + runHook preInstall + mkdir -p $out/bin $out/share/landing + + # Copy standalone server + cp -r dist/apps/landing/.next/standalone/* $out/share/landing/ + + # Copy public assets + mkdir -p $out/share/landing/apps/landing/public + cp -r dist/apps/landing/public/* $out/share/landing/apps/landing/public/ || true + + # Copy static files + mkdir -p $out/share/landing/dist/apps/landing/.next/static + cp -r dist/apps/landing/.next/static/* $out/share/landing/dist/apps/landing/.next/static/ + + # Create wrapper script + cat > $out/bin/imphnen-landing <