Skip to content

Import only specific values from project_settings into env.

decentral1se requested to merge qris:fix_destroyed_env into develop

Created by: qris

Prevents project_settings from accidentally stomping all over env, for example overwriting env.path with garbage.

On this Mac, the first remotely executed sudo command fails:

[server.compume.qwirx.com:48001] sudo: mkdir -p /var/django/boxcastle
[server.compume.qwirx.com:48001] out: sudo password:
[server.compume.qwirx.com:48001] out: /bin/bash: module: No such file or directory
[server.compume.qwirx.com:48001] out: 

Fatal error: sudo() received nonzero return code 1 while executing!

Requested: mkdir -p /var/django/boxcastle
Executed: sudo -S -p 'sudo password:'  /bin/bash -l -c "export PATH=\"\$PATH:\"<module 'posixpath' from '/Users/chriswilson/projects/boxcastle/django/website/.ve/lib/python2.7/posixpath.pyc'>\"\" && mkdir -p /var/django/boxcastle"

Aborting.

The PATH statement added to the environment is clearly absurd (some Python internals instead of a list of directories).

Tracing through, I find that env.path is set wrongly here:

> /Users/chriswilson/projects/boxcastle/django/website/.ve/src/dye/dye/fablib.py(17)_setup_paths()
-> for setting in user_settings:
(Pdb) p user_settings
['repo_type', 'host_list', 'requirements_per_env', 'local_vcs_root', 'project_type', 'relative_ve_dir', 'local_requirements_file', 'project_name', 'server_project_home', 'repository', 'default_branch', 'test_cmd', 'webserver', 'user', 'path', 'local_deploy_dir', 'socket', 'use_virtualenv', 'server_home', 'relative_django_dir', 'django_apps', 'relative_django_settings_dir', 'os']
(Pdb) l
 12     
 13     
 14     def _setup_paths(project_settings):
 15         # first merge in variables from project_settings - but ignore __doc__ etc
 16         user_settings = [x for x in vars(project_settings).keys() if not x.startswith('__')]
 17  ->     for setting in user_settings:
 18             env[setting] = vars(project_settings)[setting]
 19     
 20         # allow for project_settings having set up some of these differently
 21         env.setdefault('verbose', False)
 22         env.setdefault('use_sudo', True)
(Pdb) p vars(project_settings)['path']
<module 'posixpath' from '/Users/chriswilson/projects/boxcastle/django/website/.ve/lib/python2.7/posixpath.pyc'>
(Pdb) p vars
<built-in function vars>
(Pdb) p project_settings
<module 'project_settings' from '/Users/chriswilson/projects/boxcastle/deploy/project_settings.pyc'>
(Pdb) p project_settings.path
<module 'posixpath' from '/Users/chriswilson/projects/boxcastle/django/website/.ve/lib/python2.7/posixpath.pyc'>

It seems that fablib.py(17)_setup_paths() tries to import every single variable defined in project_settings.py directly into env. And project_settings.py does this:

from os import path

which means that project_settings.path is defined (it points to the posixpath module that we just imported), and it gets stuffed into env.path.

We could work around this by undefining path at the end of project_settings.py. But I think it makes more sense not to wholesale blat the env with whatever random crap happens to be in the project_settings module.

Either we should be explicit about what we export from it, or simply place a reference to project_settings in env, so that we can access variables from it when needed, without having to constantly be wary of overwriting env with anything we do in project_settings.

This patch imports only certain specific settings from project_settings into env. The rest are accessible via env.project in custom tasks. Lightly tested.

Merge request reports

Loading