Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix subpackage imports and handle duplicate imports #17

Merged
merged 17 commits into from
Jan 17, 2025
2 changes: 1 addition & 1 deletion autoimport/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,4 @@
from autoimport.main import LazyLoader, lazy

__all__ = ("LazyLoader", "lazy")
__version__ = "0.0.1"
__version__ = "0.0.2"
18 changes: 11 additions & 7 deletions autoimport/main.py
Original file line number Diff line number Diff line change
Expand Up @@ -71,21 +71,25 @@ def lazy_import(name, globals=None, locals=None, fromlist=(), level=0):
**{from_item: self._lazy_modules[f"{module_name}.{from_item}"] for from_item in fromlist}
)
else:
if module_name not in self._lazy_modules:
if module_name in globals:
self._lazy_modules[module_name] = globals[module_name]
elif module_name in sys.modules:
self._lazy_modules[module_name] = sys.modules[module_name] # module already loaded in session
elif module_name not in self._lazy_modules:
self._lazy_modules[module_name] = LazyLoader(module_name)

if "." in name: # we need to send loader for parent before subpackage
parts = name.split('.')
parent = ['.'.join(parts[:i]) for i in range(1, len(parts))][0]
return LazyLoader(parent)

return self._lazy_modules[module_name]

builtins.__import__ = lazy_import
return self

def __exit__(self, *args):
"""Restores the original import mechanism and updates sys.modules with any loaded lazy modules."""
builtins.__import__ = self._original_import
# Now that builtins is restored, we can load any modules that need loading
for name, lazy_module in self._lazy_modules.items():
if name in sys.modules: # Update sys.modules to avoid issues with subsequent imports
sys.modules[name] = lazy_module


if __name__ == "__main__":
import time
Expand Down
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ dependencies = []
# Optional dependencies ------------------------------------------------------------------------------------------------
[project.optional-dependencies]
dev = [
"numpy", # for import tests
"numpy", # for tests
]

[project.urls] # Optional
Expand Down
4 changes: 2 additions & 2 deletions tests/test_autoimport.py
Original file line number Diff line number Diff line change
Expand Up @@ -31,12 +31,12 @@ def test_attribute_access(self):
self.assertIsInstance(result, str)

def test_submodule_imports(self):
"""Test nested module imports and functionality."""
"""Test numpy module imports and functionality."""
with lazy():
import numpy.random
random_number = numpy.random.rand()
self.assertLess(random_number, 1.0)

def test_direct_lazyloader(self):
"""Test direct LazyLoader instantiation."""
base64_lazy = LazyLoader("base64")
Expand Down
Loading