saltstack / salt

Software to automate the management and configuration of any infrastructure or application at scale. Get access to the Salt software package repository here:
https://repo.saltproject.io/
Apache License 2.0
14.11k stars 5.47k forks source link

[BUG] ext_pillar stack _process_stack_cfg does not catch yaml parse errors, making location of yaml parse error unknown #62748

Open Noah-Huppert opened 2 years ago

Noah-Huppert commented 2 years ago

Description The "stack" external pillar calls a function named _process_stack_cfg. This function then calls the Salt YAML safe load function for each pillar file which needs to be parsed. However the _process_stack_cfg function does not catch this error. So the exception bubbles all the way up to salt/pillar/__init__.py#ext_pillar() leaving the user completely confused about where the YAML parsing error actually occurred.

This type of ambiguous YAML parse error "but from where?" sort of issue plagues Salt stack. This is just one case of it.

Setup (Please provide relevant configs and/or SLS files (be sure to remove sensitive info. There is no general set-up of Salt.)

Please be as specific as possible and give set-up details.

Running in Minion mode.

Steps to Reproduce the behavior

With /etc/salt/minion containing default values except:

ext_pillar:
   - stack:
      pillar:environment:
        base:
          - /srv/pillar/base/pillar-stack.cfg
          - /srv/pillar/base-secret/pillar-stack.cfg
        work:
          - /srv/pillar/base/pillar-stack.cfg
          - /srv/pillar/base-secret/pillar-stack.cfg
          - /srv/pillar/work/pillar-stack.cfg
        wsl:
          - /srv/pillar/base/pillar-stack.cfg
          - /srv/pillar/base-secret/pillar-stack.cfg
          - /srv/pillar/wsl/pillar-stack.cfg

Then in all of the /srv/pillar/*/pillar-stack.cfg files place the text */*. Next to this file place directories with init.sls files inside of them. Make one of these init.sls files have a YAML syntax error and watch as you get the extremely ambiguous error:

/usr/lib/python3.10/site-packages/_distutils_hack/__init__.py:33: UserWarning: Setuptools is replacing distutils.
  warnings.warn("Setuptools is replacing distutils.")
[ERROR   ] Exception caught loading ext_pillar 'stack':
  File "/usr/lib/python3.10/site-packages/salt/pillar/__init__.py", line 1188, in ext_pillar
    ext = self._external_pillar_data(pillar, val, key)
  File "/usr/lib/python3.10/site-packages/salt/pillar/__init__.py", line 1108, in _external_pillar_data
    ext = self.ext_pillars[key](self.minion_id, pillar, **val)
  File "/usr/lib/python3.10/site-packages/salt/loader/lazy.py", line 149, in __call__
    return self.loader.run(run_func, *args, **kwargs)
  File "/usr/lib/python3.10/site-packages/salt/loader/lazy.py", line 1228, in run
    return self._last_context.run(self._run_as, _func_or_method, *args, **kwargs)
  File "/usr/lib/python3.10/site-packages/salt/loader/lazy.py", line 1243, in _run_as
    return _func_or_method(*args, **kwargs)
  File "/usr/lib/python3.10/site-packages/salt/pillar/stack.py", line 414, in ext_pillar
    stack = _process_stack_cfg(cfg, stack, minion_id, pillar)
  File "/usr/lib/python3.10/site-packages/salt/pillar/stack.py", line 462, in _process_stack_cfg
    raise e
  File "/usr/lib/python3.10/site-packages/salt/pillar/stack.py", line 458, in _process_stack_cfg
    obj = salt.utils.yaml.safe_load(
  File "/usr/lib/python3.10/site-packages/salt/utils/yamlloader.py", line 167, in safe_load
    return yaml.load(stream, Loader=Loader)
  File "/usr/lib/python3.10/site-packages/yaml/__init__.py", line 81, in load
    return loader.get_single_data()
  File "/usr/lib/python3.10/site-packages/yaml/constructor.py", line 49, in get_single_data
    node = self.get_single_node()
  File "yaml/_yaml.pyx", line 673, in yaml._yaml.CParser.get_single_node
  File "yaml/_yaml.pyx", line 687, in yaml._yaml.CParser._compose_document
  File "yaml/_yaml.pyx", line 731, in yaml._yaml.CParser._compose_node
  File "yaml/_yaml.pyx", line 847, in yaml._yaml.CParser._compose_mapping_node
  File "yaml/_yaml.pyx", line 860, in yaml._yaml.CParser._parse_next_event

[CRITICAL] Pillar render error: Failed to load ext_pillar stack: mapping values are not allowed in this context
  in "<unicode string>", line 70, column 38
local:
    Data failed to compile:
----------
    Pillar failed to render with the following messages:
----------
    Failed to load ext_pillar stack: mapping values are not allowed in this context
  in "<unicode string>", line 70, column 38

As you can see, the user really isn't given any information about where the YAML error occurred. In fact to the user it may seem like the error came from their /etc/salt/minion file, since ext_pillar stack is mentioned.

Expected behavior

If Salt fails to parse a YAML file it gives the path to that file.

Versions Report

salt --versions-report (Provided by running salt --versions-report. Please also mention any differences in master/minion versions.) ```yaml Salt Version: Salt: 3005 Dependency Versions: cffi: Not Installed cherrypy: Not Installed dateutil: Not Installed docker-py: Not Installed gitdb: Not Installed gitpython: Not Installed Jinja2: 3.0.3 libgit2: Not Installed M2Crypto: 0.38.0 Mako: 1.1.3 msgpack: 1.0.4 msgpack-pure: Not Installed mysql-python: Not Installed pycparser: Not Installed pycrypto: Not Installed pycryptodome: 3.15.0 pygit2: Not Installed Python: 3.10.5 (main, Jun 8 2022, 02:00:39) [GCC 10.2.1 20201203] python-gnupg: Not Installed PyYAML: 6.0 PyZMQ: 23.2.0 smmap: Not Installed timelib: Not Installed Tornado: 4.5.3 ZMQ: 4.3.4 System Versions: dist: void rolling void locale: utf-8 machine: x86_64 release: 5.18.11_1 system: Linux version: Void rolling void ```
johnnybubonic commented 2 years ago

https://github.com/saltstack/salt/blob/master/salt/pillar/stack.py#L424

Noah-Huppert commented 2 years ago

https://github.com/saltstack/salt/blob/master/salt/pillar/stack.py#L424

🤦‍♂️, Missed that...

benfiedler commented 1 year ago

Troubleshooting a problem with ext_pillar encountered while trying to upgrade my salt master, I encountered this bug as well. For what it's worth, it looks like has been fixed in 3006(.2?)

3005.2 master (onedir) output from # salt-run pillar.show_pillar:

_errors:
    - Failed to load ext_pillar stack: while scanning an alias
        in "<unicode string>", line 7, column 5
      did not find expected alphabetic or numeric character
        in "<unicode string>", line 7, column 6

3006.2 master (onedir) output from # salt-run pillar.show_pillar:

_errors:
    - Failed to load ext_pillar stack: Stack pillar yaml parsing error in /srv/pillar/mydev/hostsfile/common.sls:
      while scanning an alias
        in "<unicode string>", line 7, column 5:
              *: None
              ^
      expected alphabetic or numeric character, but found ':'
        in "<unicode string>", line 7, column 6:
              *: None
               ^

Now, I just need to figure out why the exact same ext_pillar files that load fine in 3005.1 'classic' salt master produce this error in 3005+ onedir....