From c1542ebb5616f33332cb9acf2e6c608fd9429dbf Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 12:42:02 +0200 Subject: [PATCH 1/9] skia-python: add build-skia-python.yml for riscv64 wheels --- .github/workflows/build-skia-python.yml | 122 ++++++++++++++++++++++++ 1 file changed, 122 insertions(+) create mode 100644 .github/workflows/build-skia-python.yml diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml new file mode 100644 index 000000000..970a3e341 --- /dev/null +++ b/.github/workflows/build-skia-python.yml @@ -0,0 +1,122 @@ +# SPDX-FileCopyrightText: 2026 The RISE Project +# SPDX-License-Identifier: MIT +--- +# This workflow is based on the `build_wheels` job of: +# https://github.com/kyamagu/skia-python/blob/v144.0.post2/.github/workflows/ci.yml +name: Build skia-python wheels (riscv64) + +on: + workflow_dispatch: + inputs: + version: + description: 'skia-python version to build (git tag without leading v, e.g. 144.0.post2)' + required: true + default: '144.0.post2' + pull_request: + paths: + - '.github/workflows/build-skia-python.yml' + +concurrency: + group: ${{ github.workflow }}-${{ inputs.version || '144.0.post2' }}-${{ github.head_ref || github.run_id }} + cancel-in-progress: true + +permissions: + contents: read # to fetch code (actions/checkout) + +env: + # `inputs.version` is empty on pull_request events; default to 144.0.post2 there. + SKIA_PYTHON_VERSION: ${{ inputs.version || '144.0.post2' }} + GN_REVISION: 0625da07ece7b1a374ec0719b6f40ebe3d0950c1 + MANYLINUX_RISCV64_IMAGE: quay.io/pypa/manylinux_2_39_riscv64 + +jobs: + setup: + uses: $/.github/workflows/_setup.yml + + build_wheels: + needs: [setup] + name: Build skia-python ${{ inputs.version || '144.0.post2' }} cp312/cp313/cp314/cp314t-manylinux_riscv64 + runs-on: ubuntu-24.04-riscv + timeout-minutes: 1440 # full Skia (Chromium's 2D graphics engine) compile from source + + steps: + - name: Checkout skia-python v${{ env.SKIA_PYTHON_VERSION }} + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 + with: + repository: kyamagu/skia-python + ref: v${{ env.SKIA_PYTHON_VERSION }} + submodules: true + persist-credentials: false + + - name: Build wheels + uses: pypa/cibuildwheel@1828c10ab37f080699c7b81cea34097c684a7074 # v4.2.0 + with: + output-dir: wheelhouse/ + env: + CIBW_ARCHS: riscv64 + CIBW_BUILD: cp312-manylinux_riscv64 cp313-manylinux_riscv64 cp314-manylinux_riscv64 cp314t-manylinux_riscv64 + CIBW_MANYLINUX_RISCV64_IMAGE: ${{ env.MANYLINUX_RISCV64_IMAGE }} + CIBW_SKIP: "*musllinux*" + # Reimplements scripts/build_Linux.sh: its `yum install ... ninja-build gn` + # comes from EPEL, which the riscv64 manylinux image doesn't carry (gotcha + # 51), so ninja comes from its own riscv64 PyPI wheel and gn is bootstrapped + # from source (gn.googlesource.com/gn's build/gen.py has no arch-specific + # logic). Everything after that mirrors the upstream script unchanged. + CIBW_BEFORE_ALL_LINUX: | + set -e + dnf install -y --enablerepo=crb \ + fontconfig-devel mesa-libGL-devel mesa-libEGL-devel libglvnd-devel \ + mesa-libGLES-devel libglvnd mesa-libGLES mesa-libEGL libglvnd-egl \ + xorg-x11-server-Xvfb mesa-dri-drivers expat-devel libxml2-devel + python3 -m pip install ninja + git clone --depth 1 https://gn.googlesource.com/gn /tmp/gn + git -C /tmp/gn fetch --depth 1 origin ${{ env.GN_REVISION }} + git -C /tmp/gn checkout ${{ env.GN_REVISION }} + (cd /tmp/gn && python3 build/gen.py && ninja -C out gn) + install -m 0755 /tmp/gn/out/gn /usr/local/bin/gn + cd skia + patch -R -p1 < ../patch/0001-Make-SkPath-immutable-on-GN-build.patch + patch -R -p1 < ../patch/0001-Disable-legacy-PNG-encoding-decoding-in-SkPicture.patch + patch -p1 < ../patch/skia-m144-minimize-download.patch + patch -p1 < ../patch/skia-m132-colrv1-freetype.diff + patch -p1 < ../patch/skia-m132-egl-runtime.diff + python3 tools/git-sync-deps + gn gen out/Release --args=" + is_official_build=true + skia_enable_svg=true + skia_use_vulkan=true + skia_use_system_libjpeg_turbo=false + skia_use_system_libwebp=false + skia_use_system_libpng=false + skia_use_system_icu=false + skia_use_system_harfbuzz=false + skia_use_system_freetype2=false + extra_cflags_cc=[\"-frtti\"] + extra_ldflags=[\"-lrt\"] + " + ninja -C out/Release + cd .. + CIBW_BEFORE_BUILD: pip install pybind11 numpy + CIBW_ENVIRONMENT: PIP_EXTRA_INDEX_URL=https://pypi.riseproject.dev/simple/ + CIBW_TEST_REQUIRES: pytest pillow glfw + # moderngl (used only by test_GrDirectContext_MakeGL_EGL) has no riscv64 wheel. + CIBW_TEST_COMMAND: >- + xvfb-run -s "-screen 0 640x480x24" + python -m pytest {project}/tests --deselect {project}/tests/test_grcontext.py::test_GrDirectContext_MakeGL_EGL + CIBW_REPAIR_WHEEL_COMMAND_LINUX: "auditwheel repair --exclude libEGL.so.1 -w {dest_dir} {wheel}" + + - uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 + with: + name: skia-python-${{ env.SKIA_PYTHON_VERSION }}-manylinux_riscv64 + path: wheelhouse/*.whl + if-no-files-found: error + + publish: + name: Publish skia-python ${{ inputs.version || '144.0.post2' }} + needs: [setup, build_wheels] + permissions: + contents: write + pull-requests: write + uses: $/.github/workflows/_publish-wheel.yml + with: + artifact-pattern: skia-python-${{ inputs.version || '144.0.post2' }}-*-manylinux_riscv64 From 88b04194d6f6a759223990832a8f3903c3ec6b87 Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 13:09:09 +0200 Subject: [PATCH 2/9] skia-python: drop Xvfb (Rocky 10 ships none) and skip GL tests without a display Rocky 10 (the riscv64 manylinux image's base) carries no virtual X server at all -- xorg-x11-server-Xvfb, tigervnc-server and weston are all absent from BaseOS/AppStream/CRB/Extras, on every architecture, not just riscv64. Drops the dnf install and the xvfb-run wrapper, and carries a patch so the 'gpu'-parametrized tests skip gracefully instead of erroring when glfw can't reach a display. --- .github/workflows/build-skia-python.yml | 16 ++++++- ...-tests-when-glfw.init-fails-not-just.patch | 43 +++++++++++++++++++ 2 files changed, 57 insertions(+), 2 deletions(-) create mode 100644 patches/skia-python/144.0.post2/0001-Skip-GPU-context-tests-when-glfw.init-fails-not-just.patch diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index 970a3e341..9fb5c4e07 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -15,6 +15,7 @@ on: pull_request: paths: - '.github/workflows/build-skia-python.yml' + - 'patches/skia-python/**' concurrency: group: ${{ github.workflow }}-${{ inputs.version || '144.0.post2' }}-${{ github.head_ref || github.run_id }} @@ -48,6 +49,15 @@ jobs: submodules: true persist-credentials: false + - name: Checkout python-wheels + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 + with: + path: python-wheels + persist-credentials: false + + - name: Patch skia-python source + run: git apply python-wheels/patches/skia-python/${{ env.SKIA_PYTHON_VERSION }}/*.patch + - name: Build wheels uses: pypa/cibuildwheel@1828c10ab37f080699c7b81cea34097c684a7074 # v4.2.0 with: @@ -67,7 +77,7 @@ jobs: dnf install -y --enablerepo=crb \ fontconfig-devel mesa-libGL-devel mesa-libEGL-devel libglvnd-devel \ mesa-libGLES-devel libglvnd mesa-libGLES mesa-libEGL libglvnd-egl \ - xorg-x11-server-Xvfb mesa-dri-drivers expat-devel libxml2-devel + mesa-dri-drivers expat-devel libxml2-devel python3 -m pip install ninja git clone --depth 1 https://gn.googlesource.com/gn /tmp/gn git -C /tmp/gn fetch --depth 1 origin ${{ env.GN_REVISION }} @@ -100,8 +110,10 @@ jobs: CIBW_ENVIRONMENT: PIP_EXTRA_INDEX_URL=https://pypi.riseproject.dev/simple/ CIBW_TEST_REQUIRES: pytest pillow glfw # moderngl (used only by test_GrDirectContext_MakeGL_EGL) has no riscv64 wheel. + # No xvfb-run: Rocky 10 ships no Xvfb (nor Xvnc/weston) at all, so there's no + # display to run one under; 0001-*.patch makes the 'gpu'-parametrized tests + # skip instead of error when glfw can't reach one. CIBW_TEST_COMMAND: >- - xvfb-run -s "-screen 0 640x480x24" python -m pytest {project}/tests --deselect {project}/tests/test_grcontext.py::test_GrDirectContext_MakeGL_EGL CIBW_REPAIR_WHEEL_COMMAND_LINUX: "auditwheel repair --exclude libEGL.so.1 -w {dest_dir} {wheel}" diff --git a/patches/skia-python/144.0.post2/0001-Skip-GPU-context-tests-when-glfw.init-fails-not-just.patch b/patches/skia-python/144.0.post2/0001-Skip-GPU-context-tests-when-glfw.init-fails-not-just.patch new file mode 100644 index 000000000..16c8c2375 --- /dev/null +++ b/patches/skia-python/144.0.post2/0001-Skip-GPU-context-tests-when-glfw.init-fails-not-just.patch @@ -0,0 +1,43 @@ +From ba4f377e460a8611d1ca7ff6015306913bcfd714 Mon Sep 17 00:00:00 2001 +From: Ludovic Henry +Date: Thu, 10 Sep 2026 13:07:37 +0200 +Subject: [PATCH] Skip GPU-context tests when glfw.init() fails, not just when + glfw is missing + +opengl_context's try/except only catches ImportError (glfw not +installed) and UserWarning; glfw_context() raises a plain RuntimeError +when glfw.init() returns False, which happens whenever no display +server (X11/Wayland) is reachable, not only when glfw itself is +absent. That RuntimeError propagates uncaught, erroring every test +that depends on the 'gpu'-parametrized surface/context fixtures +instead of the graceful pytest.skip('OpenGL is not available') the +rest of this fixture already falls back to. + +Rocky Linux 10 (the riscv64 manylinux image's base) ships no virtual +X server at all: xorg-x11-server-Xvfb, tigervnc-server and weston are +all absent from BaseOS/AppStream/CRB/Extras on every architecture, not +just riscv64 (RHEL 10 dropped Xvfb outright, same shape as its SDL2 +removal) -- so no DISPLAY is ever available to build a real GL context +in that container, and every test using 'gpu' hits this exact path. + +Upstream-Status: Inappropriate [Rocky 10, this repo's riscv64 CI base image, ships no Xvfb/Xvnc/weston at all -- specific to our infra, not a defect other environments with a display server would hit] +--- + tests/conftest.py | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/tests/conftest.py b/tests/conftest.py +index 0658d2a..af22987 100644 +--- a/tests/conftest.py ++++ b/tests/conftest.py +@@ -46,7 +46,7 @@ def opengl_context(request): + return + except ImportError: + logger.warning('glfw not found') +- except UserWarning as e: ++ except (RuntimeError, UserWarning) as e: + logger.exception(e) + pytest.skip('GLFW error') + +-- +2.50.1 (Apple Git-155) + From 500e9b788b4b9633f855d43420fabfd9da9224e5 Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 13:59:28 +0200 Subject: [PATCH 3/9] skia-python: full-clone gn, not --depth 1 build/gen.py's GenerateLastCommitPosition runs 'git describe HEAD --match initial-commit' unconditionally whenever .git exists, to generate a cosmetic version header; a depth-1 clone has none of the history back to that root tag, so it fails outright with 'No names found, cannot describe anything.' gn's repo is 42MB full, ~4s to clone -- shallow isn't worth the fragility here. --- .github/workflows/build-skia-python.yml | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index 9fb5c4e07..e233b18bd 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -79,8 +79,10 @@ jobs: mesa-libGLES-devel libglvnd mesa-libGLES mesa-libEGL libglvnd-egl \ mesa-dri-drivers expat-devel libxml2-devel python3 -m pip install ninja - git clone --depth 1 https://gn.googlesource.com/gn /tmp/gn - git -C /tmp/gn fetch --depth 1 origin ${{ env.GN_REVISION }} + # Full clone, not --depth 1: build/gen.py's GenerateLastCommitPosition + # runs `git describe --match initial-commit` unconditionally whenever + # .git exists, which needs the full history back to that root tag. + git clone https://gn.googlesource.com/gn /tmp/gn git -C /tmp/gn checkout ${{ env.GN_REVISION }} (cd /tmp/gn && python3 build/gen.py && ninja -C out gn) install -m 0755 /tmp/gn/out/gn /usr/local/bin/gn From 420ba83b44a4313286b301fa5fdeee3759d97710 Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 14:31:08 +0200 Subject: [PATCH 4/9] skia-python: force CXX=g++ when bootstrapping gn build/gen.py's WriteGNNinja defaults cxx to os.environ.get('CXX', 'clang++') on any non-MSVC/AIX/Windows host, unconditionally -- verified against a real clone of gn's own source, and against the live manylinux_2_39_riscv64 image manifest (quay.io), which has no layer installing clang anywhere; only GCC is provisioned. The /opt/clang/bin PATH entry baked into the image's own ENV is a dead path on this architecture. Skia's own build already assumes GCC (upstream's gn args set no is_clang), so this just makes gn's bootstrap use the same toolchain the rest of the build already relies on. --- .github/workflows/build-skia-python.yml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index e233b18bd..fcfde828a 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -84,7 +84,9 @@ jobs: # .git exists, which needs the full history back to that root tag. git clone https://gn.googlesource.com/gn /tmp/gn git -C /tmp/gn checkout ${{ env.GN_REVISION }} - (cd /tmp/gn && python3 build/gen.py && ninja -C out gn) + # build/gen.py defaults CXX to clang++ on any non-MSVC/AIX/Windows + # host when CXX isn't set; this image has no clang, only GCC. + (cd /tmp/gn && CXX=g++ python3 build/gen.py && ninja -C out gn) install -m 0755 /tmp/gn/out/gn /usr/local/bin/gn cd skia patch -R -p1 < ../patch/0001-Make-SkPath-immutable-on-GN-build.patch From f6d6c73ff6305e6d4ab82530675f2ce690b755fb Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 14:59:01 +0200 Subject: [PATCH 5/9] skia-python: pass --allow-warnings to gn's own build/gen.py GCC's -Wcomment fires on src/gn/header_checker.h's ASCII-art dependency-graph diagram (a // line ending in a backslash, e.g. '// / \'), and gen.py sets -Werror unconditionally unless told otherwise. gn's own gen.py ships an --allow-warnings flag for exactly this (source only gets -Werror coverage against clang upstream); using it is cleaner than patching a third-party bootstrap tool's own source for an ASCII-art comment. gn itself never ships in the wheel, so this carries no risk to the built extension. --- .github/workflows/build-skia-python.yml | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index fcfde828a..d3d6f39d7 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -86,7 +86,10 @@ jobs: git -C /tmp/gn checkout ${{ env.GN_REVISION }} # build/gen.py defaults CXX to clang++ on any non-MSVC/AIX/Windows # host when CXX isn't set; this image has no clang, only GCC. - (cd /tmp/gn && CXX=g++ python3 build/gen.py && ninja -C out gn) + # --allow-warnings: gn's own source only gets clang -Werror + # coverage upstream; GCC's -Wcomment fires on an ASCII-art + # diagram in a doc-comment (src/gn/header_checker.h). + (cd /tmp/gn && CXX=g++ python3 build/gen.py --allow-warnings && ninja -C out gn) install -m 0755 /tmp/gn/out/gn /usr/local/bin/gn cd skia patch -R -p1 < ../patch/0001-Make-SkPath-immutable-on-GN-build.patch From 172553b9bdd11f4e616f58243bcdd7955e67187c Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 15:59:33 +0200 Subject: [PATCH 6/9] skia-python: install libstdc++-static for gn's -static-libstdc++ link gn links itself with -static-libstdc++ -pthread; the riscv64 manylinux image doesn't ship libstdc++.a by default (gotcha 77), only via the CRB libstdc++-static package, already enabled for the other -devel packages on this same line. --- .github/workflows/build-skia-python.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index d3d6f39d7..7203f255e 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -77,7 +77,7 @@ jobs: dnf install -y --enablerepo=crb \ fontconfig-devel mesa-libGL-devel mesa-libEGL-devel libglvnd-devel \ mesa-libGLES-devel libglvnd mesa-libGLES mesa-libEGL libglvnd-egl \ - mesa-dri-drivers expat-devel libxml2-devel + mesa-dri-drivers expat-devel libxml2-devel libstdc++-static python3 -m pip install ninja # Full clone, not --depth 1: build/gen.py's GenerateLastCommitPosition # runs `git describe --match initial-commit` unconditionally whenever From 2be69f07eecc0cb387ca6230b64f12c0d60c083b Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 17:31:39 +0200 Subject: [PATCH 7/9] skia-python: patch skia/bin/fetch-gn to skip its riscv64-less CIPD download tools/git-sync-deps calls bin/fetch-gn unconditionally, with no skip flag (unlike its --skip-emsdk sibling). fetch-gn's CPU map has no riscv64 entry and Google's CIPD has no prebuilt gn for riscv64 to add one for, so it KeyErrors outright. We already built and installed our own gn to PATH before this step runs; nothing downstream reads skia/bin/gn or third_party/gn/gn directly, so skipping the download when a gn is already on PATH is a correct no-op here. --- ...-download-when-a-gn-is-already-on-PA.patch | 37 +++++++++++++++++++ 1 file changed, 37 insertions(+) create mode 100644 patches/skia-python/144.0.post2/0002-Skip-the-CIPD-gn-download-when-a-gn-is-already-on-PA.patch diff --git a/patches/skia-python/144.0.post2/0002-Skip-the-CIPD-gn-download-when-a-gn-is-already-on-PA.patch b/patches/skia-python/144.0.post2/0002-Skip-the-CIPD-gn-download-when-a-gn-is-already-on-PA.patch new file mode 100644 index 000000000..5c75c0722 --- /dev/null +++ b/patches/skia-python/144.0.post2/0002-Skip-the-CIPD-gn-download-when-a-gn-is-already-on-PA.patch @@ -0,0 +1,37 @@ +From 7a8dff07c5fd64343665d6b7d17994d6ee3a5b87 Mon Sep 17 00:00:00 2001 +From: Ludovic Henry +Date: Thu, 10 Sep 2026 17:30:42 +0200 +Subject: [PATCH] Skip the CIPD gn download when a gn is already on PATH + +bin/fetch-gn's CPU map (platform.machine().lower() -> {aarch64, +amd64, arm64, x86_64}) has no riscv64 entry, and there's no prebuilt +gn published for riscv64 on Google's CIPD to add one for -- so this +KeyErrors outright on any riscv64 host, unconditionally, with no way +to opt out (tools/git-sync-deps calls it with no skip flag, unlike +its --skip-emsdk sibling). When a gn is already resolvable via PATH, +skip the download entirely instead of trying to fetch one: nothing +downstream of git-sync-deps reads skia/bin/gn or third_party/gn/gn +directly, they're only ever invoked through PATH. + +Upstream-Status: Inappropriate [riscv64 has no prebuilt gn published on Google's CIPD to add a CPU-map entry for; this only ever fires when PATH already resolves one, which is specific to how this repo builds skia-python for that architecture] +--- + bin/fetch-gn | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/skia/bin/fetch-gn b/skia/bin/fetch-gn +index ebdc31c4..c425d70e 100755 +--- a/skia/bin/fetch-gn ++++ b/skia/bin/fetch-gn +@@ -17,6 +17,9 @@ from urllib.request import urlopen + + os.chdir(os.path.join(os.path.dirname(__file__), os.pardir)) + ++if shutil.which('gn'): ++ sys.exit(0) ++ + gnzip = os.path.join(tempfile.mkdtemp(), 'gn.zip') + with open(gnzip, 'wb') as f: + OS = {'darwin': 'mac', 'linux': 'linux', 'linux2': 'linux', 'win32': 'windows'}[sys.platform] +-- +2.50.1 (Apple Git-155) + From fcde2449ed88625fdf43e15072b70d8b6a87e40c Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Thu, 10 Sep 2026 21:00:53 +0200 Subject: [PATCH 8/9] skia-python: also place gn at skia/bin/gn, not just PATH BUILD.gn's 'skia.h' action target hardcodes args = [rebase_path("//bin/gn")] + ... to invoke gn/find_headers.py, which runs 'gn desc' to enumerate public include dirs for the generated skia.h umbrella header -- this is evaluated at ninja build time (not gn gen time), and reads //bin/gn directly rather than resolving through $PATH or GN's own GetExePath()-based self-regeneration mechanism. Confirmed against BUILD.gn and gn/find_headers.py at the pinned skia commit before pushing, since this failure only surfaces ~2.5h into the ninja build. Our patched bin/fetch-gn correctly no-ops (gotcha: no riscv64 CIPD binary) but never populates this path since it never runs its download logic; copy our self-built gn there explicitly, same binary already at /usr/local/bin/gn. --- .github/workflows/build-skia-python.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index 7203f255e..39f9181cf 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -91,6 +91,10 @@ jobs: # diagram in a doc-comment (src/gn/header_checker.h). (cd /tmp/gn && CXX=g++ python3 build/gen.py --allow-warnings && ninja -C out gn) install -m 0755 /tmp/gn/out/gn /usr/local/bin/gn + # BUILD.gn's `skia.h` action hardcodes rebase_path("//bin/gn") -- + # the path our patched bin/fetch-gn would have populated -- so PATH + # alone isn't enough; put the same binary there too. + install -D -m 0755 /tmp/gn/out/gn skia/bin/gn cd skia patch -R -p1 < ../patch/0001-Make-SkPath-immutable-on-GN-build.patch patch -R -p1 < ../patch/0001-Disable-legacy-PNG-encoding-decoding-in-SkPicture.patch From 92a25cd6f3bb5d6ab48f95e3ccd740e2c55470bd Mon Sep 17 00:00:00 2001 From: Ludovic Henry Date: Fri, 11 Sep 2026 02:03:19 +0200 Subject: [PATCH 9/9] skia-python: use -k for test exclusion, not path-based --deselect Gotcha 14: a --deselect path silently no-ops when it doesn't exactly match pytest's rootdir-relative nodeid, which is what happened with {project}/tests/test_grcontext.py::test_GrDirectContext_MakeGL_EGL -- it kept running and failing on the missing moderngl import. test_GrDirectContext_MakeGL_GLX has no display-unavailable skip at all (unlike the fixture-based tests 0001-*.patch covers) and fails outright with no X server. -k "not " matches by nodeid substring regardless of path form, for both. --- .github/workflows/build-skia-python.yml | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/.github/workflows/build-skia-python.yml b/.github/workflows/build-skia-python.yml index 39f9181cf..1cc7e4d2c 100644 --- a/.github/workflows/build-skia-python.yml +++ b/.github/workflows/build-skia-python.yml @@ -120,12 +120,16 @@ jobs: CIBW_BEFORE_BUILD: pip install pybind11 numpy CIBW_ENVIRONMENT: PIP_EXTRA_INDEX_URL=https://pypi.riseproject.dev/simple/ CIBW_TEST_REQUIRES: pytest pillow glfw - # moderngl (used only by test_GrDirectContext_MakeGL_EGL) has no riscv64 wheel. - # No xvfb-run: Rocky 10 ships no Xvfb (nor Xvnc/weston) at all, so there's no - # display to run one under; 0001-*.patch makes the 'gpu'-parametrized tests - # skip instead of error when glfw can't reach one. + # moderngl (used only by test_GrDirectContext_MakeGL_EGL) has no riscv64 wheel; + # test_GrDirectContext_MakeGL_GLX has no display-unavailable skip at all, unlike + # the fixture-based 'gpu'-parametrized tests 0001-*.patch covers. No xvfb-run: + # Rocky 10 ships no Xvfb (nor Xvnc/weston) at all, so there's no display to run + # one under. -k, not --deselect {project}/...: gotcha 14 -- a path-based + # --deselect silently no-ops since pytest reports nodeids relative to its + # rootdir, not the absolute {project} path. CIBW_TEST_COMMAND: >- - python -m pytest {project}/tests --deselect {project}/tests/test_grcontext.py::test_GrDirectContext_MakeGL_EGL + python -m pytest {project}/tests + -k "not test_GrDirectContext_MakeGL_EGL and not test_GrDirectContext_MakeGL_GLX" CIBW_REPAIR_WHEEL_COMMAND_LINUX: "auditwheel repair --exclude libEGL.so.1 -w {dest_dir} {wheel}" - uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1