Skip to content

Improve/clarify importlib recipe for loading code from a source file path #121607

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

Closed
brettcannon opened this issue Jul 10, 2024 · 3 comments
Closed
Labels
docs Documentation in the Doc dir topic-importlib

Comments

@brettcannon
Copy link
Member

brettcannon commented Jul 10, 2024

          > https://docs.python.org/3/library/importlib.html#importing-a-source-file-directly 

Ahh -- thanks -- I hadn't found that.

That looks to me like it's the non-deprecated way to do:

module = SourceFileLoader(name, path).load_module()

Is that correct -- will it do the same thing?

In which case, I propose that that recipe be added to importlib as a utility function along the lines of:

def load_module_from_path(name, path):
    """
    load a module from a file on disk

    :param name: name of the module
    :type name: str

    :param path: path to the file
    :type path: PathLike

    :returns: instantiated module object

    Note: The module is also added to sys.modules, and will behave the same as though
              the file were on sys.path and imported the usual way.
    """
    import os  # import here, so that it only gets imported if needed.
    path = os.fspath(path)

    spec = importlib.util.spec_from_file_location(name, path)
    module = importlib.util.module_from_spec(spec)
    sys.modules[name] = module
    spec.loader.exec_module(module)

    return module

I understand that it was a deliberate decision to put the recipe in the docs, rather than a utility function, though unless it's really something that is "not recommended" (in which case perhaps it should say so in the docs) -- then this is just complex enough that a utility function is called for -- particularly since SourceFileLoader(name, path).load_module() (now deprecated?) is advice readily found on the internet.

Does this need another issue or PR?

Meanwhile, for the original issue:

I suggest that checking for __fspath__ be added to the: FileLoader.__init__() and perhaps a couple other places where file paths are initialized -- that is the "outer" parts of the importlib API.

Though for my use-case the proposed utility function would solve the problem at hand.

Originally posted by @ChrisBarker-NOAA in #87005 (comment)

Linked PRs

@ZeroIntensity
Copy link
Member

If we go the route of adding a new function to importlib.util, it might be worthwhile to assume the module name based on the path.

Any time I've seen someone use this snippet (or something similar) for source file importing, they've always used the trailing file name, minus the .py suffix, as the module name. Would eliminate some of the redundancy to do this automatically. IIRC, I've done this in the past with pathlib: module_name = Path("/path/to/module.py").stem

@brettcannon
Copy link
Member Author

If we go the route of adding a new function to importlib.util

We're not for various reasons. If people want a function I think it should come from PyPI.

brettcannon added a commit that referenced this issue Sep 13, 2024
miss-islington pushed a commit to miss-islington/cpython that referenced this issue Sep 13, 2024
…ar (pythonGH-121519)

(cherry picked from commit 3880917)

Co-authored-by: Chris Barker <[email protected]>
Co-authored-by: Brett Cannon <[email protected]>
Co-authored-by: Peter Bierma <[email protected]>
miss-islington pushed a commit to miss-islington/cpython that referenced this issue Sep 13, 2024
…ar (pythonGH-121519)

(cherry picked from commit 3880917)

Co-authored-by: Chris Barker <[email protected]>
Co-authored-by: Brett Cannon <[email protected]>
Co-authored-by: Peter Bierma <[email protected]>
@picnixz picnixz added stdlib Python modules in the Lib dir docs Documentation in the Doc dir topic-importlib and removed stdlib Python modules in the Lib dir labels Sep 13, 2024
Yhg1s pushed a commit that referenced this issue Sep 24, 2024
…ear (GH-121519) (#124080)

gh-121607: Edited source file import recipe to make it more clear (GH-121519)
(cherry picked from commit 3880917)

Co-authored-by: Chris Barker <[email protected]>
Co-authored-by: Brett Cannon <[email protected]>
Co-authored-by: Peter Bierma <[email protected]>
brettcannon added a commit that referenced this issue Oct 10, 2024
…ear (GH-121519) (GH-124081)

gh-121607: Edited source file import recipe to make it more clear (GH-121519)
(cherry picked from commit 3880917)

Co-authored-by: Chris Barker <[email protected]>
Co-authored-by: Brett Cannon <[email protected]>
Co-authored-by: Peter Bierma <[email protected]>
@brettcannon
Copy link
Member Author

All backports are merged, so I'm closing this. Thanks, everyone!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
docs Documentation in the Doc dir topic-importlib
Projects
None yet
Development

No branches or pull requests

3 participants