From 7d19edf06607621d0c5714508df08819de110f8d Mon Sep 17 00:00:00 2001 From: Ben Boeckel Date: Fri, 10 Apr 2026 12:24:41 -0400 Subject: [PATCH 1/2] selftest: add a test asking Python about known modules This will tell us if we have modules that work but are not part of packaging. --- projects/python3.functions.cmake | 34 +++++---- selftest/tests/CMakeLists.txt | 13 ++++ selftest/tests/python-builtin-modules.py | 89 ++++++++++++++++++++++++ selftest/tests/python-module-list.cmake | 28 ++++++++ 4 files changed, 150 insertions(+), 14 deletions(-) create mode 100755 selftest/tests/python-builtin-modules.py create mode 100644 selftest/tests/python-module-list.cmake diff --git a/projects/python3.functions.cmake b/projects/python3.functions.cmake index 0051e5d9..cc47958d 100644 --- a/projects/python3.functions.cmake +++ b/projects/python3.functions.cmake @@ -9,20 +9,7 @@ function (superbuild_python_write_reqs path) endforeach () endfunction () -function (superbuild_install_superbuild_python3) - if (USE_SYSTEM_python3) - return () - endif() - - set(options) - set(values - DESTINATION_SUBDIR - BUNDLE - LIBSUFFIX) - set(multivalues - MODULES) - cmake_parse_arguments(_install_superbuild_python "${options}" "${values}" "${multivalues}" ${ARGN}) - +function (_superbuild_install_superbuild_python3_module_list var) set(modules __future__ _bootlocale @@ -235,6 +222,25 @@ function (superbuild_install_superbuild_python3) _ssl) endif () + set("${var}" "${modules}" PARENT_SCOPE) +endfunction () + +function (superbuild_install_superbuild_python3) + if (USE_SYSTEM_python3) + return () + endif() + + set(options) + set(values + DESTINATION_SUBDIR + BUNDLE + LIBSUFFIX) + set(multivalues + MODULES) + cmake_parse_arguments(_install_superbuild_python "${options}" "${values}" "${multivalues}" ${ARGN}) + + _superbuild_install_superbuild_python3_module_list(modules) + if (WIN32) superbuild_windows_install_python( MODULE_DESTINATION "/" diff --git a/selftest/tests/CMakeLists.txt b/selftest/tests/CMakeLists.txt index 37c456f8..48339249 100644 --- a/selftest/tests/CMakeLists.txt +++ b/selftest/tests/CMakeLists.txt @@ -45,6 +45,19 @@ if (UNIX AND NOT APPLE AND NOT USE_SYSTEM_python3) ) endif () +if (TARGET "python3" AND + NOT USE_SYSTEM_python3 AND + python3_SOURCE_SELECTION VERSION_GREATER_EQUAL "3.10") + add_test( + NAME python3-packaged-modules-list + COMMAND + "${CMAKE_COMMAND}" + "-Dopenssl_enabled=${openssl_enabled}" + "-Dsuperbuild_python_executable=${superbuild_python_executable}" + "-Dsuperbuild_python_version=${superbuild_python_version}" + -P "${CMAKE_CURRENT_SOURCE_DIR}/python-module-list.cmake") +endif () + function (add_license_test package) if (NOT TARGET "${package}") return () diff --git a/selftest/tests/python-builtin-modules.py b/selftest/tests/python-builtin-modules.py new file mode 100755 index 00000000..22f62396 --- /dev/null +++ b/selftest/tests/python-builtin-modules.py @@ -0,0 +1,89 @@ +#!/usr/bin/env python3 +import sys +import importlib + +missing = set() +working = set() +known_broken = set([ + '_curses', # missing dep + '_curses_panel', # missing dep + '_gdbm', # databases; missing dep + '_hashlib', # missing dep + '_ssl', # tested elsewhere + '_tkinter', # missing dep + 'curses', # missing dep + 'nis', # Solaris + 'readline', # missing dep + 'ssl', # tested elsewhere + 'tkinter', # missing dep + 'turtle', # missing dep +]) +if sys.platform != 'linux': + known_broken.update(set([ + 'ossaudiodev', + 'spwd', + ])) +if sys.platform != 'darwin': + known_broken.update(set([ + '_dbm', # databases; missing dep + '_scproxy', # urllib helper + ])) +if sys.platform == 'win32': + known_broken.update(set([ + '_crypt', + '_posixshmem', + '_posixsubprocess', + 'crypt', + 'fcntl', + 'grp', + 'idlelib', + 'posix', + 'pty', + 'pwd', + 'resource', + 'syslog', + 'termios', + 'tty', + 'turtledemo', + ])) +else: + known_broken.update(set([ + '_msi', + '_overlapped', # asyncio impl detail + '_winapi', + '_wmi', + 'msilib', + 'msvcrt', + 'nt', + 'winreg', + 'winsound', + ])) + +uninstalled = set([ + '_aix_support', # unsupported platform + '_curses', # missing dep + '_curses_panel', # missing dep + '_ssl', # tested elsewhere +]) + +for name in sys.stdlib_module_names: + # `this` prints to stdout when imported. Skip it so it doesn't confuse + # things later. + if name == 'this': + working.add(name) + continue + try: + importlib.import_module(name) + working.add(name) + except ImportError: + missing.add(name) + +missing.difference_update(known_broken) + +if missing: + print(', '.join(missing), file=sys.stderr) + sys.exit(100) + +working.difference_update(uninstalled) + +print(';'.join(working)) diff --git a/selftest/tests/python-module-list.cmake b/selftest/tests/python-module-list.cmake new file mode 100644 index 00000000..9fad46ae --- /dev/null +++ b/selftest/tests/python-module-list.cmake @@ -0,0 +1,28 @@ +list(APPEND CMAKE_MODULE_PATH + "${CMAKE_CURRENT_LIST_DIR}/../../projects") +include(python3.functions) + +_superbuild_install_superbuild_python3_module_list(installed_modules) +execute_process( + COMMAND + "${superbuild_python_executable}" + "${CMAKE_CURRENT_LIST_DIR}/python-builtin-modules.py" + OUTPUT_VARIABLE working_modules + RESULT_VARIABLE res + ERROR_VARIABLE err + OUTPUT_STRIP_TRAILING_WHITESPACE + ERROR_STRIP_TRAILING_WHITESPACE) +if (res EQUAL 100) + message(FATAL_ERROR + "Failed to import builtin modules: ${err}") +elseif (res) + message(FATAL_ERROR + "Failed to list builtin modules: ${err}") +endif () + +list(REMOVE_ITEM working_modules + ${installed_modules}) +foreach (working_module IN LISTS working_modules) + message(SEND_ERROR + "Builtin module ${working_module} is available but not listed for packaging") +endforeach () -- GitLab From 8c5456770c361de955a7bac2f180102f260faed3 Mon Sep 17 00:00:00 2001 From: Ben Boeckel Date: Fri, 10 Apr 2026 12:42:39 -0400 Subject: [PATCH 2/2] python3: update list of modules to install --- projects/python3.functions.cmake | 110 ++++++++++++++++++++++++++++++- 1 file changed, 109 insertions(+), 1 deletion(-) diff --git a/projects/python3.functions.cmake b/projects/python3.functions.cmake index cc47958d..498c53c4 100644 --- a/projects/python3.functions.cmake +++ b/projects/python3.functions.cmake @@ -12,41 +12,117 @@ endfunction () function (_superbuild_install_superbuild_python3_module_list var) set(modules __future__ + _abc + _ast + _asyncio + _bisect + _blake2 _bootlocale + _bz2 + _codecs + _codecs_cn + _codecs_hk + _codecs_iso2022 + _codecs_jp + _codecs_kr + _codecs_tw + _collections _collections_abc _compat_pickle _compression + _contextvars + _crypt + _csv + _ctypes + _datetime + _dbm + _decimal _dummy_thread + _elementtree + _frozen_importlib + _frozen_importlib_external + _functools + _gdbm + _hashlib + _heapq + _imp + _io + _json + _locale + _lsprof _lzma _markupbase + _md5 + _msi + _multibytecodec + _multiprocessing + _opcode + _operator _osx_support + _overlapped + _pickle + _posixshmem + _posixsubprocess _py_abc + _pydatetime _pydecimal _pyio + _pylong + _queue + _random + _scproxy + _sha1 + _sha2 + _sha3 + _signal _sitebuiltins + _socket + _sqlite3 + _sre + _stat + _statistics + _string _strptime - _sysconfigdata__linux_x86_64-linux-gnu + _struct + _symtable _sysconfigdata__darwin_darwin + _sysconfigdata__linux_x86_64-linux-gnu + _thread _threading_local + _tokenize + _tracemalloc + _typing + _uuid + _warnings + _weakref _weakrefset + _winapi + _wmi + _zoneinfo abc aifc antigravity argparse + array ast asynchat asyncio asyncore + atexit + audioop base64 bdb + binascii binhex bisect + builtins bz2 cProfile calendar cgi cgitb chunk + cmath cmd code codecs @@ -78,6 +154,9 @@ function (_superbuild_install_superbuild_python3_module_list var) encodings ensurepip enum + errno + faulthandler + fcntl filecmp fileinput fnmatch @@ -85,11 +164,14 @@ function (_superbuild_install_superbuild_python3_module_list var) fractions ftplib functools + gc genericpath getopt getpass gettext glob + graphlib + grp gzip hashlib heapq @@ -104,6 +186,7 @@ function (_superbuild_install_superbuild_python3_module_list var) inspect io ipaddress + itertools json keyword lib2to3 @@ -114,11 +197,18 @@ function (_superbuild_install_superbuild_python3_module_list var) macpath mailbox mailcap + marshal + math mimetypes + mmap modulefinder + msilib + msvcrt multiprocessing netrc + nis nntplib + nt ntpath nturl2path numbers @@ -126,6 +216,7 @@ function (_superbuild_install_superbuild_python3_module_list var) operator optparse os + ossaudiodev pathlib pdb pickle @@ -135,24 +226,30 @@ function (_superbuild_install_superbuild_python3_module_list var) platform plistlib poplib + posix posixpath pprint profile pstats pty + pwd py_compile pyclbr pydoc pydoc_data + pyexpat queue quopri random re + readline reprlib + resource rlcompleter runpy sched secrets + select selectors shelve shlex @@ -164,6 +261,7 @@ function (_superbuild_install_superbuild_python3_module_list var) sndhdr socket socketserver + spwd sqlite3 sre_compile sre_constants @@ -178,19 +276,24 @@ function (_superbuild_install_superbuild_python3_module_list var) sunau symbol symtable + sys sysconfig + syslog tabnanny tarfile telnetlib tempfile + termios test textwrap this threading + time timeit tkinter token tokenize + tomllib trace traceback tracemalloc @@ -199,6 +302,7 @@ function (_superbuild_install_superbuild_python3_module_list var) turtledemo types typing + unicodedata unittest urllib uu @@ -208,12 +312,16 @@ function (_superbuild_install_superbuild_python3_module_list var) wave weakref webbrowser + winreg + winsound wsgiref xdrlib xml xmlrpc zipapp zipfile + zipimport + zlib zoneinfo ) -- GitLab