UNDERSTANDING JINJA
jinja是sls文件是默认的模板语言
JINJA IN STATES
在state文件被运行之前需要将文件中jinja模板语言部分处理掉,处理完之后再转化成YAML格式,最后变成python数据结构。
jinja模板语法通常被用于在state文件中使用控制结构,如if条件,for循环等,可以达到消除冗余数据的效果。
在sls文件中使用jinja模板
示例:
{% if grains['os'] != 'FreeBSD' %}
tcsh:
pkg:
- installed
{% endif %}
motd:
file.managed:
{% if grains['os'] == 'FreeBSD' %}
- name: /etc/motd
{% elif grains['os'] == 'Debian' %}
- name: /etc/motd.tail
{% endif %}
- source: salt://motd
View Code 解析:
依据minion端的os系统来部署不同的配置文件,但是上面的例子在jinja模板使用的代码可能过于冗余,代码内容的用途过于单一,它的作用仅能体现在一个文件的传输模块中。
所以为了优化这种情况,name应该使用pillar变量,将这种判断逻辑包含到pillar环境里面,又或者将这种逻辑放在一个基础jinja模板中被继承,实现解耦,便于后续的变更。
jinja循环控制结构的示例:
{% set motd = ['/etc/motd'] %}
{% if grains['os'] == 'Debian' %}
{% set motd = ['/etc/motd.tail', '/var/run/motd'] %}
{% endif %}
{% for motdfile in motd %}
{{ motdfile }}:
file.managed:
- source: salt://motd
{% endfor %}
View Code 在filter_by里面应用grains变量,相当于把逻辑放在另一个模板中了,可以被其他sls文件中的模板包引用
{% set auditd = salt['grains.filter_by']({
'RedHat': { 'package': 'audit' },
'Debian': { 'package': 'auditd' },
}) %}
View Code 依据minion端变量auditd的值来指定包名
INCLUDE AND IMPORT
包含和导入可用于sls文件只共享通用的可配置的内容
示例:
{% from 'lib.sls' import test %}
{% from 'lib.sls' import test with context %}
View Code
INCLUDING CONTEXT DURING INCLUDE/IMPORT
{% import 'openssl/vars.sls' as ssl with context %}
#使用with context将变量的上下文也包含进来
MACROS
宏定义,宏的使用有利于消除代码的冗余
示例:
# init.sls
{% from 'lib.sls' import pythonpkg with context %}
python-virtualenv:
pkg.installed:
- name: {{ pythonpkg('virtualenv') }}
python-fabric:
pkg.installed:
- name: {{ pythonpkg('fabric') }}
View Code 使用了一个include包含另一个sls文件
# lib.sls
{% macro pythonpkg(pkg) -%}
{%- if grains['os'] == 'FreeBSD' -%}
py27-{{ pkg }}
{%- elif grains['os'] == 'Debian' -%}
python-{{ pkg }}
{%- endif -%}
{%- endmacro %}
View Code 定义了一个宏pythonpkg,用于做变量替换,利用一个预设的规则对引用的变量做逻辑处理
TEMPLATE INHERITANCE
模板继承,参考jinja的模板语言中的继承逻辑和使用逻辑
FILTERS
过滤器
strftime
将与时间有关的对象转化成基于时间的字符串,需要系统timelib库的支持
示例:
{% set curtime = None | strftime() %}
{{ "2002/12/25"|strftime("%y") }}
{{ "1040814000"|strftime("%Y-%m-%d") }}
{{ datetime|strftime("%u") }}
{{ "tomorrow"|strftime }}
View Code yaml_encode
用于对一些需要特殊的字符做yaml转换
JINJA IN FILES
jinja在文件中的使用
示例:
# redis.sls
/etc/redis/redis.conf:
file.managed:
- source: salt://redis.conf
- template: jinja
- context:
bind: 127.0.0.1
# lib.sls
{% set port = 6379 %}
# redis.conf
{% from 'lib.sls' import port with context %}
port {{ port }}
bind {{ bind }}
View Code 文件中的内容可以关联到外部模板文件中预设好的逻辑中,实现灵活配置。
ESCAPING JINJA
jinja语法转义
比较简单的转义:
{{ '{{' }}
成块的转义:
{% raw %}
some text that contains jinja characters that need to be escaped
{% endraw %}
View Code
CALLING SALT FUNCTIONS
jinja中可以使用salt函数,可以的函数列表可以参考以下链接:
两个等价函数的使用示例:
{{ salt['cmd.run']('whoami') }}
{{ salt.cmd.run('whoami') }}
DEBUGGING
show_full_context可用于输出当前上下文的变量值,便于debug分析排查问题
示例:
Context is: {{ show_full_context() }}
CUSTOM EXECUTION MODULES
如何使用自定义的模块
{{ salt['my_custom_module.my_custom_function']() }}
关于编写自有执行模块参考以下两个:
(1)一个执行模块在jinja语法中如何被执行
https://docs.saltstack.com/en/2016.11/topics/tutorials/jinja_to_execution_module.html#tutorial-jinja-to-execution-module
(2)如何写一个执行模块
https://docs.saltstack.com/en/2016.11/ref/modules/index.html#writing-execution-modules
关于执行模块后续再深究。
思考:宏的定义和之前的变量定义逻辑有何不同?
宏定义能实现一组变量特定逻辑的处理,如果将多个变量定义放在普通的模板变量定义逻辑里面,一千个变量就需要定义一千次,而宏只需要定义一个规则,调用的时候自动
应用即可。
运维网声明
1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网 享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com