diff --git a/flake.lock b/flake.lock index 3b54e324b95..79eaa275763 100644 --- a/flake.lock +++ b/flake.lock @@ -5,83 +5,136 @@ "nixpkgs-lib": "nixpkgs-lib" }, "locked": { - "lastModified": 1748821116, - "narHash": "sha256-F82+gS044J1APL0n4hH50GYdPRv/5JWm34oCJYmVKdE=", + "lastModified": 1743550720, + "narHash": "sha256-hIshGgKZCgWh6AYJpJmRgFdR3WUbkY04o82X05xqQiY=", "owner": "hercules-ci", "repo": "flake-parts", - "rev": "49f0870db23e8c1ca0b5259734a02cd9e1e371a1", + "rev": "c621e8422220273271f52058f618c94e405bb0f5", "type": "github" }, "original": { + "id": "flake-parts", + "type": "indirect" + } + }, + "flake-parts_2": { + "inputs": { + "nixpkgs-lib": "nixpkgs-lib_2" + }, + "locked": { + "lastModified": 1743550720, + "narHash": "sha256-hIshGgKZCgWh6AYJpJmRgFdR3WUbkY04o82X05xqQiY=", "owner": "hercules-ci", "repo": "flake-parts", + "rev": "c621e8422220273271f52058f618c94e405bb0f5", "type": "github" + }, + "original": { + "id": "flake-parts", + "type": "indirect" } }, - "flake-utils": { + "flake-parts_3": { + "inputs": { + "nixpkgs-lib": "nixpkgs-lib_3" + }, "locked": { - "lastModified": 1659877975, - "narHash": "sha256-zllb8aq3YO3h8B/U0/J1WBgAL8EX5yWf5pMj3G0NAmc=", - "owner": "numtide", - "repo": "flake-utils", - "rev": "c0e246b9b83f637f4681389ecabcb2681b4f3af0", + "lastModified": 1743550720, + "narHash": "sha256-hIshGgKZCgWh6AYJpJmRgFdR3WUbkY04o82X05xqQiY=", + "owner": "hercules-ci", + "repo": "flake-parts", + "rev": "c621e8422220273271f52058f618c94e405bb0f5", "type": "github" }, "original": { - "owner": "numtide", - "repo": "flake-utils", - "type": "github" + "id": "flake-parts", + "type": "indirect" } }, - "geospatial": { - "inputs": { - "flake-parts": "flake-parts", - "nixgl": "nixgl", - "nixpkgs": "nixpkgs" + "nixpkgs": { + "locked": { + "lastModified": 1744098102, + "narHash": "sha256-tzCdyIJj9AjysC3OuKA+tMD/kDEDAF9mICPDU7ix0JA=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "c8cd81426f45942bb2906d5ed2fe21d2f19d95b7", + "type": "github" }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs-lib": { "locked": { - "lastModified": 1749111814, - "narHash": "sha256-QqriB8GtPn7hxAPyp7jIk3a2555p75/kmB90n2abu5g=", - "owner": "imincik", - "repo": "geospatial-nix.repo", - "rev": "41f92ade4891a67c44d06ac37dcc225a3b123160", + "lastModified": 1743296961, + "narHash": "sha256-b1EdN3cULCqtorQ4QeWgLMrd5ZGOjLSLemfa00heasc=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "e4822aea2a6d1cdd36653c134cacfd64c97ff4fa", "type": "github" }, "original": { - "owner": "imincik", - "repo": "geospatial-nix.repo", + "owner": "nix-community", + "repo": "nixpkgs.lib", "type": "github" } }, - "nixgl": { - "inputs": { - "flake-utils": "flake-utils", - "nixpkgs": [ - "geospatial", - "nixpkgs" - ] + "nixpkgs-lib_2": { + "locked": { + "lastModified": 1743296961, + "narHash": "sha256-b1EdN3cULCqtorQ4QeWgLMrd5ZGOjLSLemfa00heasc=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "e4822aea2a6d1cdd36653c134cacfd64c97ff4fa", + "type": "github" }, + "original": { + "owner": "nix-community", + "repo": "nixpkgs.lib", + "type": "github" + } + }, + "nixpkgs-lib_3": { "locked": { - "lastModified": 1713543440, - "narHash": "sha256-lnzZQYG0+EXl/6NkGpyIz+FEOc/DSEG57AP1VsdeNrM=", + "lastModified": 1743296961, + "narHash": "sha256-b1EdN3cULCqtorQ4QeWgLMrd5ZGOjLSLemfa00heasc=", "owner": "nix-community", - "repo": "nixGL", - "rev": "310f8e49a149e4c9ea52f1adf70cdc768ec53f8a", + "repo": "nixpkgs.lib", + "rev": "e4822aea2a6d1cdd36653c134cacfd64c97ff4fa", "type": "github" }, "original": { "owner": "nix-community", - "repo": "nixGL", + "repo": "nixpkgs.lib", "type": "github" } }, - "nixpkgs": { + "nixpkgs_2": { "locked": { - "lastModified": 1748856973, - "narHash": "sha256-RlTsJUvvr8ErjPBsiwrGbbHYW8XbB/oek0Gi78XdWKg=", + "lastModified": 1745234285, + "narHash": "sha256-GfpyMzxwkfgRVN0cTGQSkTC0OHhEkv3Jf6Tcjm//qZ0=", "owner": "NixOS", "repo": "nixpkgs", - "rev": "e4b09e47ace7d87de083786b404bf232eb6c89d8", + "rev": "c11863f1e964833214b767f4a369c6e6a7aba141", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs_3": { + "locked": { + "lastModified": 1744868846, + "narHash": "sha256-5RJTdUHDmj12Qsv7XOhuospjAjATNiTMElplWnJE9Hs=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "ebe4301cbd8f81c4f8d3244b3632338bbeb6d49c", "type": "github" }, "original": { @@ -91,28 +144,124 @@ "type": "github" } }, - "nixpkgs-lib": { + "nixpkgs_4": { "locked": { - "lastModified": 1748740939, - "narHash": "sha256-rQaysilft1aVMwF14xIdGS3sj1yHlI6oKQNBRTF40cc=", - "owner": "nix-community", - "repo": "nixpkgs.lib", - "rev": "656a64127e9d791a334452c6b6606d17539476e2", + "lastModified": 1744868846, + "narHash": "sha256-5RJTdUHDmj12Qsv7XOhuospjAjATNiTMElplWnJE9Hs=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "ebe4301cbd8f81c4f8d3244b3632338bbeb6d49c", "type": "github" }, "original": { - "owner": "nix-community", - "repo": "nixpkgs.lib", + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs_5": { + "locked": { + "lastModified": 1744868846, + "narHash": "sha256-5RJTdUHDmj12Qsv7XOhuospjAjATNiTMElplWnJE9Hs=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "ebe4301cbd8f81c4f8d3244b3632338bbeb6d49c", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "qgisLatest": { + "inputs": { + "flake-parts": "flake-parts", + "nixpkgs": "nixpkgs_3" + }, + "locked": { + "lastModified": 1746268773, + "narHash": "sha256-WO1SHo96bKcPkZ0s9GogL0JqEukhwTZrSsw+bwl79m4=", + "owner": "imincik", + "repo": "QGIS", + "rev": "0e95bafe8cdc920080c53b7d15ab867eb78f631d", + "type": "github" + }, + "original": { + "owner": "imincik", + "ref": "nix-package-release-3_42", + "repo": "QGIS", + "type": "github" + } + }, + "qgisLtr": { + "inputs": { + "flake-parts": "flake-parts_2", + "nixpkgs": "nixpkgs_4" + }, + "locked": { + "lastModified": 1746604554, + "narHash": "sha256-uglIhnYAN7dB02sBr+DV2KlYtARURUVNuP0uIsiEAs8=", + "owner": "imincik", + "repo": "QGIS", + "rev": "e82dcace180741f5e23baea8c46b08d625fba14f", + "type": "github" + }, + "original": { + "owner": "imincik", + "ref": "nix-package-release-3_40", + "repo": "QGIS", + "type": "github" + } + }, + "qgisMaster": { + "inputs": { + "flake-parts": "flake-parts_3", + "nixpkgs": "nixpkgs_5" + }, + "locked": { + "lastModified": 1746545503, + "narHash": "sha256-3bBzsn+6swpEKk5obmENeQj4XmMkxXFdze9oQ0xfdIs=", + "owner": "imincik", + "repo": "QGIS", + "rev": "43f75f91b5d16a8bd83cee030e015839cc2b76c2", + "type": "github" + }, + "original": { + "owner": "imincik", + "ref": "nix-package-master", + "repo": "QGIS", + "type": "github" + } + }, + "qgisPyQgisDocumentationRepo": { + "inputs": { + "nixpkgs": "nixpkgs_2", + "qgisLatest": "qgisLatest", + "qgisLtr": "qgisLtr", + "qgisMaster": "qgisMaster" + }, + "locked": { + "lastModified": 1746780316, + "narHash": "sha256-MbCeJ4KgYilj13/Dhsq5GCWQ2DKLeMtiyp4KWMYEobE=", + "owner": "imincik", + "repo": "pyqgis-api-docs-builder", + "rev": "535ea3212dba1d39d413adae645c536e159ac907", + "type": "github" + }, + "original": { + "owner": "imincik", + "ref": "nix-package", + "repo": "pyqgis-api-docs-builder", "type": "github" } }, "root": { "inputs": { - "geospatial": "geospatial", - "nixpkgs": [ - "geospatial", - "nixpkgs" - ] + "nixpkgs": "nixpkgs", + "qgisPyQgisDocumentationRepo": "qgisPyQgisDocumentationRepo" } } }, diff --git a/flake.nix b/flake.nix index 5aebc0f4348..2e2ca646585 100644 --- a/flake.nix +++ b/flake.nix @@ -1,66 +1,138 @@ { - description = "Run QGIS with extra Python packages"; + description = "QGIS Documentation"; - inputs.geospatial.url = "github:imincik/geospatial-nix.repo"; - inputs.nixpkgs.follows = "geospatial/nixpkgs"; + nixConfig = { + # extra-substituters = [ "https://example.cachix.org" ]; + # extra-trusted-public-keys = [ "example.cachix.org-1:xxxx=" ]; + + # IFD is required for QGIS repo. + allow-import-from-derivation = true; + }; + + inputs = { + nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable"; + + qgisPyQgisDocumentationRepo = { + # FIXME: https://github.com/qgis/QGIS-Sysadmin-Documentation/issues/137 + url = "github:imincik/pyqgis-api-docs-builder/nix-package"; + }; + }; + + outputs = inputs@{ self, nixpkgs, qgisPyQgisDocumentationRepo }: - outputs = { self, geospatial, nixpkgs }: let - system = "x86_64-linux"; - pkgs = import nixpkgs { + # Flake system + supportedSystems = [ "x86_64-linux" "aarch64-linux" "x86_64-darwin" "aarch64-darwin" ]; + forAllSystems = nixpkgs.lib.genAttrs supportedSystems; + nixpkgsFor = forAllSystems (system: import nixpkgs { inherit system; - config = { allowUnfree = true; }; - }; - extraPythonPackages = ps: [ - ps.pyqtwebengine - ps.jsonschema - ps.debugpy - ps.future - ps.psutil - ]; - qgisWithExtras = geospatial.packages.${system}.qgis.override { - inherit extraPythonPackages; - }; - qgisLtrWithExtras = geospatial.packages.${system}.qgis-ltr.override { - inherit extraPythonPackages; - }; - in { - packages.${system} = { - default = qgisWithExtras; - qgis-ltr = qgisLtrWithExtras; - }; - - devShells.${system}.default = pkgs.mkShell { - packages = [ - pkgs.gum - pkgs.gource - pkgs.ffmpeg - pkgs.chafa - pkgs.pre-commit - pkgs.nixfmt-rfc-style - (pkgs.python3.withPackages (ps: [ - ps.pip - ps.setuptools - ps.sphinx - ps.sphinx_rtd_theme - ps.recommonmark - ps.myst-parser - ps.sphinx-autobuild - ps.docutils - ps.rstcheck - ps.sphinxext-rediraffe - ps.sphinx-togglebutton - ps.sphinx-copybutton - ])) - pkgs.vscode - pkgs.transifex-cli - pkgs.texlive.combined.scheme-full - ]; - shellHook = '' - - #source ${./scripts/shell-hook.sh} - ''; - }; + config.allowUnfree = true; + }); + + in + { + # + ### PACKAGES + # + + packages = forAllSystems (system: + let + pkgs = nixpkgsFor.${system}; + + in + { + # TODO: add docs-master and docs-ltr versions + docs-latest = pkgs.callPackage ./nix/package.nix { + pyQgisDocumentation = qgisPyQgisDocumentationRepo.packages.${system}.docs-latest; + }; + + # FIXME + # default = docs-master; + }); + + + # + ### APPS + # + + apps = forAllSystems (system: + let + pkgs = nixpkgsFor.${system}; + inherit (nixpkgs) lib; + + wwwLauncherLatest = pkgs.writeShellApplication { + name = "website"; + runtimeInputs = [ pkgs.python3 ]; + text = '' + exec ${lib.getExe pkgs.python3} \ + -m http.server 8000 \ + -d ${self.packages.${system}.docs-latest}/ + ''; + }; + + in + rec { + docs-latest = { + type = "app"; + program = "${wwwLauncherLatest}/bin/website"; + }; + + default = docs-latest; + }); + + + # + ### SHELLS + # + + devShells = forAllSystems (system: + let + pkgs = nixpkgsFor.${system}; + + pythonPackages = pkgs.python3Packages; + in + { + # Development environment + default = pkgs.mkShell { + name = "impurePythonEnv"; + venvDir = "./.venv"; + buildInputs = [ + # A Python interpreter including the 'venv' module is required to bootstrap + # the environment. + pythonPackages.python + + # This executes some shell code to initialize a venv in $venvDir before + # dropping into the shell + pythonPackages.venvShellHook + pkgs.vscode + pkgs.transifex-cli + + # Those are dependencies that we would like to use from nixpkgs, which will + # add them to PYTHONPATH and thus make them accessible from within the venv. + ]; + + # Run this command, only after creating the virtual environment + postVenvCreation = '' + export DIRENV_LOG_FORMAT= + unset SOURCE_DATE_EPOCH + pip install -r REQUIREMENTS.txt + echo "-----------------------" + echo "🌈 Your Dev Environment is prepared." + echo "📒 Note:" + echo "-----------------------" + echo "start vscode like this:" + echo "" + echo "./vscode.sh" + echo "-----------------------" + ''; + + # Now we can execute any commands within the virtual environment. + # This is optional and can be left out to run pip manually. + postShellHook = '' + # allow pip to install wheels + unset SOURCE_DATE_EPOCH + ''; + }; + }); }; } - diff --git a/nix/examples/flake.lock b/nix/examples/flake.lock new file mode 100644 index 00000000000..3b54e324b95 --- /dev/null +++ b/nix/examples/flake.lock @@ -0,0 +1,121 @@ +{ + "nodes": { + "flake-parts": { + "inputs": { + "nixpkgs-lib": "nixpkgs-lib" + }, + "locked": { + "lastModified": 1748821116, + "narHash": "sha256-F82+gS044J1APL0n4hH50GYdPRv/5JWm34oCJYmVKdE=", + "owner": "hercules-ci", + "repo": "flake-parts", + "rev": "49f0870db23e8c1ca0b5259734a02cd9e1e371a1", + "type": "github" + }, + "original": { + "owner": "hercules-ci", + "repo": "flake-parts", + "type": "github" + } + }, + "flake-utils": { + "locked": { + "lastModified": 1659877975, + "narHash": "sha256-zllb8aq3YO3h8B/U0/J1WBgAL8EX5yWf5pMj3G0NAmc=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "c0e246b9b83f637f4681389ecabcb2681b4f3af0", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "geospatial": { + "inputs": { + "flake-parts": "flake-parts", + "nixgl": "nixgl", + "nixpkgs": "nixpkgs" + }, + "locked": { + "lastModified": 1749111814, + "narHash": "sha256-QqriB8GtPn7hxAPyp7jIk3a2555p75/kmB90n2abu5g=", + "owner": "imincik", + "repo": "geospatial-nix.repo", + "rev": "41f92ade4891a67c44d06ac37dcc225a3b123160", + "type": "github" + }, + "original": { + "owner": "imincik", + "repo": "geospatial-nix.repo", + "type": "github" + } + }, + "nixgl": { + "inputs": { + "flake-utils": "flake-utils", + "nixpkgs": [ + "geospatial", + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1713543440, + "narHash": "sha256-lnzZQYG0+EXl/6NkGpyIz+FEOc/DSEG57AP1VsdeNrM=", + "owner": "nix-community", + "repo": "nixGL", + "rev": "310f8e49a149e4c9ea52f1adf70cdc768ec53f8a", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "nixGL", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1748856973, + "narHash": "sha256-RlTsJUvvr8ErjPBsiwrGbbHYW8XbB/oek0Gi78XdWKg=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "e4b09e47ace7d87de083786b404bf232eb6c89d8", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs-lib": { + "locked": { + "lastModified": 1748740939, + "narHash": "sha256-rQaysilft1aVMwF14xIdGS3sj1yHlI6oKQNBRTF40cc=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "656a64127e9d791a334452c6b6606d17539476e2", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "nixpkgs.lib", + "type": "github" + } + }, + "root": { + "inputs": { + "geospatial": "geospatial", + "nixpkgs": [ + "geospatial", + "nixpkgs" + ] + } + } + }, + "root": "root", + "version": 7 +} diff --git a/nix/examples/flake.nix b/nix/examples/flake.nix new file mode 100644 index 00000000000..5aebc0f4348 --- /dev/null +++ b/nix/examples/flake.nix @@ -0,0 +1,66 @@ +{ + description = "Run QGIS with extra Python packages"; + + inputs.geospatial.url = "github:imincik/geospatial-nix.repo"; + inputs.nixpkgs.follows = "geospatial/nixpkgs"; + + outputs = { self, geospatial, nixpkgs }: + let + system = "x86_64-linux"; + pkgs = import nixpkgs { + inherit system; + config = { allowUnfree = true; }; + }; + extraPythonPackages = ps: [ + ps.pyqtwebengine + ps.jsonschema + ps.debugpy + ps.future + ps.psutil + ]; + qgisWithExtras = geospatial.packages.${system}.qgis.override { + inherit extraPythonPackages; + }; + qgisLtrWithExtras = geospatial.packages.${system}.qgis-ltr.override { + inherit extraPythonPackages; + }; + in { + packages.${system} = { + default = qgisWithExtras; + qgis-ltr = qgisLtrWithExtras; + }; + + devShells.${system}.default = pkgs.mkShell { + packages = [ + pkgs.gum + pkgs.gource + pkgs.ffmpeg + pkgs.chafa + pkgs.pre-commit + pkgs.nixfmt-rfc-style + (pkgs.python3.withPackages (ps: [ + ps.pip + ps.setuptools + ps.sphinx + ps.sphinx_rtd_theme + ps.recommonmark + ps.myst-parser + ps.sphinx-autobuild + ps.docutils + ps.rstcheck + ps.sphinxext-rediraffe + ps.sphinx-togglebutton + ps.sphinx-copybutton + ])) + pkgs.vscode + pkgs.transifex-cli + pkgs.texlive.combined.scheme-full + ]; + shellHook = '' + + #source ${./scripts/shell-hook.sh} + ''; + }; + }; +} + diff --git a/nix/package.nix b/nix/package.nix new file mode 100644 index 00000000000..1c1a8b1216d --- /dev/null +++ b/nix/package.nix @@ -0,0 +1,128 @@ +{ lib +, stdenv +, fetchFromGitHub + +, pyQgisDocumentation + +, python3Packages +}: + +let + sphinxext-rediraffe = python3Packages.buildPythonPackage rec { + pname = "sphinxext-rediraffe"; + version = "0.2.7"; + pyproject = true; + + src = fetchFromGitHub { + owner = "sphinx-doc"; + repo = "sphinxext-rediraffe"; + rev = "refs/tags/v${version}"; + hash = "sha256-g+GD1ApD26g6PwPOH/ir7aaEgH+n1QQYSr9QizYrmug="; + }; + + # Fix "packaging.version.InvalidVersion: Invalid version: 'main'" + postPatch = '' + substituteInPlace "setup.py" \ + --replace-fail 'version = "main"' 'version = "${version}"' + ''; + + build-system = with python3Packages; [ + setuptools + ]; + + dependencies = with python3Packages; [ + sphinx + ]; + + pythonImportsCheck = [ "sphinxext.rediraffe" ]; + }; + + sphinx-togglebutton = python3Packages.buildPythonPackage rec { + pname = "sphinx-togglebutton"; + version = "0.3.2"; + pyproject = true; + + src = fetchFromGitHub { + owner = "executablebooks"; + repo = "sphinx-togglebutton"; + rev = "refs/tags/v${version}"; + hash = "sha256-i7SshD1giWgDAHpiIBW03OCTLlPO/Y3Ykz0WXGoG5Zg="; + }; + + build-system = with python3Packages; [ + setuptools + ]; + + dependencies = with python3Packages; [ + sphinx + ]; + + pythonImportsCheck = [ "sphinx_togglebutton" ]; + }; + + # FIXME: don't hardcode QGIS version + intersphinxMapping = "${pyQgisDocumentation}/3.42/objects.inv"; + +in +stdenv.mkDerivation { + name = "qgis-documentation"; + + src = lib.cleanSourceWith { + src = ../.; + filter = ( + path: type: (builtins.all (x: x != baseNameOf path) [ + ".git" + ".github" + "flake.nix" + "flake.lock" + "package.nix" + "result" + ]) + ); + }; + + postPatch = '' + # Load intersphinx inventory objects from pre-fetched file + substituteInPlace "conf.py" \ + --replace-fail \ + "'https://qgis.org/pyqgis/{}/'.format(pyqgis_version), None)}" \ + "'${intersphinxMapping}', '${intersphinxMapping}')}" + + # Fix "WARNING: unsupported theme option 'display_version' given" + # https://github.com/readthedocs/sphinx_rtd_theme/issues/1623 + substituteInPlace "conf.py" \ + --replace-fail \ + "'display_version': True," \ + "# 'display_verson': True," + ''; + + buildInputs = with python3Packages; [ + pyyaml + sphinx + sphinx-copybutton + sphinxext-rediraffe + sphinx-intl + sphinx-rtd-theme + sphinx-tabs + sphinx-togglebutton + ]; + + buildPhase = '' + # List of languages taken from Makefile + LANGUAGES="en bg cs de es fi fr id it ja ko nl pt_BR pt_PT ro ru tr zh_Hant zh_Hans" + + for LANG in $LANGUAGES; do + if [ "$LANG" != "en" ]; then + sphinx-build -b html . build/html/$LANG -D language=$LANG -t i18n + else + sphinx-build -b html -nW --keep-going . build/html/$LANG + fi + done + ''; + + installPhase = '' + mkdir -p $out + cp -r build/html/* $out/ + ''; +} +