Heredocs
Heredocs let you quote strings with more control over escaping, interpolation, and formatting. They’re especially good for long strings with complicated content.
Example
$gitconfig = @("GITCONFIG"/L) [user] name = ${displayname} email = ${email} [color] ui = true [alias] lg = "log --pretty=format:'%C(yellow)%h%C(reset) %s \ %C(cyan)%cr%C(reset) %C(blue)%an%C(reset) %C(green)%d%C(reset)' --graph" wdiff = diff --word-diff=color --ignore-space-at-eol \ --word-diff-regex='[[:alnum:]]+|[^[:space:][:alnum:]]+' [merge] defaultToUpstream = true [push] default = upstream | GITCONFIG file { "${homedir}/.gitconfig": ensure => file, content => $gitconfig, }
Syntax
To write a heredoc, you place a heredoc tag in a line of code. This tag acts as a literal string value, but the content of that string is read from the lines that follow it. The string ends when an end marker is reached.
The general form of a heredoc string is:
heredoc tag @("ENDTEXT"/<X>) | You can use a heredoc tag in Puppet code, anywhere a
string value is accepted. In the above example, the heredoc
tag A heredoc tag starts with Between those characters, the heredoc tag contains end text
(see below) — text that is used to mark the end of the
string. You can optionally surround this end text with
double quotation marks to enable interpolation (see below).
In the above example, the end text is It also optionally contains escape switches (see below),
which start with a slash |
the string This is the text that makes up my string. | The content of the string starts on the next line, and can run over multiple lines. If you specified escape switches in the heredoc tag, the string can contain the enabled escape sequences. In the above example, the string starts with |
end marker | - ENDTEXT | On a line of its own, the end marker consists of:
In the above example, the end marker is |
End text
The heredoc tag contains piece of text called the end text. When Puppet reaches a line that contains only that end text (plus optional formatting control), the string ends.
Both occurrences of the end text must match exactly, with the same capitalization and internal spacing.
End text can be any run of text that doesn’t include line breaks, colons, slashes, or parentheses. It can include spaces, and can be mixed case. The following are all valid end text:
EOT
...end...end...
Verse 8 of The Raven
Enabling interpolation
By default, heredocs do not allow you to interpolate values into the string content. You can enable interpolation by double-quoting the end text in the opening heredoc tag. That is:
An opening tag like
@(EOT)
won’t allow interpolation.An opening tag like
@("EOT")
allows interpolation.
$
) that you want to be literal, not interpolated, you must enable
the literal dollar sign escape switch (/$
) in the heredoc tag: @("EOT"/$)
. Then use the escape
sequence \$
to
specify the literal dollar sign in the string. See the information on enabling
escape sequences, below, for more details.Enabling escape sequences
By default, heredocs have no escape sequences and every character is literal (except interpolated expressions, if enabled). To enable escape sequences, add switches to the heredoc tag.
To enable individual escape sequences, add a slash (/
) and one or more
switches. For example, to enable an escape sequence for dollar signs (\$
) and new lines
(\n
), add
/$n
to the
heredoc tag
:
@("EOT"/$n)
To enable all escape sequences, add a slash and no switches:
@("EOT"/)
Use the following switches to enable escape sequences:
Switch to put in the heredoc tag | Escape sequence to use in the heredoc string | Result in the string value |
---|---|---|
(automatic) | \\ | Single backslash. This switch is enabled when any other escape sequence is enabled. |
n | \n | New line |
r | \r | Carriage return |
t | \t | Tab |
s | \s | Space |
$ | \$ | Literal dollar sign (to prevent interpolation) |
u | \uXXXX or \u{XXXXXX} | Unicode character number XXXX
(a four-digit hexadecimal number) or XXXXXX (a two- to six-digit hexadecimal number)
|
L | \<New line or carriage
return> | Nothing. This lets you put line breaks in the heredoc source code that does not appear in the string value. |
\\
escape sequence. So, for example, If you
want the result to include a double backslash, use four backslashes.Enabling syntax checking
To enable syntax checking of heredoc text, add the name of the syntax to the heredoc tag. For example:
@(END:pp) @(END:epp) @(END:json)
If Puppet has a syntax checker for the given syntax, it validates the heredoc text, but only if the heredoc is static text and does not contain any interpolations. If Puppet has no checker available for the given syntax, it silently ignores the syntax tag.
Syntax checking in heredocs is useful for validating syntax earlier, avoiding later failure.
By default, heredocs are treated as text unless otherwise specified in the heredoc tag.
Stripping indentation
To make your code easier to read, you can
indent the content of a heredoc to separate it from the surrounding code. To strip
this indentation from the resulting string value, put the same amount of indentation
in front of the end marker and use a pipe character (|
) to indicate the position of the first
“real” character on each
line.
$mytext = @(EOT) This block of text is visibly separated from everything around it. | EOTIf a line has less indentation than you’ve indicated with the pipe, Puppet strips any spaces it can without deleting non-space characters.
If a line has more indentation than you’ve indicated with the pipe, the excess spaces are included in the final string value.
Suppressing literal line breaks
If you enable
the L
escape switch, you can end a line with a backslash (\
) to exclude the
following line break from the string value. This lets you break up long lines in
your source code without adding unwanted literal line breaks to the resulting string
value.
For example, Puppet would read this as a single line:
lg = "log --pretty=format:'%C(yellow)%h%C(reset) %s \ %C(cyan)%cr%C(reset) %C(blue)%an%C(reset) %C(green)%d%C(reset)' --graph"
Suppressing the final line break
By default, heredocs end with a
trailing line break, but you can exclude this line break from the final string. To
suppress it, add a hyphen (-
) to the end marker, before the end text, but after the indentation
pipe if you used one. This works even if you don’t have the L
escape switch
enabled.
For example, Puppet would read this as a string with no line break at the end:
$mytext = @("EOT") This is too inconvenient for ${double} or ${single} quotes, but must be one line. |-EOT