Skip to content

gh-92913: Clarify change to init config module_search_paths[_set] fields #92980

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

Merged
merged 3 commits into from
May 19, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 16 additions & 4 deletions Doc/c-api/init_config.rst
Original file line number Diff line number Diff line change
Expand Up @@ -1289,7 +1289,11 @@ Example setting the program name::
}

More complete example modifying the default configuration, read the
configuration, and then override some parameters::
configuration, and then override some parameters. Note that since
3.11, many parameters are not calculated until initialization, and
so values cannot be read from the configuration structure. Any values
set before initialize is called will be left unchanged by
initialization::

PyStatus init_python(const char *program_name)
{
Expand All @@ -1314,7 +1318,15 @@ configuration, and then override some parameters::
goto done;
}

/* Append our custom search path to sys.path */
/* Specify sys.path explicitly */
/* To calculate the default and then modify, finish initialization and
then use PySys_GetObject("path") to get the list. */
condig.module_search_paths_set = 1
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Two typos in this line: condig, and missing a trailing semicolon.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks. I was zoned out of my mind with fatigue/allergies when I did this PR, so I'm impressed this was the worst of it (it wasn't the worst of my whole day, unfortunately)

status = PyWideStringList_Append(&config.module_search_paths,
L"/path/to/stdlib");
if (PyStatus_Exception(status)) {
goto done;
}
status = PyWideStringList_Append(&config.module_search_paths,
L"/path/to/more/modules");
if (PyStatus_Exception(status)) {
Expand Down Expand Up @@ -1417,8 +1429,8 @@ It is possible to completely ignore the function calculating the default
path configuration by setting explicitly all path configuration output
fields listed above. A string is considered as set even if it is non-empty.
``module_search_paths`` is considered as set if
``module_search_paths_set`` is set to ``1``. In this case, path
configuration input fields are ignored as well.
``module_search_paths_set`` is set to ``1``. In this case,
``module_search_paths`` will be used without modification.

Set :c:member:`~PyConfig.pathconfig_warnings` to ``0`` to suppress warnings when
calculating the path configuration (Unix only, Windows does not log any warning).
Expand Down
15 changes: 15 additions & 0 deletions Doc/whatsnew/3.11.rst
Original file line number Diff line number Diff line change
Expand Up @@ -403,6 +403,11 @@ Other CPython Implementation Changes
instead of prepending them.
(Contributed by Bastian Neuburger in :issue:`44934`.)

* The :c:member:`PyConfig.module_search_paths_set` field must now be set to 1 for
initialization to use :c:member:`PyConfig.module_search_paths` to initialize
:data:`sys.path`. Otherwise, initialization will recalculate the path and replace
any values added to ``module_search_paths``.


New Modules
===========
Expand Down Expand Up @@ -1861,6 +1866,16 @@ Porting to Python 3.11
* Distributors are encouraged to build Python with the optimized Blake2
library `libb2`_.

* The :c:member:`PyConfig.module_search_paths_set` field must now be set to 1 for
initialization to use :c:member:`PyConfig.module_search_paths` to initialize
:data:`sys.path`. Otherwise, initialization will recalculate the path and replace
any values added to ``module_search_paths``.

* :c:func:`PyConfig_Read` no longer calculates the initial search path, and will not
fill any values into :c:member:`PyConfig.module_search_paths`. To calculate default
paths and then modify them, finish initialization and use :c:func:`PySys_GetObject`
to retrieve :data:`sys.path` as a Python list object and modify it directly.


Deprecated
----------
Expand Down
5 changes: 3 additions & 2 deletions Lib/test/_test_embed_set_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -236,10 +236,11 @@ def test_path(self):
module_search_paths=['a', 'b', 'c'])
self.assertEqual(sys.path, ['a', 'b', 'c'])

# Leave sys.path unchanged if module_search_paths_set=0
# sys.path is reset if module_search_paths_set=0
self.set_config(module_search_paths_set=0,
module_search_paths=['new_path'])
self.assertEqual(sys.path, ['a', 'b', 'c'])
self.assertNotEqual(sys.path, ['a', 'b', 'c'])
self.assertNotEqual(sys.path, ['new_path'])

def test_argv(self):
self.set_config(parse_argv=0,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Ensures changes to :c:member:`PyConfig.module_search_paths` are ignored
unless :c:member:`PyConfig.module_search_paths_set` is set
5 changes: 3 additions & 2 deletions Modules/getpath.py
Original file line number Diff line number Diff line change
Expand Up @@ -228,6 +228,7 @@ def search_up(prefix, *landmarks, test=isfile):
use_environment = config.get('use_environment', 1)

pythonpath = config.get('module_search_paths')
pythonpath_was_set = config.get('module_search_paths_set')

real_executable_dir = None
stdlib_dir = None
Expand Down Expand Up @@ -626,8 +627,8 @@ def search_up(prefix, *landmarks, test=isfile):
config['module_search_paths'] = py_setpath.split(DELIM)
config['module_search_paths_set'] = 1

elif not pythonpath:
# If pythonpath was already set, we leave it alone.
elif not pythonpath_was_set:
# If pythonpath was already explicitly set or calculated, we leave it alone.
# This won't matter in normal use, but if an embedded host is trying to
# recalculate paths while running then we do not want to change it.
pythonpath = []
Expand Down