Is there a way I could render an sls file that resides in the pillar? Something more or less the equivalent of state.show_sls?
Take a look at pillar module. You can check rendered pillar (or rather resulting data) by calling e.g.
$ salt '*' pillar.items
Or some particular part of the pillar e.g. elasticsearch:
$ salt '*' pillar.get elasticsearch
See also the slsutil.renderer module:
salt '*' slsutil.renderer salt://path/to/file
salt '*' slsutil.renderer /path/to/file
salt '*' slsutil.renderer /path/to/file.jinja 'jinja'
salt '*' slsutil.renderer /path/to/file.sls 'jinja|yaml'
salt '*' slsutil.renderer string='Inline template! {{ saltenv }}'
salt '*' slsutil.renderer string='Hello, {{ name }}.' name='world'
For pillar sls files it may only work on the saltmaster. Example:
salt-call --local slsutil.renderer /srv/nacl/pillar/myservice/init.sls 'yamlex'
Related
I am configuring a local Salt setup and I have hit a bit of a wall.
My setup is:
CentOS: Red Hat Enterprise Linux Server release 7.7 (Maipo)
Salt: salt 3000.1
I have a very basic configuration with nothing changed from default in the Master or Minion config.
My directory structure is as follows:
/srv/salt/apache/init.sls
/srv/salt/uptodate/common.sls
If I run the following:
salt '*' state.sls apache Test=true
It correctly applies the sls files inside the apache folder.
If I run:
salt '*' state.sls uptodate Test=true
It returns:
minion:
Data failed to compile:
----------
No matching sls found for 'uptodate' in env 'base'
I have no top.sls files configured and if I move common.sls into the apache directory it also does not get applied.
Does anyone have any idea what is going wrong here?
The init.sls can be compared to an index.html file on a webserver.
If you want to apply a statefile other than a init.sls you need to add the name of the state file.
This should work for you:
salt '*' state.sls uptodate.common test=True
Is there a way to exclude minions from being targeted even if I run salt '*' state.apply on CLI?
Ideally the exclusion should be declared somewhere in top.sls
From CLI, you can exclude minion as follows,
salt -C 'not minion-id' test.ping
Above pattern is available since version 2015.8.0. If you are using older version then,
salt -C '* and not minion-id' test.ping
Please read more about Compound matchers here.
You want to use compound matching. Targetting all the minions for the webserver states except minion_id_1 can be done like this.
base:
'not minion_id_1':
- match: compound
- webserver
Documentation on compound matching can be found here: docs.saltstack.com/en/latest/topics/targeting/compound.html
Is there a command that I can use to know what static configuration file does my salt-call is using?
Probably enabling the LOG_LEVEL could help, for example within the minion you could use:
salt-call -l trace state.highstate
or to be more verbose:
salt-call -l debug state.highstate
You also have:
salt-call state.show_highstate
or
salt-call state.show_lowstate
Check the COMPILER BASICS docs to get more info about it
Is it possible to target a specific set of minions when applying a state? Instead of doing:
salt '*' state.sls mystate.sls
I want to do:
salt '[key1,key2,...]' state.sls mystate.sls
Of course, just use -L
salt -L 'key1,key2,key3,...' state.sls mystate.sls
http://docs.saltstack.com/en/latest/topics/targeting/globbing.html#lists
I need to execute a script on another minion. The best solution seems to be Peer Publishing, but the only documentation I have been able to find only shows how to do it via CLI.
How can I define the following in a module?
salt-call system.example.com publish.publish '*' cmd.run './script_to_run'
You want the salt.client.Caller() API.
#!/usr/bin/env python
import salt.client
salt_call = salt.client.Caller()
salt_call.function('publish.publish', 'web001',
'cmd.run', 'logger "publish.publish success"')
You have to run the above as the salt user (usually root).
Then scoot over to web001 and confirm the message is in /var/log/syslog. Worked for me.
The syntax for the .sls file:
salt-call publish.publish \* cmd.run 'cd /*directory* && ./script_to_run.sh:
cmd.run
Alternative syntax:
execute script on other minion:
cmd.run
- name: salt-call publish.publish \* cmd.run 'cd /*directory* && ./script_to_run.sh
What I specifically did (I needed to execute a command, but only if a published command executed successfully. Which command to publish depends on the role of the minion):
execute script:
cmd.run:
- name: *some shell command here*
- cwd: /*directory*
- require:
- file: *some file here*
{% if 'role_1' in grains['roles'] -%}
- onlyif: salt-call publish.publish \* cmd.run 'cd /*other_directory* && ./script_to_run_A.sh'
{% elif 'role_2' in grains['roles'] -%}
- onlyif: salt-call publish.publish \* cmd.run 'cd /*other_directory* && ./script_to_run_B.sh'
{% endif %}
Remember to enable peer communication in /etc/salt/master under the section 'Peer Publish Settings':
peer:
.*:
- .*
This configuration is not secure, since it enables all minions to execute all commands on fellow minions, but I have not figured out the correct syntax to select minions based on their role yet.
Another note is that it probably would be better to create a custom command containing the cmd.run and then enable only that, since enabling all nodes to execute arbitrary scripts on each other is not secure.
The essence of this answer is the same as Dan Garthwaite's, but what I needed was a solution for a .sls file.