Skip to content

Commit

Permalink
Merge pull request #20467 from charris/backport-20395
Browse files Browse the repository at this point in the history
ENH: provide a convenience function to replace npy_load_module
  • Loading branch information
charris committed Nov 26, 2021
2 parents e1fe715 + ad4bbe7 commit f326832
Show file tree
Hide file tree
Showing 5 changed files with 40 additions and 17 deletions.
4 changes: 3 additions & 1 deletion numpy/compat/py3k.py
Expand Up @@ -111,7 +111,9 @@ def __exit__(self, *excinfo):

def npy_load_module(name, fn, info=None):
"""
Load a module.
Load a module. Uses ``load_module`` which will be deprecated in python
3.12. An alternative that uses ``exec_module`` is in
numpy.distutils.misc_util.exec_mod_from_location
.. versionadded:: 1.11.2
Expand Down
4 changes: 2 additions & 2 deletions numpy/distutils/ccompiler_opt.py
Expand Up @@ -645,9 +645,9 @@ def dist_log(*args, stderr=False):
@staticmethod
def dist_load_module(name, path):
"""Load a module from file, required by the abstract class '_Cache'."""
from numpy.compat import npy_load_module
from .misc_util import exec_mod_from_location
try:
return npy_load_module(name, path)
return exec_mod_from_location(name, path)
except Exception as e:
_Distutils.dist_log(e, stderr=True)
return None
Expand Down
37 changes: 29 additions & 8 deletions numpy/distutils/misc_util.py
Expand Up @@ -30,8 +30,6 @@ def clean_up_temporary_directory():

atexit.register(clean_up_temporary_directory)

from numpy.compat import npy_load_module

__all__ = ['Configuration', 'get_numpy_include_dirs', 'default_config_dict',
'dict_append', 'appendpath', 'generate_config_py',
'get_cmd', 'allpath', 'get_mathlibs',
Expand All @@ -43,7 +41,8 @@ def clean_up_temporary_directory():
'dot_join', 'get_frame', 'minrelpath', 'njoin',
'is_sequence', 'is_string', 'as_list', 'gpaths', 'get_language',
'quote_args', 'get_build_architecture', 'get_info', 'get_pkg_info',
'get_num_build_jobs']
'get_num_build_jobs', 'sanitize_cxx_flags',
'exec_mod_from_location']

class InstallableLib:
"""
Expand Down Expand Up @@ -905,9 +904,8 @@ def _get_configuration_from_setup_py(self, setup_py,
try:
setup_name = os.path.splitext(os.path.basename(setup_py))[0]
n = dot_join(self.name, subpackage_name, setup_name)
setup_module = npy_load_module('_'.join(n.split('.')),
setup_py,
('.py', 'U', 1))
setup_module = exec_mod_from_location(
'_'.join(n.split('.')), setup_py)
if not hasattr(setup_module, 'configuration'):
if not self.options['assume_default_configuration']:
self.warn('Assuming default configuration '\
Expand Down Expand Up @@ -1953,8 +1951,8 @@ def get_version(self, version_file=None, version_variable=None):
name = os.path.splitext(os.path.basename(fn))[0]
n = dot_join(self.name, name)
try:
version_module = npy_load_module('_'.join(n.split('.')),
fn, info)
version_module = exec_mod_from_location(
'_'.join(n.split('.')), fn)
except ImportError as e:
self.warn(str(e))
version_module = None
Expand Down Expand Up @@ -2415,3 +2413,26 @@ def get_build_architecture():
# systems, so delay the import to here.
from distutils.msvccompiler import get_build_architecture
return get_build_architecture()


_cxx_ignore_flags = {'-Werror=implicit-function-declaration', '-std=c99'}


def sanitize_cxx_flags(cxxflags):
'''
Some flags are valid for C but not C++. Prune them.
'''
return [flag for flag in cxxflags if flag not in _cxx_ignore_flags]


def exec_mod_from_location(modname, modfile):
'''
Use importlib machinery to import a module `modname` from the file
`modfile`. Depending on the `spec.loader`, the module may not be
registered in sys.modules.
'''
spec = importlib.util.spec_from_file_location(modname, modfile)
foo = importlib.util.module_from_spec(spec)
spec.loader.exec_module(foo)
return foo

8 changes: 4 additions & 4 deletions numpy/random/tests/test_extending.py
Expand Up @@ -5,6 +5,7 @@
import sys
import warnings
import numpy as np
from numpy.distutils.misc_util import exec_mod_from_location

try:
import cffi
Expand Down Expand Up @@ -75,10 +76,9 @@ def test_cython(tmp_path):
assert so1 is not None
assert so2 is not None
# import the so's without adding the directory to sys.path
from importlib.machinery import ExtensionFileLoader
extending = ExtensionFileLoader('extending', so1).load_module()
extending_distributions = ExtensionFileLoader('extending_distributions', so2).load_module()

exec_mod_from_location('extending', so1)
extending_distributions = exec_mod_from_location(
'extending_distributions', so2)
# actually test the cython c-extension
from numpy.random import PCG64
values = extending_distributions.uniforms_ex(PCG64(0), 10, 'd')
Expand Down
4 changes: 2 additions & 2 deletions numpy/testing/_private/utils.py
Expand Up @@ -1228,13 +1228,13 @@ def rundocs(filename=None, raise_on_error=True):
>>> np.lib.test(doctests=True) # doctest: +SKIP
"""
from numpy.compat import npy_load_module
from numpy.distutils.misc_util import exec_mod_from_location
import doctest
if filename is None:
f = sys._getframe(1)
filename = f.f_globals['__file__']
name = os.path.splitext(os.path.basename(filename))[0]
m = npy_load_module(name, filename)
m = exec_mod_from_location(name, filename)

tests = doctest.DocTestFinder().find(m)
runner = doctest.DocTestRunner(verbose=False)
Expand Down

0 comments on commit f326832

Please sign in to comment.