]> granicus.if.org Git - icinga2/blob - doc/17-language-reference.md
Elasticsearch: Change Content-Type header to 'application/x-ndjson' for bulk streams
[icinga2] / doc / 17-language-reference.md
1 # Language Reference <a id="language-reference"></a>
2
3 ## Object Definition <a id="object-definition"></a>
4
5 Icinga 2 features an object-based configuration format. You can define new
6 objects using the `object` keyword:
7
8     object Host "host1.example.org" {
9       display_name = "host1"
10
11       address = "192.168.0.1"
12       address6 = "2001:db8:1234::42"
13     }
14
15 In general you need to write each statement on a new line. Expressions started
16 with `{`, `(` and `[` extend until the matching closing character and can be broken
17 up into multiple lines.
18
19 Alternatively you can write multiple statements on a single line by separating
20 them with a semicolon:
21
22     object Host "host1.example.org" {
23       display_name = "host1"
24
25       address = "192.168.0.1"; address6 = "2001:db8:1234::42"
26     }
27
28 Each object is uniquely identified by its type (`Host`) and name
29 (`host1.example.org`). Some types have composite names, e.g. the
30 `Service` type which uses the `host_name` attribute and the name
31 you specified to generate its object name.
32
33 Exclamation marks (!) are not permitted in object names.
34
35 Objects can contain a comma-separated list of property
36 declarations. Instead of commas semicolons may also be used.
37 The following data types are available for property values:
38
39 All objects have at least the following attributes:
40
41 Attribute            | Description
42 ---------------------|-----------------------------
43 name                 | The name of the object. This attribute can be modified in the object definition to override the name specified with the `object` directive.
44 type                 | The type of the object.
45
46 ## Expressions <a id="expressions"></a>
47
48 The following expressions can be used on the right-hand side of assignments.
49
50 ### Numeric Literals <a id="numeric-literals"></a>
51
52 A floating-point number.
53
54 Example:
55
56     27.3
57
58 ### Duration Literals <a id="duration-literals"></a>
59
60 Similar to floating-point numbers except for the fact that they support
61 suffixes to help with specifying time durations.
62
63 Example:
64
65     2.5m
66
67 Supported suffixes include ms (milliseconds), s (seconds), m (minutes),
68 h (hours) and d (days).
69
70 Duration literals are converted to seconds by the config parser and
71 are treated like numeric literals.
72
73 ### String Literals <a id="string-literals"></a>
74
75 A string.
76
77 Example:
78
79     "Hello World!"
80
81 #### String Literals Escape Sequences <a id="string-literals-escape-sequences"></a>
82
83 Certain characters need to be escaped. The following escape sequences
84 are supported:
85
86 Character                 | Escape sequence
87 --------------------------|------------------------------------
88 "                         | \\"
89 \\                        | \\\\
90 &lt;TAB&gt;               | \\t
91 &lt;CARRIAGE-RETURN&gt;   | \\r
92 &lt;LINE-FEED&gt;         | \\n
93 &lt;BEL&gt;               | \\b
94 &lt;FORM-FEED&gt;         | \\f
95
96 In addition to these pre-defined escape sequences you can specify
97 arbitrary ASCII characters using the backslash character (\\) followed
98 by an ASCII character in octal encoding.
99
100 ### Multi-line String Literals <a id="multiline-string-literals"></a>
101
102 Strings spanning multiple lines can be specified by enclosing them in
103 {{{ and }}}.
104
105 Example:
106
107     {{{This
108     is
109     a multi-line
110     string.}}}
111
112 Unlike in ordinary strings special characters do not have to be escaped
113 in multi-line string literals.
114
115 ### Boolean Literals <a id="boolean-literals"></a>
116
117 The keywords `true` and `false` are used to denote truth values.
118
119 ### Null Value <a id="null-value"></a>
120
121 The `null` keyword can be used to specify an empty value.
122
123 ### Dictionary <a id="dictionary"></a>
124
125 An unordered list of key-value pairs. Keys must be unique and are
126 compared in a case-sensitive manner.
127
128 Individual key-value pairs must either be comma-separated or on separate lines.
129 The comma after the last key-value pair is optional.
130
131 Example:
132
133     {
134       address = "192.168.0.1"
135       port = 443
136     }
137
138 Identifiers may not contain certain characters (e.g. space) or start
139 with certain characters (e.g. digits). If you want to use a dictionary
140 key that is not a valid identifier, you can enclose the key in double
141 quotes.
142
143 ### Array <a id="array"></a>
144
145 An ordered list of values.
146
147 Individual array elements must be comma-separated.
148 The comma after the last element is optional.
149
150 Example:
151
152     [ "hello", 42 ]
153
154 An array may simultaneously contain values of different types, such as
155 strings and numbers.
156
157 ### Operators <a id="expression-operators"></a>
158
159 The following operators are supported in expressions. The operators are sorted by descending precedence.
160
161 Operator | Precedence | Examples (Result)                             | Description
162 ---------|------------|-----------------------------------------------|--------------------------------
163 `()`       | 1          | (3 + 3) * 5                                   | Groups sub-expressions
164 `()`       | 1          | Math.random()                                 | Calls a function
165 `[]`       | 1          | a[3]                                          | Array subscript
166 `.`       | 1          | a.b                                           | Element access
167 `!`        | 2          | !"Hello" (false), !false (true)               | Logical negation of the operand
168 `~`        | 2          | ~true (false)                                 | Bitwise negation of the operand
169 `+`        | 2          | +3                                            | Unary plus
170 `-`        | 2          | -3                                            | Unary minus
171 `&`        | 2          | &var (reference to 'var')                     | Reference operator
172 `*`        | 2          | *var                                          | Indirection operator
173 `*`        | 3          | 5m * 10 (3000)                                | Multiplies two numbers
174 `/`        | 3          | 5m / 5 (60)                                   | Divides two numbers
175 `%`        | 3          | 17 % 12 (5)                                   | Remainder after division
176 `+`        | 4          | 1 + 3 (4), "hello " + "world" ("hello world") | Adds two numbers; concatenates strings
177 `-`        | 4          | 3 - 1 (2)                                     | Subtracts two numbers
178 `<<`       | 5          | 4 << 8 (1024)                                 | Left shift
179 `>>`       | 5          | 1024 >> 4 (64)                                | Right shift
180 `<`        | 6         | 3 < 5 (true)                                  | Less than
181 `>`        | 6         | 3 > 5 (false)                                 | Greater than
182 `<=`       | 6         | 3 <= 3 (true)                                 | Less than or equal
183 `>=`       | 6         | 3 >= 3 (true)                                 | Greater than or equal
184 `in`       | 7          | "foo" in [ "foo", "bar" ] (true)              | Element contained in array
185 `!in`      | 7          | "foo" !in [ "bar", "baz" ] (true)             | Element not contained in array
186 `==`       | 8         | "hello" == "hello" (true), 3 == 5 (false)     | Equal to
187 `!=`       | 8         | "hello" != "world" (true), 3 != 3 (false)     | Not equal to
188 `&`        | 9          | 7 & 3 (3)                                     | Binary AND
189 `^`        | 10          | 17 ^ 12 (29)                                  | Bitwise XOR
190 <code>&#124;</code>    | 11          | 2 &#124; 3 (3)                                | Binary OR
191 <code>&#124;&#124;</code>  | 12     | true &#124;&#124; false (true), 0 &#124;&#124; 7 (7)| Logical OR
192 `&&`       | 13         | true && false (false), 3 && 7 (7), 0 && 7 (0) | Logical AND
193 `=`        | 14         | a = 3                                         | Assignment
194 `=>`       | 15         | x => x * x (function with arg x)              | Lambda, for loop
195
196 ### References <a id="references"></a>
197
198 A reference to a value can be obtained using the `&` operator. The `*` operator can be used
199 to dereference a reference:
200
201     var value = "Hello!"
202     var p = &value /* p refers to value */
203     *p = "Hi!"
204     log(value) // Prints "Hi!" because the variable was changed
205
206 ### Namespaces <a id="namespaces"></a>
207
208 Namespaces can be used to organize variables and functions. They are used to avoid name conflicts. The `namespace`
209 keyword is used to create a new namespace:
210
211     namespace Utils {
212         function calculate() {
213             return 2 + 2
214         }
215     }
216
217 The namespace is made available as a global variable which has the namespace's name (e.g. `Utils`):
218
219     Utils.calculate()
220
221 The `using` keyword can be used to make all attributes in a namespace available to a script without having to
222 explicitly specify the namespace's name for each access:
223
224     using Utils
225     calculate()
226
227 The `using` keyword only has an effect for the current file and only for code that follows the keyword:
228
229     calculate() // This will not work.
230     using Utils
231
232 The following namespaces are automatically imported as if by using the `using` keyword:
233
234 * System
235 * System.Configuration
236 * Types
237 * Icinga
238
239 ### Function Calls <a id="function-calls"></a>
240
241 Functions can be called using the `()` operator:
242
243     const MyGroups = [ "test1", "test" ]
244
245     {
246       check_interval = len(MyGroups) * 1m
247     }
248
249 A list of available functions is available in the [Library Reference](18-library-reference.md#library-reference) chapter.
250
251 ## Assignments <a id="dictionary-operators"></a>
252
253 In addition to the `=` operator shown above a number of other operators
254 to manipulate attributes are supported. Here's a list of all
255 available operators (the outermost `{` `}` stand for a local variable scope):
256
257 ### Operator = <a id="operator-assignment"></a>
258
259 Sets an attribute to the specified value.
260
261 Example:
262
263     {
264       a = 5
265       a = 7
266     }
267
268 In this example `a` has the value `7` after both instructions are executed.
269
270 ### Operator += <a id="operator-additive-assignment"></a>
271
272 The += operator is a shortcut. The following expression:
273
274     {
275       a = [ "hello" ]
276       a += [ "world" ]
277     }
278
279 is equivalent to:
280
281     {
282       a = [ "hello" ]
283       a = a + [ "world" ]
284     }
285
286 ### Operator -= <a id="operator-substractive-assignment"></a>
287
288 The -= operator is a shortcut. The following expression:
289
290     {
291       a = 10
292       a -= 5
293     }
294
295 is equivalent to:
296
297     {
298       a = 10
299       a = a - 5
300     }
301
302 ### Operator \*= <a id="operator-multiply-assignment"></a>
303
304 The *= operator is a shortcut. The following expression:
305
306     {
307       a = 60
308       a *= 5
309     }
310
311 is equivalent to:
312
313     {
314       a = 60
315       a = a * 5
316     }
317
318 ### Operator /= <a id="operator-dividing-assignment"></a>
319
320 The /= operator is a shortcut. The following expression:
321
322     {
323       a = 300
324       a /= 5
325     }
326
327 is equivalent to:
328
329     {
330       a = 300
331       a = a / 5
332     }
333
334 ## Indexer <a id="indexer"></a>
335
336 The indexer syntax provides a convenient way to set dictionary elements.
337
338 Example:
339
340     {
341       hello.key = "world"
342     }
343
344 Example (alternative syntax):
345
346     {
347       hello["key"] = "world"
348     }
349
350 This is equivalent to writing:
351
352     {
353       hello += {
354         key = "world"
355       }
356     }
357
358 If the `hello` attribute does not already have a value, it is automatically initialized to an empty dictionary.
359
360 ## Template Imports <a id="template-imports"></a>
361
362 Objects can import attributes from other objects.
363
364 Example:
365
366     template Host "default-host" {
367       vars.colour = "red"
368     }
369
370     template Host "test-host" {
371       import "default-host"
372
373       vars.colour = "blue"
374     }
375
376     object Host "localhost" {
377       import "test-host"
378
379       address = "127.0.0.1"
380       address6 = "::1"
381     }
382
383 The `default-host` and `test-host` objects are marked as templates
384 using the `template` keyword. Unlike ordinary objects templates are not
385 instantiated at run-time. Parent objects do not necessarily have to be
386 templates, however in general they are.
387
388 The `vars` dictionary for the `localhost` object contains all three
389 custom attributes and the custom attribute `colour` has the value `"blue"`.
390
391 Parent objects are resolved in the order they're specified using the
392 `import` keyword.
393
394 Default templates which are automatically imported into all object definitions
395 can be specified using the `default` keyword:
396
397     template CheckCommand "plugin-check-command" default {
398       // ...
399     }
400
401 Default templates are imported before any other user-specified statement in an
402 object definition is evaluated.
403
404 If there are multiple default templates the order in which they are imported
405 is unspecified.
406
407 ## Constants <a id="constants"></a>
408
409 Global constants can be set using the `const` keyword:
410
411     const VarName = "some value"
412
413 Once defined a constant can be accessed from any file. Constants cannot be changed
414 once they are set.
415
416 > **Tip**
417 >
418 > Best practice is to manage constants in the [constants.conf](04-configuring-icinga-2.md#constants-conf) file.
419
420 ### Icinga 2 Specific Constants <a id="icinga-constants"></a>
421
422 Icinga 2 provides a number of special global constants. These include directory paths, global configuration
423 and runtime parameters for the application version and (build) platform.
424
425 Directory paths:
426
427 Constant            | Description
428 --------------------|-------------------
429 ConfigDir           |**Read-only.** Main configuration directory. Usually set to `/etc/icinga2`.
430 DataDir             |**Read-only.** Runtime data for the Icinga daemon. Usually set to `/var/lib/icinga2`.
431 LogDir              |**Read-only.** Logfiles from the daemon. Usually set to `/var/log/icinga2`.
432 CacheDir            |**Read-only.** Cached status information of the daemon. Usually set to `/var/cache/icinga2`.
433 SpoolDir            |**Read-only.** Spool directory for certain data outputs. Usually set to `/var/spool/icinga2`.
434 InitRunDir          |**Read-only.** Directory for PID files and sockets in daemon mode. Usually set to `/run/icinga2`.
435 ZonesDir            |**Read-only.** Contains the path of the zones.d directory. Defaults to `ConfigDir + "/zones.d"`.
436
437 Global configuration:
438
439 Constant            | Description
440 --------------------|-------------------
441 Vars                |**Read-write.** Contains a dictionary with global custom attributes. Not set by default.
442 NodeName            |**Read-write.** Contains the cluster node name. Set to the local hostname by default.
443 ReloadTimeout       |**Read-write.** Defines the reload timeout for child processes. Defaults to `300s`.
444 Environment         |**Read-write.** The name of the Icinga environment. Included in the SNI host name for outbound connections. Not set by default.
445 RunAsUser           |**Read-write.** Defines the user the Icinga 2 daemon is running as. Set in the Icinga 2 sysconfig.
446 RunAsGroup          |**Read-write.** Defines the group the Icinga 2 daemon is running as. Set in the Icinga 2 sysconfig.
447 MaxConcurrentChecks |**Read-write.** The number of max checks run simultaneously. Defaults to `512`.
448 ApiBindHost         |**Read-write.** Overrides the default value for the ApiListener `bind_host` attribute. Not set by default.
449 ApiBindPort         |**Read-write.** Overrides the default value for the ApiListener `bind_port` attribute. Not set by default.
450
451 Application runtime details:
452
453 Constant            | Description
454 --------------------|-------------------
455 PlatformName        |**Read-only.** The name of the operating system, e.g. `Ubuntu`.
456 PlatformVersion     |**Read-only.** The version of the operating system, e.g. `14.04.3 LTS`.
457 PlatformKernel      |**Read-only.** The name of the operating system kernel, e.g. `Linux`.
458 PlatformKernelVersion|**Read-only.** The version of the operating system kernel, e.g. `3.13.0-63-generic`.
459 BuildCompilerName   |**Read-only.** The name of the compiler Icinga was built with, e.g. `Clang`.
460 BuildCompilerVersion|**Read-only.** The version of the compiler Icinga was built with, e.g. `7.3.0.7030031`.
461 BuildHostName       |**Read-only.** The name of the host Icinga was built on, e.g. `acheron`.
462 ApplicationVersion  |**Read-only.** The application version, e.g. `2.9.0`.
463
464 Writable constants can be specified on the CLI using the `--define/-D` parameter.
465
466 > **Note for v2.10+**
467 >
468 > Default paths which include `/etc` and `/var` as base directory continue to work
469 > based on the `SysconfDir` and `LocalStateDir` constants respectively.
470
471 In addition to that, the constants below are used to define specific file paths. You should never need
472 to change them, as they are pre-compiled based on the constants above.
473
474 Variable            |Description
475 --------------------|-------------------
476 StatePath           |**Read-write.** Contains the path of the Icinga 2 state file. Defaults to `DataDir + "/icinga2.state"`.
477 ObjectsPath         |**Read-write.** Contains the path of the Icinga 2 objects file. Defaults to `CacheDir + "/icinga2.debug"`.
478 PidPath             |**Read-write.** Contains the path of the Icinga 2 PID file. Defaults to `InitRunDir + "/icinga2.pid"`.
479 PkgDataDir          |**Read-only.** Contains the path of the package data directory. Defaults to `PrefixDir + "/share/icinga2"`.
480
481 The constants below have been used until Icinga v2.10, and are still intact. You don't need them
482 for future builds and configuration based on the newly available constants above.
483
484 Variable            |Description
485 --------------------|-------------------
486 PrefixDir           |**Read-only.** Contains the installation prefix that was specified with `cmake -DCMAKE_INSTALL_PREFIX`. `Defaults to "/usr/local"`.
487 SysconfDir          |**Read-only.** Contains the path of the sysconf directory. Defaults to `PrefixDir + "/etc"`.
488 LocalStateDir       |**Read-only.** Contains the path of the local state directory. Defaults to `PrefixDir + "/var"`.
489 RunDir              |**Read-only.** Contains the path of the run directory. Defaults to `LocalStateDir + "/run"`.
490
491 Advanced runtime constants. Please only use them if advised by support or developers.
492
493 Variable                   | Description
494 ---------------------------|-------------------
495 EventEngine                |**Read-write.** The name of the socket event engine, can be `poll` or `epoll`. The epoll interface is only supported on Linux.
496 AttachDebugger             |**Read-write.** Whether to attach a debugger when Icinga 2 crashes. Defaults to `false`.
497 ICINGA2\_RLIMIT\_FILES     |**Read-write.** Defines the resource limit for RLIMIT_NOFILE that should be set at start-up. Value cannot be set lower than the default `16 * 1024`. 0 disables the setting. Set in Icinga 2 sysconfig.
498 ICINGA2\_RLIMIT\_PROCESSES |**Read-write.** Defines the resource limit for RLIMIT_NPROC that should be set at start-up. Value cannot be set lower than the default `16 * 1024`. 0 disables the setting. Set in Icinga 2 sysconfig.
499 ICINGA2\_RLIMIT\_STACK     |**Read-write.** Defines the resource limit for RLIMIT_STACK that should be set at start-up. Value cannot be set lower than the default `256 * 1024`. 0 disables the setting. Set in Icinga 2 sysconfig.
500
501 ## Apply <a id="apply"></a>
502
503 The `apply` keyword can be used to create new objects which are associated with
504 another group of objects.
505
506     apply Service "ping" to Host {
507       import "generic-service"
508
509       check_command = "ping4"
510
511       assign where host.name == "localhost"
512     }
513
514 In this example the `assign where` condition is a boolean expression which is
515 evaluated for all objects of type `Host` and a new service with name "ping"
516 is created for each matching host. [Expression operators](17-language-reference.md#expression-operators)
517 may be used in `assign where` conditions.
518
519 The `to` keyword and the target type may be omitted if there is only one target
520 type, e.g. for the `Service` type.
521
522 Depending on the object type used in the `apply` expression additional local
523 variables may be available for use in the `where` condition:
524
525 Source Type       | Target Type | Variables
526 ------------------|-------------|--------------
527 Service           | Host        | host
528 Dependency        | Host        | host
529 Dependency        | Service     | host, service
530 Notification      | Host        | host
531 Notification      | Service     | host, service
532 ScheduledDowntime | Host        | host
533 ScheduledDowntime | Service     | host, service
534
535 Any valid config attribute can be accessed using the `host` and `service`
536 variables. For example, `host.address` would return the value of the host's
537 "address" attribute -- or null if that attribute isn't set.
538
539 More usage examples are documented in the [monitoring basics](03-monitoring-basics.md#using-apply-expressions)
540 chapter.
541
542 ## Apply For <a id="apply-for"></a>
543
544 [Apply](17-language-reference.md#apply) rules can be extended with the
545 [for loop](17-language-reference.md#for-loops) keyword.
546
547     apply Service "prefix-" for (key => value in host.vars.dictionary) to Host {
548       import "generic-service"
549
550       check_command = "ping4"
551       vars.host_value = value
552     }
553
554
555 Any valid config attribute can be accessed using the `host` and `service`
556 variables. The attribute must be of the Array or Dictionary type. In this example
557 `host.vars.dictionary` is of the Dictionary type which needs a key-value-pair
558 as iterator.
559
560 In this example all generated service object names consist of `prefix-` and
561 the value of the `key` iterator. The prefix string can be omitted if not required.
562
563 The `key` and `value` variables can be used for object attribute assignment, e.g. for
564 setting the `check_command` attribute or custom attributes as command parameters.
565
566 `apply for` rules are first evaluated against all objects matching the `for loop` list
567 and afterwards the `assign where` and `ignore where` conditions are evaluated.
568
569 It is not necessary to check attributes referenced in the `for loop` expression
570 for their existance using an additional `assign where` condition.
571
572 More usage examples are documented in the [monitoring basics](03-monitoring-basics.md#using-apply-for)
573 chapter.
574
575 ## Group Assign <a id="group-assign"></a>
576
577 Group objects can be assigned to specific member objects using the `assign where`
578 and `ignore where` conditions.
579
580     object HostGroup "linux-servers" {
581       display_name = "Linux Servers"
582
583       assign where host.vars.os == "Linux"
584     }
585
586 In this example the `assign where` condition is a boolean expression which is evaluated
587 for all objects of the type `Host`. Each matching host is added as member to the host group
588 with the name "linux-servers". Membership exclusion can be controlled using the `ignore where`
589 condition. [Expression operators](17-language-reference.md#expression-operators) may be used in `assign where` and
590 `ignore where` conditions.
591
592 Source Type       | Variables
593 ------------------|--------------
594 HostGroup         | host
595 ServiceGroup      | host, service
596 UserGroup         | user
597
598
599 ## Boolean Values <a id="boolean-values"></a>
600
601 The `assign where`, `ignore where`, `if` and `while`  statements, the `!` operator as
602 well as the `bool()` function convert their arguments to a boolean value based on the
603 following rules:
604
605 Description          | Example Value     | Boolean Value
606 ---------------------|-------------------|--------------
607 Empty value          | null              | false
608 Zero                 | 0                 | false
609 Non-zero integer     | -23945            | true
610 Empty string         | ""                | false
611 Non-empty string     | "Hello"           | true
612 Empty array          | []                | false
613 Non-empty array      | [ "Hello" ]       | true
614 Empty dictionary     | {}                | false
615 Non-empty dictionary | { key = "value" } | true
616
617 For a list of supported expression operators for `assign where` and `ignore where`
618 statements, see [expression operators](17-language-reference.md#expression-operators).
619
620 ## Comments <a id="comments"></a>
621
622 The Icinga 2 configuration format supports C/C++-style and shell-style comments.
623
624 Example:
625
626     /*
627      This is a comment.
628      */
629     object Host "localhost" {
630       check_interval = 30 // this is also a comment.
631       retry_interval = 15 # yet another comment
632     }
633
634 ## Includes <a id="includes"></a>
635
636 Other configuration files can be included using the `include` directive.
637 Paths must be relative to the configuration file that contains the
638 `include` directive.
639
640 Example:
641
642     include "some/other/file.conf"
643     include "conf.d/*.conf"
644
645 Wildcard includes are not recursive.
646
647 Icinga also supports include search paths similar to how they work in a
648 C/C++ compiler:
649
650     include <itl>
651
652 Note the use of angle brackets instead of double quotes. This causes the
653 config compiler to search the include search paths for the specified
654 file. By default $PREFIX/share/icinga2/include is included in the list of search
655 paths. Additional include search paths can be added using
656 [command-line options](11-cli-commands.md#config-include-path).
657
658 Wildcards are not permitted when using angle brackets.
659
660 ## Recursive Includes <a id="recursive-includes"></a>
661
662 The `include_recursive` directive can be used to recursively include all
663 files in a directory which match a certain pattern.
664
665 Example:
666
667     include_recursive "conf.d", "*.conf"
668     include_recursive "templates"
669
670 The first parameter specifies the directory from which files should be
671 recursively included.
672
673 The file names need to match the pattern given in the second parameter.
674 When no pattern is specified the default pattern "*.conf" is used.
675
676 ## Zone Includes <a id="zone-includes"></a>
677
678 The `include_zones` recursively includes all subdirectories for the
679 given path.
680
681 In addition to that it sets the `zone` attribute for all objects created
682 in these subdirectories to the name of the subdirectory.
683
684 Example:
685
686     include_zones "etc", "zones.d", "*.conf"
687     include_zones "puppet", "puppet-zones"
688
689 The first parameter specifies a tag name for this directive. Each `include_zones`
690 invocation should use a unique tag name. When copying the zones' configuration
691 files Icinga uses the tag name as the name for the destination directory in
692 `/var/lib/icinga2/api/config`.
693
694 The second parameter specifies the directory which contains the subdirectories.
695
696 The file names need to match the pattern given in the third parameter.
697 When no pattern is specified the default pattern "*.conf" is used.
698
699 ## Library directive <a id="library"></a>
700
701 The `library` directive was used to manually load additional
702 libraries. Starting with version 2.9 it is no longer necessary to explicitly load
703 libraries and this directive has no effect.
704
705 ## Functions <a id="functions"></a>
706
707 Functions can be defined using the `function` keyword.
708
709 Example:
710
711     function multiply(a, b) {
712       return a * b
713     }
714
715 When encountering the `return` keyword further execution of the function is terminated and
716 the specified value is supplied to the caller of the function:
717
718     log(multiply(3, 5))
719
720 In this example the `multiply` function we declared earlier is invoked with two arguments (3 and 5).
721 The function computes the product of those arguments and makes the result available to the
722 function's caller.
723
724 When no value is supplied for the `return` statement the function returns `null`.
725
726 Functions which do not have a `return` statement have their return value set to the value of the
727 last expression which was performed by the function. For example, we could have also written our
728 `multiply` function like this:
729
730     function multiply(a, b) {
731       a * b
732     }
733
734 Anonymous functions can be created by omitting the name in the function definition. The
735 resulting function object can be used like any other value:
736
737     var fn = function() { 3 }
738
739     fn() /* Returns 3 */
740
741 ## Lambda Expressions <a id="lambdas"></a>
742
743 Functions can also be declared using the alternative lambda syntax.
744
745 Example:
746
747     f = (x) => x * x
748
749 Multiple statements can be used by putting the function body into braces:
750
751     f = (x) => {
752       log("Lambda called")
753       x * x
754     }
755
756 Just like with ordinary functions the return value is the value of the last statement.
757
758 For lambdas which take exactly one argument the braces around the arguments can be omitted:
759
760     f = x => x * x
761
762 ## Abbreviated Lambda Syntax <a id="nullary-lambdas"></a>
763
764 Lambdas which take no arguments can also be written using the abbreviated lambda syntax.
765
766 Example:
767
768     f = {{ 3 }}
769
770 This creates a new function which returns the value 3.
771
772 ## Variable Scopes <a id="variable-scopes"></a>
773
774 When setting a variable Icinga checks the following scopes in this order whether the variable
775 already exists there:
776
777 * Local Scope
778 * `this` Scope
779 * Global Scope
780
781 The local scope contains variables which only exist during the invocation of the current function,
782 object or apply statement. Local variables can be declared using the `var` keyword:
783
784     function multiply(a, b) {
785       var temp = a * b
786       return temp
787     }
788
789 Each time the `multiply` function is invoked a new `temp` variable is used which is in no way
790 related to previous invocations of the function.
791
792 When setting a variable which has not previously been declared as local using the `var` keyword
793 the `this` scope is used.
794
795 The `this` scope refers to the current object which the function or object/apply statement
796 operates on.
797
798     object Host "localhost" {
799       check_interval = 5m
800     }
801
802 In this example the `this` scope refers to the "localhost" object. The `check_interval` attribute
803 is set for this particular host.
804
805 You can explicitly access the `this` scope using the `this` keyword:
806
807     object Host "localhost" {
808       var check_interval = 5m
809
810       /* This explicitly specifies that the attribute should be set
811        * for the host, if we had omitted `this.` the (poorly named)
812        * local variable `check_interval` would have been modified instead.
813        */
814       this.check_interval = 1m
815   }
816
817 Similarly the keywords `locals` and `globals` are available to access the local and global scope.
818
819 Functions also have a `this` scope. However unlike for object/apply statements the `this` scope for
820 a function is set to whichever object was used to invoke the function. Here's an example:
821
822      hm = {
823        h_word = null
824
825        function init(word) {
826          h_word = word
827        }
828      }
829
830      /* Let's invoke the init() function */
831      hm.init("hello")
832
833 We're using `hm.init` to invoke the function which causes the value of `hm` to become the `this`
834 scope for this function call.
835
836 ## Closures <a id="closures"></a>
837
838 By default `function`s, `object`s and `apply` rules do not have access to variables declared
839 outside of their scope (except for global variables).
840
841 In order to access variables which are defined in the outer scope the `use` keyword can be used:
842
843     function MakeHelloFunction(name) {
844       return function() use(name) {
845         log("Hello, " + name)
846       }
847     }
848
849 In this case a new variable `name` is created inside the inner function's scope which has the
850 value of the `name` function argument.
851
852 Alternatively a different value for the inner variable can be specified:
853
854     function MakeHelloFunction(name) {
855       return function() use (greeting = "Hello, " + name) {
856         log(greeting)
857       }
858     }
859
860 ## Conditional Statements <a id="conditional-statements"></a>
861
862 Sometimes it can be desirable to only evaluate statements when certain conditions are met. The if/else
863 construct can be used to accomplish this.
864
865 Example:
866
867     a = 3
868
869     if (a < 5) {
870       a *= 7
871     } else if (a > 10) {
872       a *= 5
873     } else {
874       a *= 2
875     }
876
877 An if/else construct can also be used in place of any other value. The value of an if/else statement
878 is the value of the last statement which was evaluated for the branch which was taken:
879
880     a = if (true) {
881       log("Taking the 'true' branch")
882       7 * 3
883     } else {
884       log("Taking the 'false' branch")
885       9
886     }
887
888 This example prints the log message "Taking the 'true' branch" and the `a` variable is set to 21 (7 * 3).
889
890 The value of an if/else construct is null if the condition evaluates to false and no else branch is given.
891
892 ## While Loops <a id="while-loops"></a>
893
894 The `while` statement checks a condition and executes the loop body when the condition evaluates to `true`.
895 This is repeated until the condition is no longer true.
896
897 Example:
898
899     var num = 5
900
901     while (num > 5) {
902         log("Test")
903         num -= 1
904     }
905
906 The `continue` and `break` keywords can be used to control how the loop is executed: The `continue` keyword
907 skips over the remaining expressions for the loop body and begins the next loop evaluation. The `break` keyword
908 breaks out of the loop.
909
910 ## For Loops <a id="for-loops"></a>
911
912 The `for` statement can be used to iterate over arrays and dictionaries.
913
914 Example:
915
916     var list = [ "a", "b", "c" ]
917
918     for (var item in list) {
919       log("Item: " + item)
920     }
921
922 The loop body is evaluated once for each item in the array. The variable `item` is declared as a local
923 variable just as if the `var` keyword had been used.
924
925 Iterating over dictionaries can be accomplished in a similar manner:
926
927     var dict = { a = 3, b = 7 }
928
929     for (var key => var value in dict) {
930       log("Key: " + key + ", Value: " + value)
931     }
932
933 The `continue` and `break` keywords can be used to control how the loop is executed: The `continue` keyword
934 skips over the remaining expressions for the loop body and begins the next loop evaluation. The `break` keyword
935 breaks out of the loop.
936
937 The `var` keyword is optional when declaring variables in the loop's header. Variables declared without the `var`
938 keyword are nonetheless local to the function.
939
940 ## Constructors <a id="constructor"></a>
941
942 In order to create a new value of a specific type constructor calls may be used.
943
944 Example:
945
946     var pd = PerfdataValue()
947     pd.label = "test"
948     pd.value = 10
949
950 You can also try to convert an existing value to another type by specifying it as an argument for the constructor call.
951
952 Example:
953
954     var s = String(3) /* Sets s to "3". */
955
956 ## Throwing Exceptions <a id="throw"></a>
957
958 Built-in commands may throw exceptions to signal errors such as invalid arguments. User scripts can throw exceptions
959 using the `throw` keyword.
960
961 Example:
962
963     throw "An error occurred."
964
965 ## Handling Exceptions <a id="try-except"></a>
966
967 Exceptions can be handled using the `try` and `except` keywords. When an exception occurs while executing code in the
968 `try` clause no further statements in the `try` clause are evaluated and the `except` clause is executed instead.
969
970 Example:
971
972     try {
973         throw "Test"
974
975         log("This statement won't get executed.")
976     } except {
977         log("An error occurred in the try clause.")
978     }
979
980 ## Breakpoints <a id="breakpoints"></a>
981
982 The `debugger` keyword can be used to insert a breakpoint. It may be used at any place where an assignment would also be a valid expression.
983
984 By default breakpoints have no effect unless Icinga is started with the `--script-debugger` command-line option. When the script debugger is enabled Icinga stops execution of the script when it encounters a breakpoint and spawns a console which lets the user inspect the current state of the execution environment.
985
986 ## Types <a id="types"></a>
987
988 All values have a static type. The `typeof` function can be used to determine the type of a value:
989
990     typeof(3) /* Returns an object which represents the type for numbers */
991
992 The following built-in types are available:
993
994 Type       | Examples          | Description
995 -----------|-------------------|------------------------
996 Number     | 3.7               | A numerical value.
997 Boolean    | true, false       | A boolean value.
998 String     | "hello"           | A string.
999 Array      | [ "a", "b" ]      | An array.
1000 Dictionary | { a = 3 }         | A dictionary.
1001
1002 Depending on which libraries are loaded additional types may become available. The `icinga`
1003 library implements a whole bunch of other [object types](09-object-types.md#object-types),
1004 e.g. Host, Service, CheckCommand, etc.
1005
1006 Each type has an associated type object which describes the type's semantics. These
1007 type objects are made available using global variables which match the type's name:
1008
1009     /* This logs 'true' */
1010     log(typeof(3) == Number)
1011
1012 The type object's `prototype` property can be used to find out which methods a certain type
1013 supports:
1014
1015     /* This returns: ["contains","find","len","lower","replace","reverse","split","substr","to_string","trim","upper"] */
1016     keys(String.prototype)
1017
1018 Additional documentation on type methods is available in the
1019 [library reference](18-library-reference.md#library-reference).
1020
1021 ## Location Information <a id="location-information"></a>
1022
1023 The location of the currently executing script can be obtained using the
1024 `current_filename` and `current_line` keywords.
1025
1026 Example:
1027
1028     log("Hello from '" + current_filename + "' in line " + current_line)
1029
1030 ## Reserved Keywords <a id="reserved-keywords"></a>
1031
1032 These keywords are reserved and must not be used as constants or custom attributes.
1033
1034     object
1035     template
1036     include
1037     include_recursive
1038     include_zones
1039     library
1040     null
1041     true
1042     false
1043     const
1044     var
1045     this
1046     globals
1047     locals
1048     use
1049     default
1050     ignore_on_error
1051     current_filename
1052     current_line
1053     apply
1054     to
1055     where
1056     import
1057     assign
1058     ignore
1059     function
1060     return
1061     break
1062     continue
1063     for
1064     if
1065     else
1066     while
1067     throw
1068     try
1069     except
1070     in
1071     using
1072     namespace
1073
1074 You can escape reserved keywords using the `@` character. The following example
1075 tries to set `vars.include` which references a reserved keyword and generates
1076 an error:
1077
1078     [2014-09-15 17:24:00 +0200] critical/config: Location:
1079     /etc/icinga2/conf.d/hosts/localhost.conf(13):   vars.sla = "24x7"
1080     /etc/icinga2/conf.d/hosts/localhost.conf(14):
1081     /etc/icinga2/conf.d/hosts/localhost.conf(15):   vars.include = "some cmdb export field"
1082                                                          ^^^^^^^
1083     /etc/icinga2/conf.d/hosts/localhost.conf(16): }
1084     /etc/icinga2/conf.d/hosts/localhost.conf(17):
1085
1086     Config error: in /etc/icinga2/conf.d/hosts/localhost.conf: 15:8-15:14: syntax error, unexpected include (T_INCLUDE), expecting T_IDENTIFIER
1087     [2014-09-15 17:24:00 +0200] critical/config: 1 errors, 0 warnings.
1088
1089 You can escape the `include` keyword by prefixing it with an additional `@` character:
1090
1091     object Host "localhost" {
1092       import "generic-host"
1093
1094       address = "127.0.0.1"
1095       address6 = "::1"
1096
1097       vars.os = "Linux"
1098       vars.sla = "24x7"
1099
1100       vars.@include = "some cmdb export field"
1101     }