pyinvoke / invoke

Pythonic task management & command execution.
http://pyinvoke.org
BSD 2-Clause "Simplified" License
4.31k stars 365 forks source link

Importing Python modules from a scripts directory beside the tasks directory #994

Open RobMeades opened 1 month ago

RobMeades commented 1 month ago

We use invoke in a directory structure which looks like this:

-- scripts
   -- __init__.py
   -- useful_script_1.py
   -- useful_script_2.py
   -- ...
-- tasks
   -- __init__.py
   -- task_1.py
   -- task_2.py

In our invoke tasks we import stuff from the scripts directory like this:

from scripts import useful_script_1

Some time between version 2.0.0 of invoke and the latest version something changed in invoke which stopped this working; we get the error:

ImportError: cannot import name 'useful_script_1' from 'scripts' (unknown location)

We have made this work up to now by sticking with version 2.0.0 of invoke but it would be better to adopt the latest version: what is the simplest way to make script-import work from an invoke task again?

The exact error with backtrace is:

Traceback (most recent call last):
  File "c:\program files\python39\lib\runpy.py", line 197, in _run_module_as_main
    return _run_code(code, main_globals, None,
  File "c:\program files\python39\lib\runpy.py", line 87, in _run_code
    exec(code, run_globals)
  File "C:\Program Files\Python39\Scripts\inv.exe\__main__.py", line 7, in <module>
  File "c:\program files\python39\lib\site-packages\invoke\program.py", line 387, in run
    self.parse_collection()
  File "c:\program files\python39\lib\site-packages\invoke\program.py", line 479, in parse_collection
    self.load_collection()
  File "c:\program files\python39\lib\site-packages\invoke\program.py", line 716, in load_collection
    module, parent = loader.load(coll_name)
  File "c:\program files\python39\lib\site-packages\invoke\loader.py", line 91, in load
    spec.loader.exec_module(module)
  File "<frozen importlib._bootstrap_external>", line 855, in exec_module
  File "<frozen importlib._bootstrap>", line 228, in _call_with_frames_removed
  File "c:\projects\my_project\tasks\__init__.py", line 2, in <module>
    from scripts import useful_script_1
ImportError: cannot import name 'useful_script_1' from 'scripts' (unknown location)