This is related to how the Python import system and module search paths work.
In the script version:
import os
os.chdir("/app/my-favorite-module")
from my_favorite_module.foo import Bar
os.chdir("/app")
When you change the current working directory using os.chdir
, it only affects the script's current process and its child processes (if any). When the script is importing the module my_favorite_module.foo
, Python searches for the module in the standard module search paths. Since you changed the working directory, the current directory is /app/my-favorite-module
, and Python won't look in this directory for modules. Instead, it will look in the standard module paths, and thus, it will not find my_favorite_module.foo
.
On the other hand, in the Python REPL version:
import os; os.chdir("/app/my-favorite-module")
from my_favorite_module.foo import Bar
os.chdir("/app")
The Python REPL runs interactively, and when you change the current working directory using os.chdir
in the REPL, it affects the Python process running the REPL itself. As a result, when you then import my_favorite_module.foo
, Python will search for the module in the current directory (/app/my-favorite-module
), find it, and import it successfully.
As you've mentioned, using sys.path
is a proper workaround for this situation. By adding the directory to sys.path
, you are essentially telling Python to look in that directory when searching for modules, and this works consistently both in scripts and the Python REPL.