poundctl.tmpl - templates for poundctl.
Contents
Copyright
Copyright © 2023-2025 Sergey Poznyakoff
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent
permitted by law.
pound January 2, 2025 POUNDCTL.TMPL(5)
Description
The syntax of poundctl templates is modelled after and mostly conforming to the specifications of the
golang template module (https://pkg.go.dev/text/template).
Templates are executed by applying them to a JSON object. Annotations in a template refer to attributes
of the object to control execution and derive values to be displayed. Execution of the template walks
the structure and sets the cursor, represented by a period (called dot), to the value at the current
location in the object as execution proceeds.
The input text for a template is as ASCII text is arbitrary format. Actions -- data evaluations or
control structures -- are delimited by {{ and }}; all text outside actions is copied to the output
verbatim.
To aid in formatting template source code, if {{ is followed immediately by a minus sign and white space,
all trailing white space is trimmed from the immediately preceding text. Similarly, if }} is preceded by
white space and a minus sign, all leading white space is trimmed from the immediately following text.
Notice that the presence of the whitespace in these trim markers is mandatory: "{{- 3}}" trims the
immediately preceding text and outputs "3", while "{{-3}}" parses as an action containing the number -3.
Actions
Here is the list of actions. Arguments and pipelines are evaluations of data, defined in detail in the
corresponding sections that follow.
{{}} Empty action is discarded. It may be useful to trim the preceding or following whitespace, as in
{{--}}.{{/*acomment*/}}
Comments are discarded. They may span multiple lines of text. Comments do not nest and must
start immediately after the opening delimiter (with optional dash and whitespace in between). A
comment may be followed by any action described below.
Comments may be used to control trailing and leading whitespace as well:
{{-acommenttrimmingthesurroundingwhitespace-}}{{pipeline}}Pipeline is evaluated, and the default textual representation of its value is copied to the
output.
{{ifpipeline}}T1{{end}}
If the value of the pipeline is empty, no output is generated; otherwise, T1 is executed. The
empty values are null, false, numeric 0, empty string (""), array ([]), or object ({}). Dot is
unaffected.
{{ifpipeline}}T1{{else}}T0{{end}}
If the value of the pipeline is empty, T0 is executed; otherwise, T1 is executed. Dot is
unaffected.
{{ifpipeline}}T1{{elseifpipeline}}T2{{else}}T0{{end}}
A shortcut to simplify writing the if-else chains. Equivalent to (newlines added for
readability):
{{if pipeline }}
T1
{{else -}}
{{if pipeline }}
T2
{{else}}
T0
{{end}}
{{end}}
{{rangepipeline}}T1{{end}}
The value of pipeline must be an object or array. If it is of length zero, nothing is output.
Otherwise, dot is set to the successive elements of the array or object and T1 is executed. For
objects, the elements will be visited in sorted key order.
{{rangepipeline}}T1{{else}}T0{{end}}
Same as above, except that if the value of the pipeline is of length zero, T0 is executed with dot
unaffected.
Within the {{range}} action, the following two keywords may appear:
{{break}}
The innermost {{rangepipeline}} loop is ended early, stopping the current iteration and bypassing
all remaining iterations.
{{continue}}
The current iteration of the innermost {{rangepipeline}} loop is stopped, and the loop starts the
next iteration.
{{define"name"}}text{{end}}
The text is collected and stored for the further use as template with the given name. It can be
invoked using the {{template}} action (see below).
{{template"name"}}
The template with the specified name (see the {{define}}above)isexecutedwithdotsettonull.
{{template"name"value}}
The template with the specified name (see the {{define}}above)isexecutedwithdotsettovalue.
{{block"name"pipeline}}T1{{end}}
A block is shorthand for defining a template
{{define "name"}} T1 {{end}}
and then executing it in place
{{template "name" pipeline}}
{{withpipeline}}T1{{end}}
If the value of the pipeline is empty, no output is generated; otherwise, dot is set to the value
of the pipeline and T1 is executed.
{{withpipeline}}T1{{else}}T0{{end}}
Same as above, but if the value of the pipeline is empty, T0 is executed with dot unchanged.
Arguments
An argument is a simple value, i.e. any of the following:
Numeric value (integer or floating point)
Boolean value: true or false.
Quoted string.
A dot (.)
This represents the cursor value.
Attribute: .Attr
This is the value of the attribute Attr in the current value (dot).
Attribute references can be nested, as in .Attr.Xattr.Yattr.
A variable reference: $var.
Here, var is the name of the variable defined in the range action. See the subsection Variables,
below.
Function call in parentheses, for grouping.
Pipelines
A pipeline is a series of one or more commands delimited by pipe sign (|). Each command is either an
argument or a functioncall, in form:
func arg1 arg2...
where func is the name of one of the built-in functions discussed below.
Pipelines are executed from left to right, with the result of the previous command implicitly added to
the list of arguments of each subsequent command. For example, the pipeline
.attr | eq $x
is equivalent to
eq $x .attr
i.e. it calls the built-in function eq with two arguments: the value of the variable x and attribute attr
of the cursor value.
The following built-in functions are defined:
andA1A2
Evaluates to true if pipelines A1 and A2 both evaluate to true. Notice, that there is no boolean
shortcut evaluation: both pipelines are evaluated prior to calling and.
orA1A2
Evaluates to true if at least one of the pipelines A1 and A2 evaluates to true. Notice, that
there is no boolean shortcut evaluation: both pipelines are evaluated prior to calling or.
indexA1A2...
Returns the result of indexing its first argument by the following arguments. Thus, if . is an
array, then:
index . 5
evaluates to its fifth element (.[5]).
lenA1 Returns the integer length of its argument.
notA1 Returns true if its argument evaluates to false.
eqA1A2
Returns true if both its arguments are equal. This applies only if both A1 and A2 are numeric or
if they both are strings.
neA1A2
Returns true if its arguments (both must be numeric or strings) are not equal.
ltA1A2
Returns true if A1 is numerically less than A2.
leA1A2
Returns true if A1 is numerically less than or equal to A2.
gtA1A2
Returns true if A1 is numerically greater than A2.
geA1A2
Returns true if A1 is numerically greater than or equal to A2.
evenA1
Returns true if A1, which must evaluate to an integer value, is divisible by 2.
printfFMTA1...
Implements the printf(3) function. FMT must evaluate to a string. Rest of arguments is
interpreted according to the conversion specifications in FMT. The result is a formatted string.
In addition to the standard conversion specifications described in printf(3), the "%v" specifier
is implemented: it formats its argument in the best way, depending on its actual type.
typeofA1
Evaluates to the type of its argument, one of: null, bool, number, integer, string, array, object.
existsA1A2A1 must evaluate to an object and A2 to string. The function evaluates to true if the attribute
A2 is present in A1.
addA1A2...
Returns the sum of its arguments.
subA1A2
Returns the difference A1 - A2.
mulA1A2
Multiplies A1 by A2.
divA1A2
Divides A1 by A2.
Variables
Variables (referred to as $name) can be defined in range and with actions. For range, the syntax is:
{{range$index,$element=pipeline}}T1{{end}}
where index and element are arbitrary variable names. When executing this action, during each iteration
$index and $element are set to the index (attribute name) and value of each successive element. Dot
remains unaffected.
For with, the syntax is:
{{with$var=pipeline}}T1{{end}}Pipeline is evaluated, its result is assigned to $var and the T1 block is executed with dot unchanged.
A variable's scope extends to the end action of the control structure (with or range) in which it is
declared. This includes any nested statements that may appear in between.
Input Object
Depending on the request issued by poundctl, the invoked template can receive as its argument (dot) an
object of the following types: full listing, listener, service, or backend.
Since there is no explicit indication of the object type being passed, templates normally use heuristics
based on the presence or absence of certain attribute to deduce the object type in question. The
recommended approach is described in the following pseudo-code fragment:
{{if exists . "listeners" }}
{{/* This is a full listing, as requested by poundctllist. */}}
...
{{else if exists . "services"}}
{{/* Single listener, as requested by poundctllist/L.
Notice that this attribute is present in the full listing as
well, so presence of "listeners" should be checked first. */}}
...
{{else if exists . "backends"}}
{{/* Single service, as requested by poundctllist/L/S. */}}
...
{{else}}
{{/* Backend listing (poundctllist/L/S/B) */}}
...
{{end}}
Structures of each object are discussed in subsections that follow.
Fulllisting
A full listing contains the following attributes:
listeners
An array of listener objects. See below for a description.
services
An array of service objects, representing services defined in the global scope of the pound
configuration file.
pid PID of the running pound daemon.
versionPound version number (string).
workers
Workers statistics. This is a JSON object with the following attributes:
active Number of active threads.
count Number of threads currently running.
max Maximum number of threads.
min Minimum number of threads.
timeout
Thread idle timeout.
queue_len
Number of incoming HTTP requests in the queue (integer).
timestamp
Current time on the server, formatted as ISO 8601 date-time with microsecond precision, e.g.:
"2023-01-05T22:43:18.071559".
Listener
A listener object represents a single HTTP or HTTPS listener in pound configuration. It has the
following attributes:
addressString. Address of this listener. A string formatted as "IP:PORT" for IPv4 and IPv6 addresses or
containing socket file name, for UNIX sockets.
protocolString. Protocol used: either http or https.
services
Array of service objects representing services defined in this listener. See below for the
definition of a service object.
enabledBoolean. Whether this listener is enabled or not.
nohttps11Integer. Value of the NoHTTPS11 configuration statement for this listener. One of: 0, 1, 2.
Service
A service object describes a single service.
nameString. Symbolic name of this service.
enabledBoolean. Whether this service is enabled or not.
session_typeString. Name of the session handling algorithm for this service. One of: IP, BASIC, URL, PARM,
COOKIE, HEADER.
sessions
List of active sessions in this service. Each session is represented as object with the following
attributes:
keyString. Session key.
backendInteger. Number of the backend assigned to handle requests with this session.
expireTimestamp. Expiration time of this session, with microsecond precision.
backends
List of backends defined for this service.
emergency
Emergency backend object, or null if no such backend is defined.
Backend
The following attributes are always present in each backend object:
aliveBoolean. Whether or not this backend is alive.
conn_toInteger. Connection timeout for this backend (seconds).
enabledBoolean. Whether or not this backend is enabled.
io_toInteger. I/O timeout for this backend (seconds).
priorityInteger in range 0-9. Priority value assigned to this backend.
protocolString. Protocol used by this backend: either http or https.
typeString. Backend type. One of: acme, backend, control, redirect.
ws_toInteger Websocket timeout (seconds).
Depending on the backend type, the following attributes may be present:
acmepathString. Directory where ACME challenges are stored.
backendaddressString. Backend address.
redirecturlString. URL to redirect to.
codeInteger. HTTP code for redirection responses. One of: 301, 302, 307.
redir_reqBoolean. Whether to append the original request path to the resulting location.
If backend statistics is enabled (see BackendStats in pound(8)), the stats object will be present, with
the following attributes:
request_count
Total number of requests processed by this backend.
request_time_avg
Average time per request, in nanoseconds.
request_time_stddev
Standard deviation of the above.
Name
poundctl.tmpl - templates for poundctl.
Reporting Bugs
Report bugs to <gray@gnu.org>. You may also use github issue tracker at
https://github.com/graygnuorg/pound/issues.
See Also
pound(8), poundctl(8).
