Fix for running 'python -m' when using swig -builtin

Same as e05b5ea for -builtin.

Also added runtime tests to check 'python -m'.
This commit is contained in:
William S Fulton 2018-12-04 19:12:13 +00:00
commit 604ae7186b
17 changed files with 155 additions and 9 deletions

View file

@ -7,6 +7,11 @@ the issue number to the end of the URL: https://github.com/swig/swig/issues/
Version 4.0.0 (in progress) Version 4.0.0 (in progress)
=========================== ===========================
2018-12-04: wsfulton
[Python] #1282 Fix running 'python -m' when using 'swig -builtin'
Similar to the earlier PEP 366 conforming fix for non-builtin.
2018-11-28: wsfulton 2018-11-28: wsfulton
[Python] When using -builtin, the two step C-extension module import is now [Python] When using -builtin, the two step C-extension module import is now
one step and the wrapped API is only available once and not in an underlying one step and the wrapped API is only available once and not in an underlying
@ -44,7 +49,7 @@ Version 4.0.0 (in progress)
[Python] #1282 Make generated module runnable via python -m (PEP 366 conforming) [Python] #1282 Make generated module runnable via python -m (PEP 366 conforming)
Previously any SWIG generated modules in a package would fail with an ImportError Previously any SWIG generated modules in a package would fail with an ImportError
when using 'python -m'. when using 'python -m' for example 'python -m mypkg.mymodule'.
2018-11-13: wsfulton 2018-11-13: wsfulton
#1340 Remove -cppcast and -nocppcast command line options (this was an option #1340 Remove -cppcast and -nocppcast command line options (this was an option

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,21 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2 import py2.pkg2
print " Finished importing py2.pkg2" print " Finished importing py2.pkg2"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py2.pkg2.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2 import py3.pkg2
print " Finished importing py3.pkg2" print " Finished importing py3.pkg2"
# commandline = sys.executable + " -m py3.pkg2.bar"
# subprocess.check_call(commandline, shell=True)
# print(" Finished running: " + commandline)
# commandline = sys.executable + " -m py3.pkg2.foo"
# subprocess.check_call(commandline, shell=True)
# print(" Finished running: " + commandline)
# TODO: Commented out code above results in (from python-3.6 onwards):
# RuntimeWarning: 'py3.pkg2.bar' found in sys.modules after import of package 'py3.pkg2', but prior to execution of 'py3.pkg2.bar'; this may result in unpredictable behaviour

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,15 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2 import py2.pkg2
print " Finished importing py2.pkg2" print " Finished importing py2.pkg2"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2 import py3.pkg2
print " Finished importing py3.pkg2" print " Finished importing py3.pkg2"
# commandline = sys.executable + " -m py3.pkg2.bar"
# subprocess.check_call(commandline, shell=True)
# print(" Finished running: " + commandline)
# TODO: Commented out code above results in (from python-3.6 onwards):
# RuntimeWarning: 'py3.pkg2.bar' found in sys.modules after import of package 'py3.pkg2', but prior to execution of 'py3.pkg2.bar'; this may result in unpredictable behaviour

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,15 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2 import py2.pkg2
print " Finished importing py2.pkg2" print " Finished importing py2.pkg2"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2 import py3.pkg2
print " Finished importing py3.pkg2" print " Finished importing py3.pkg2"
# commandline = sys.executable + " -m py3.pkg2.bar"
# subprocess.check_call(commandline, shell=True)
# print(" Finished running: " + commandline)
# TODO: Commented out code above results in (from python-3.6 onwards):
# RuntimeWarning: 'py3.pkg2.bar' found in sys.modules after import of package 'py3.pkg2', but prior to execution of 'py3.pkg2.bar'; this may result in unpredictable behaviour

View file

@ -1,6 +1,17 @@
import os
import subprocess
import sys
print(" Starting subtest " + os.path.basename(__file__))
# import robin as a module in the global namespace # import robin as a module in the global namespace
import robin import robin
print(" Finished importing robin")
if not(robin.run() == "AWAY!"): if not(robin.run() == "AWAY!"):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m robin"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,8 +1,18 @@
import os
import subprocess
import sys import sys
print(" Starting subtest " + os.path.basename(__file__))
# Package brave found under one path # Package brave found under one path
sys.path.insert(0, 'path1') sys.path.insert(0, 'path1')
from brave import robin from brave import robin
print(" Finished from brave import robin")
if not(robin.run() == "AWAY!"): if not(robin.run() == "AWAY!"):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m brave.robin"
subprocess.check_call(commandline, shell=True, env = {"PYTHONPATH": "path1"})
print(" Finished running: " + commandline)

View file

@ -1,7 +1,8 @@
# These examples rely on namespace packages. Don't # These examples rely on namespace packages. Don't
# run them for old python interpreters. # run them for old python interpreters.
import sys
import os.path import os.path
import subprocess
import sys
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
print "Testing " + testname + " - namespace packages" print "Testing " + testname + " - namespace packages"

View file

@ -1,10 +1,20 @@
import os
import subprocess
import sys import sys
print(" Starting subtest " + os.path.basename(__file__))
# Package brave split into two paths. # Package brave split into two paths.
# path2/brave/robin.py and path3/brave/_robin.so # path2/brave/robin.py and path3/brave/_robin.so
sys.path.insert(0, 'path2') sys.path.insert(0, 'path2')
sys.path.insert(0, 'path3') sys.path.insert(0, 'path3')
from brave import robin from brave import robin
print(" Finished from brave import robin")
if not(robin.run() == "AWAY!"): if not(robin.run() == "AWAY!"):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m brave.robin"
subprocess.check_call(commandline, shell=True, env = {"PYTHONPATH": "path2:path3"})
print(" Finished running: " + commandline)

View file

