rekado pushed a commit to branch python-team
in repository guix.

commit a7114d49b01af8e88f643a3ba788218acfbed805
Author: Lars-Dominik Braun <l...@6xq.net>
AuthorDate: Sun Jul 23 11:22:03 2023 +0200

    build-system/pyproject: Use TOML parser.
    
    More reliable than regular expressions.
    
    * guix/build-system/pyproject.scm (%pyproject-build-system-modules): Add 
(guix build toml).
    (pyproject-build): Add argument #:backend-path.
    * guix/build/pyproject-build-system.scm (build): Add support for
    auto-detected and override backend-path.
    * gnu/packages/python-build.scm (python-tomli)[arguments]: Remove
    'add-self-to-path, because it is not necessary any more.
    (python-poetry-core): Same.
    (python-hatchling): Same.
    (python-pdm-backend): Same.
---
 gnu/packages/python-build.scm         | 30 +++----------------
 guix/build-system/pyproject.scm       |  3 ++
 guix/build/pyproject-build-system.scm | 55 ++++++++++++++++++++---------------
 3 files changed, 38 insertions(+), 50 deletions(-)

diff --git a/gnu/packages/python-build.scm b/gnu/packages/python-build.scm
index 4ee0f51b3e..a7bdfab16c 100644
--- a/gnu/packages/python-build.scm
+++ b/gnu/packages/python-build.scm
@@ -178,13 +178,7 @@ Python file, so it can be easily copied into your 
project.")
         (base32 "0kwazq3i18rphcr8gak4fgzdcj5w5bbn4k4j2l6ma32gj496qlny"))))
     (build-system pyproject-build-system)
     (arguments
-     `(#:tests? #f                      ;disabled to avoid extra dependencies
-       #:phases
-       (modify-phases %standard-phases
-         (add-before 'build 'add-self-to-path
-           (lambda _
-             ;; The build system of tomli requires... tomli.
-             (setenv "PYTHONPATH" "src"))))))
+     `(#:tests? #f))                      ;disabled to avoid extra dependencies
     (native-inputs (list python-flit-core-bootstrap python-six-bootstrap))
     (home-page "https://github.com/hukkin/tomli";)
     (synopsis "Small and fast TOML parser")
@@ -525,13 +519,7 @@ compatible build front-ends to build Poetry managed 
projects.")
         (base32 "053c8dw632p7jkhjb51k0wcx6hdw4r3lk97mds76df653qxnqmf6"))))
     (build-system pyproject-build-system)
     (arguments
-     `(#:tests? #f                      ;disabled to avoid extra dependencies
-       #:phases
-       (modify-phases %standard-phases
-         (add-before 'build 'add-self-to-path
-           (lambda _
-             ;; The build system requires itself.
-             (setenv "PYTHONPATH" "src"))))))
+     `(#:tests? #f))                      ;disabled to avoid extra dependencies
     (home-page "https://github.com/python-poetry/poetry-core";)
     (synopsis "Poetry PEP 517 build back-end")
     (description
@@ -671,12 +659,7 @@ reflected in the package visible to Python, without 
needing a reinstall.")
                 "1nn5cyc9fgrbawz38drfkl2s588k2gn3yqdm2cldbx9zy0fsjbj6"))))
     (build-system pyproject-build-system)
     (arguments
-     (list #:tests? #f                  ;to keep dependencies to a minimum
-           #:phases #~(modify-phases %standard-phases
-                        (add-before 'build 'add-src-to-path
-                          ;; Hatchling uses itself to build itself.
-                          (lambda _
-                            (setenv "PYTHONPATH" "src"))))))
+     (list #:tests? #f))                  ;to keep dependencies to a minimum
     (propagated-inputs (list python-editables
                              python-packaging-bootstrap
                              python-pathspec
@@ -750,12 +733,7 @@ version control system (like Git) to determine project 
versions.")
     (build-system pyproject-build-system)
     (arguments
      (list
-      #:tests? #f ; Depends on pytest, which we cannot import into this module.
-      #:phases
-      #~(modify-phases %standard-phases
-          (add-after 'unpack 'set-pythonpath
-            (lambda _
-              (setenv "PYTHONPATH" (string-append (getcwd) "/src")))))))
+      #:tests? #f)) ; Depends on pytest, which we cannot import into this 
module.
     (home-page "https://pdm-backend.fming.dev/";)
     (synopsis
      "PEP 517 build backend for PDM")
diff --git a/guix/build-system/pyproject.scm b/guix/build-system/pyproject.scm
index 94b9d79692..585117cbf0 100644
--- a/guix/build-system/pyproject.scm
+++ b/guix/build-system/pyproject.scm
@@ -46,6 +46,7 @@
   ;; Build-side modules imported by default.
   `((guix build pyproject-build-system)
     (guix build json)
+    (guix build toml)
     ,@%python-build-system-modules))
 
 (define (default-python)
@@ -93,6 +94,7 @@
                           #:key source
                           (tests? #t)
                           (configure-flags ''())
+                          (backend-path #f)
                           (build-backend #f)
                           (test-backend #f)
                           (test-flags ''())
@@ -116,6 +118,7 @@
                  #:source #+source
                  #:configure-flags #$configure-flags
                  #:system #$system
+                 #:backend-path #$backend-path
                  #:build-backend #$build-backend
                  #:test-backend #$test-backend
                  #:test-flags #$test-flags
diff --git a/guix/build/pyproject-build-system.scm 
b/guix/build/pyproject-build-system.scm
index c69ccc9d64..947d240114 100644
--- a/guix/build/pyproject-build-system.scm
+++ b/guix/build/pyproject-build-system.scm
@@ -21,6 +21,7 @@
   #:use-module ((guix build python-build-system) #:prefix python:)
   #:use-module (guix build utils)
   #:use-module (guix build json)
+  #:use-module (guix build toml)
   #:use-module (ice-9 match)
   #:use-module (ice-9 ftw)
   #:use-module (ice-9 format)
@@ -60,8 +61,8 @@
 ;;; wheel and expected to be created by the installing utility.
 ;;; TODO: Add support for PEP-621 entry points.
 ;;;
-;;; Caveats:
-;;; - There is no support for in-tree build backends.
+;;; This module also supports in-tree build backends, which can be
+;;; overridden by #:backend-path.
 ;;;
 ;;; Code:
 ;;;
@@ -86,23 +87,23 @@
 ;; Raised, when no wheel has been built by the build system.
 (define-condition-type &no-wheels-built &python-build-error no-wheels-built?)
 
-(define* (build #:key outputs build-backend configure-flags #:allow-other-keys)
+(define* (build #:key outputs build-backend backend-path configure-flags 
#:allow-other-keys)
   "Build a given Python package."
 
-  (define (pyproject.toml->build-backend file)
-    "Look up the build backend in a pyproject.toml file."
-    (call-with-input-file file
-      (lambda (in)
-        (let loop
-          ((line (read-line in 'concat)))
-          (if (eof-object? line) #f
-              (let ((m (string-match "build-backend = [\"'](.+)[\"']" line)))
-                (if m
-                    (match:substring m 1)
-                    (loop (read-line in 'concat)))))))))
-
   (let* ((wheel-output (assoc-ref outputs "wheel"))
          (wheel-dir (if wheel-output wheel-output "dist"))
+         (pyproject.toml (if (file-exists? "pyproject.toml")
+                             (parse-toml-file "pyproject.toml")
+                             '()))
+         ;; backend-path is prepended to sys.path, so in-tree backends can be
+         ;; found. We assume toml is json-compatible and do not encode the 
resulting
+         ;; JSON list expression.
+         (auto-backend-path (recursive-assoc-ref
+                             pyproject.toml
+                             '("build-system" "backend-path")))
+         (use-backend-path (call-with-output-string
+                            (cut write-json
+                             (or backend-path auto-backend-path '()) <>)))
          ;; There is no easy way to get data from Guile into Python via
          ;; s-expressions, but we have JSON serialization already, which Python
          ;; also supports out-of-the-box.
@@ -111,10 +112,9 @@
          ;; python-setuptools’ default backend supports setup.py *and*
          ;; pyproject.toml. Allow overriding this automatic detection via
          ;; build-backend.
-         (auto-build-backend (if (file-exists? "pyproject.toml")
-                                 (pyproject.toml->build-backend
-                                  "pyproject.toml")
-                                 #f))
+         (auto-build-backend (recursive-assoc-ref
+                              pyproject.toml
+                              '("build-system" "build-backend")))
          ;; Use build system detection here and not in importer, because a) we
          ;; have alot of legacy packages and b) the importer cannot update 
arbitrary
          ;; fields in case a package switches its build system.
@@ -122,15 +122,22 @@
                                 auto-build-backend
                                 "setuptools.build_meta")))
     (format #t
-     "Using '~a' to build wheels, auto-detected '~a', override '~a'.~%"
-     use-build-backend auto-build-backend build-backend)
+     (string-append
+      "Using '~a' to build wheels, auto-detected '~a', override '~a'.~%"
+      "Prepending '~a' to sys.path, auto-detected '~a', override '~a'.~%")
+     use-build-backend auto-build-backend build-backend
+     use-backend-path auto-backend-path backend-path)
     (mkdir-p wheel-dir)
     ;; Call the PEP 517 build function, which drops a .whl into wheel-dir.
     (invoke "python" "-c"
      "import sys, importlib, json
-config_settings = json.loads (sys.argv[3])
-builder = importlib.import_module(sys.argv[1])
-builder.build_wheel(sys.argv[2], config_settings=config_settings)"
+backend_path = json.loads (sys.argv[1]) or []
+backend_path.extend (sys.path)
+sys.path = backend_path
+config_settings = json.loads (sys.argv[4])
+builder = importlib.import_module(sys.argv[2])
+builder.build_wheel(sys.argv[3], config_settings=config_settings)"
+     use-backend-path
      use-build-backend
      wheel-dir
      config-settings)))

Reply via email to