是否可以在节点然后将其传播到 erb 模板?
例子:
node basenode {
$myvar = "bar" # default
include myclass
}
node mynode extends basenode {
$myvar = "foo"
}
class myclass {
file { "/root/myfile":
content => template("myclass/mytemplate.erb")
ensure => present,
}
}
来源我的模板.erb:
myvar has value: <%= myvar %>
我知道我的例子可能很复杂。但我试图在(几乎)所有节点上传播文件,并希望根据以下情况更改其内容:节点请求文件。$myvar = "bar"
当节点不覆盖其值时,该语句应为默认语句。
有办法解决我的问题吗?我正在使用 Puppet0.24.5
编辑:这里的问题可能是变量继承顺序。这$myvar变量不会有富价值我的节点节点。这里的解决方案是包括我的课直接我的节点。但我真的不想这样做。有没有选项可以覆盖类变量值后该课程已被收录?
答案1
Puppet 节点继承是不是与大多数其他编程语言中的继承相同。包含的类被评估立即当子节点被评估时。并且父节点被评估时在那之后。因此我的例子永远不会奏效。如果你想知道推荐的解决方案,请阅读木偶——常见的误解。我按照这种方法做了,而且有效。
尽管我不得不承认我现在非常失望,因为复杂的 puppet 语法可能会让初学者感到困惑。
答案2
其他答案已经指出了范围问题。您可能想要做的是仅将基节点用于变量定义,并将实际逻辑(包括基类定义)分离到所有节点都包含的单独类中。这样可以按照您想要的方式保留范围,并且只会在所有节点定义中添加一行额外的代码。
node basenode {
$myvar = "bar" # default
}
node mynode extends basenode {
$myvar = "foo"
include baseclass
}
class baseclass {
include myclass
}
class myclass {
file { "/root/myfile":
content => template("myclass/mytemplate.erb"),
ensure => present
}
}
答案3
我不会在 basenode 中声明默认值,而是在模板本身中声明默认值。由于 ERB 主要基于 ruby,因此您可以使用一些相当广泛的逻辑。下面是我用于管理 snort 配置文件的模板中的一个示例。
var DNS_SERVERS <% if has_variable?("dns_servers") then %>[<%= dns_servers.flatten.join(',') %>]<% else %>$HOME_NET<% end %>
在这种情况下,我使用一个数组,如果存在,则将其转换为逗号分隔的列表以供包含。否则,将使用默认的 $HOME_NET。如果我们将其简化为您的示例,我们可以使用:
myvar has value <% if has_variable?("myvar") %><% then %><%= myvar %><% else %>bar<% end %>
再次,如果变量myvar
已设置,则将展开该变量,否则将打印字符串“bar”。这样,您myvar
可以在节点定义中毫无顾忌地设置或不设置变量。