@ -1,10 +1,20 @@
import os
import subprocess
import sys import sys
print(" Starting subtest " + os.path.basename(__file__))
# Package brave split into two paths. # Package brave split into two paths.
# brave/robin.py (in path4.zip) and path3/brave/_robin.so # brave/robin.py (in path4.zip) and path3/brave/_robin.so
sys.path.insert(0, 'path4.zip') sys.path.insert(0, 'path4.zip')
sys.path.insert(0, 'path3') sys.path.insert(0, 'path3')
from brave import robin from brave import robin
print(" Finished from brave import robin")
if not(robin.run() == "AWAY!"): if not(robin.run() == "AWAY!"):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m brave.robin"
subprocess.check_call(commandline, shell=True, env = {"PYTHONPATH": "path3:path4.zip"})
print(" Finished running: " + commandline)

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,18 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2.bar import py2.pkg2.bar
print " Finished importing py2.pkg2.bar" print " Finished importing py2.pkg2.bar"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py2.pkg2.pkg3.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2.bar import py3.pkg2.bar
print " Finished importing py3.pkg2.bar" print " Finished importing py3.pkg2.bar"
commandline = sys.executable + " -m py3.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py3.pkg2.pkg3.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,18 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2.bar import py2.pkg2.bar
print " Finished importing py2.pkg2.bar" print " Finished importing py2.pkg2.bar"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py2.pkg2.pkg3.pkg4.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2.bar import py3.pkg2.bar
print " Finished importing py3.pkg2.bar" print " Finished importing py3.pkg2.bar"
commandline = sys.executable + " -m py3.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py3.pkg2.pkg3.pkg4.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,5 +1,6 @@
import sys
import os.path import os.path
import subprocess
import sys
# Test import of modules content from within __init__.py # Test import of modules content from within __init__.py
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -12,6 +13,18 @@ if sys.version_info < (2, 5):
if sys.version_info < (3, 0): if sys.version_info < (3, 0):
import py2.pkg2.bar import py2.pkg2.bar
print " Finished importing py2.pkg2.bar" print " Finished importing py2.pkg2.bar"
commandline = sys.executable + " -m py2.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py2.pkg2.pkg3.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
else: else:
import py3.pkg2.bar import py3.pkg2.bar
print " Finished importing py3.pkg2.bar" print " Finished importing py3.pkg2.bar"
commandline = sys.executable + " -m py3.pkg2.bar"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)
commandline = sys.executable + " -m py3.pkg2.pkg3.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,4 +1,6 @@
import os.path import os.path
import subprocess
import sys
# Test import of same modules from different packages # Test import of same modules from different packages
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
@ -13,3 +15,7 @@ classname = str(type(var2))
if classname.find("pkg2.foo.Pkg2_Foo") == -1: if classname.find("pkg2.foo.Pkg2_Foo") == -1:
raise RuntimeError("failed type checking: " + classname) raise RuntimeError("failed type checking: " + classname)
print " Successfully created object pkg2.foo.Pkg2_Foo" print " Successfully created object pkg2.foo.Pkg2_Foo"
commandline = sys.executable + " -m pkg2.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,4 +1,6 @@
import os.path import os.path
import subprocess
import sys
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
print "Testing " + testname + " - %module(package=...) + python 'import' in __init__.py" print "Testing " + testname + " - %module(package=...) + python 'import' in __init__.py"
@ -12,3 +14,7 @@ classname = str(type(var2))
if classname.find("pkg1.pkg2.foo.Pkg2_Foo") == -1: if classname.find("pkg1.pkg2.foo.Pkg2_Foo") == -1:
raise RuntimeError("failed type checking: " + classname) raise RuntimeError("failed type checking: " + classname)
print " Successfully created object pkg1.pkg2.foo.Pkg2_Foo" print " Successfully created object pkg1.pkg2.foo.Pkg2_Foo"
commandline = sys.executable + " -m pkg1.pkg2.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,4 +1,6 @@
import os.path import os.path
import subprocess
import sys
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
print "Testing " + testname + " - split modules" print "Testing " + testname + " - split modules"
@ -9,3 +11,7 @@ print " Finished importing pkg1.foo"
if not(pkg1.foo.count() == 3): if not(pkg1.foo.count() == 3):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m pkg1.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -1,4 +1,6 @@
import os.path import os.path
import subprocess
import sys
testname = os.path.basename(os.path.dirname(os.path.abspath(__file__))) testname = os.path.basename(os.path.dirname(os.path.abspath(__file__)))
print "Testing " + testname + " - split modules" print "Testing " + testname + " - split modules"
@ -9,3 +11,7 @@ print " Finished importing pkg1.foo"
if not(pkg1.foo.count() == 3): if not(pkg1.foo.count() == 3):
raise RuntimeError("test failed") raise RuntimeError("test failed")
commandline = sys.executable + " -m pkg1.foo"
subprocess.check_call(commandline, shell=True)
print(" Finished running: " + commandline)

View file

@ -734,7 +734,7 @@ public:
* *
*/ */
Printf(default_import_code, "\n# Pull in all the attributes from %s\n", module); Printf(default_import_code, "\n# Pull in all the attributes from %s\n", module);
Printv(default_import_code, "if __name__.rpartition('.')[0] != '':\n", NULL); Printv(default_import_code, "if __package__ or __name__.rpartition('.')[0]:\n", NULL);
Printv(default_import_code, tab4, "try:\n", NULL); Printv(default_import_code, tab4, "try:\n", NULL);
Printf(default_import_code, tab4 tab4 "from .%s import *\n", module); Printf(default_import_code, tab4 tab4 "from .%s import *\n", module);
Printv(default_import_code, tab4 "except ImportError:\n", NULL); Printv(default_import_code, tab4 "except ImportError:\n", NULL);