This function allows to choose one out of two expressions based on a
condition. It provides a functionality similar to the
... ? ... : ...
operator known from some
programming languages.
Unlike a case
or match
statement, the
if()
can be embedded into other functions and
expressions.
Parameter | Type | Required | Default | Description |
---|---|---|---|---|
as | string | optional[a] | _if | The name of the output destination field. |
condition [b] | expression | required | The conditional expression to evaluate. | |
else | expression | required | The alternative statement to execute. | |
then | expression | required | The consequent statement to execute. | |
[a] Optional parameters use their default value unless explicitly set |
Omitted Argument NamesThe argument name for
condition
can be omitted; the following forms of this function are equivalent:logscaleif("value",then="value",else="value")
and:
logscaleif(condition="value",then="value",else="value")
These examples show basic structure only; full examples are provided below.
The behavior of:
if(cond, then=onTrue, else=onFalse, as=y)
is equivalent to a case expression:
case {
test(cond) | y := onTrue;
y := onFalse
}
In particular:
The interpretation of
condition
is the same as theexpression
argument oftest()
.The evaluation of
then
/else
arguments is the same as the evaluation of the right-hand side of:=
.
The if()
function:
if()
Examples
Add a Field Based on Values of Another Field — Example 1
| statusClass :=
if(regex("^1", field=statuscode), then="informational", else=
if(regex("^2", field=statuscode), then="successful", else=
if(regex("^3", field=statuscode), then="redirection", else=
if(regex("^4", field=statuscode), then="client error", else=
if(regex("^5", field=statuscode), then="server error", else=
"unknown")))))
Nested if()
functions can be used within a
larger expression for adding a field whose value is calculated
based on another field.
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Add a statusClass field where the following conditions are set:
If the value of field statuscode begins with
1
, then statusClass is labeled asinformational
, otherwise:If the value of field statuscode begins with
2
, then statusClass is labeled assuccessful
, otherwise:If the value of field statuscode begins with
3
, then statusClass is labeled asredirection
, otherwise:If the value of field statuscode begins with
4
, then statusClass is labeled asclient error
, otherwise:If the value of field statuscode begins with
5
, then statusClass is labeled asserver error
, otherwise it is labeled asunknown
.
logscale| statusClass := if(regex("^1", field=statuscode), then="informational", else= if(regex("^2", field=statuscode), then="successful", else= if(regex("^3", field=statuscode), then="redirection", else= if(regex("^4", field=statuscode), then="client error", else= if(regex("^5", field=statuscode), then="server error", else= "unknown")))))
Event Result set
Nested if() functions for tagging a field according to different statuscode values.
Add a Field Based on Values of Another Field — Example 2
| success := if(status >= 500, then=0, else=if(status == 404, then=0, else=1))
Another example of nested if()
functions:
this is used to add a field success whose
value is calculated based on field status.
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Add a success field at the following conditions:
Set the value of field success to
0
if status is greater or equal to500
or if it's equal to400
, otherwise:Set the value of field success to
1
.
logscale| success := if(status >= 500, then=0, else=if(status == 404, then=0, else=1))
Event Result set
Nested if() functions for tagging a field according to different status values.
Add a Field Based on Values of Another Field — Example 3
| success := if(status < 500, then=if(status!=404, then=1, else=0), else=0)
Another example of nested if()
functions to
add a field success and calculate its value
based on field status.
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Add a success field at the following conditions:
logscale| success := if(status < 500, then=if(status!=404, then=1, else=0), else=0)
Event Result set
Nested if() functions for tagging a field according to different status values.
Calculate a Percentage of Successful Status Codes Over Time
| success := if(status >= 500, then=0, else=1)
| timechart(series=customer,function=
[
{
[sum(success,as=success),count(as=total)]
| pct_successful := (success/total)*100
| drop([success,total])}],span=15m,limit=100)
Calculate a percentage of successful status codes inside the
timeChart()
function field.
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} 1{{Aggregate}} 2{{Aggregate}} 3[/Drop Field\] result{{Result Set}} repo --> 0 0 --> 1 1 --> 2 2 --> 3 3 --> result style 3 fill:#2ac76d; click 3 #functions-if-examples-if-8-3 style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Add a success field at the following conditions:
If the value of field status is greater than or equal to
500
, set the value of success to0
, otherwise to1
.
logscale| success := if(status >= 500, then=0, else=1)
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} 1{{Aggregate}} 2{{Aggregate}} 3[/Drop Field\] result{{Result Set}} repo --> 0 0 --> 1 1 --> 2 2 --> 3 3 --> result style 3 fill:#2ac76d; click 3 #functions-if-examples-if-8-3 style 1 fill:#ff0000,stroke-width:4px,stroke:#000;
Create a new timechart, generating a new series, customer that uses a compound function. In this example, the embedded function is generating an array of values, but the array values are generated by an embedded aggregate. The embedded aggregate (defined using the
{}
syntax), creates asum()
andcount()
value across the events grouped by the value of success field generated from the filter query. This is counting the1
1 or0
generated by theif()
function; counting all the values and adding up the ones for successful values. These values will be assigned to the success and total fields. Note that at this point we are still within the aggregate, so the two new fields are within the context of the aggregate, with each field being created for a corresponding success value.logscale| timechart(series=customer,function= [ { [sum(success,as=success),count(as=total)]
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} 1{{Aggregate}} 2{{Aggregate}} 3[/Drop Field\] result{{Result Set}} repo --> 0 0 --> 1 1 --> 2 2 --> 3 3 --> result style 3 fill:#2ac76d; click 3 #functions-if-examples-if-8-3 style 2 fill:#ff0000,stroke-width:4px,stroke:#000;
Calculate the percentage that are successful. We are still within the aggregate, so the output of this process will be an embedded set of events with the total and success values grouped by each original HTTP response code.
logscale| pct_successful := (success/total)*100
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} 1{{Aggregate}} 2{{Aggregate}} 3[/Drop Field\] result{{Result Set}} repo --> 0 0 --> 1 1 --> 2 2 --> 3 3 --> result style 3 fill:#2ac76d; click 3 #functions-if-examples-if-8-3 style 3 fill:#ff0000,stroke-width:4px,stroke:#000;
Still within the embedded aggregate, drop the total and success fields from the array generated by the aggregate. These fields were temporary to calculate the percentage of successful results, but are not needed in the array for generating the result set. Then, set a span for the buckets for the events of 15 minutes and limit to 100 results overall.
logscale| drop([success,total])}],span=15m,limit=100)
Event Result set
This query shows how an embedded aggregate can be used to generate a sequence of values that can be formatted (in this case to calculate percentages) and generate a new event series for the aggregate values.
Convert Timestamps Based on Accuracy
errortime := if((@ingesttimestamp > @timestamp), then=@timestamp, else=@ingesttimestamp) / 1000
When parsing and processing data, the time of the data can be critical, and not all events include an explicit @timestamp field, but the ingest time stamp, when the event was parsed by LogScale, can be a suitable proxy. The lack of timestamp, or a significant difference between the timestamps may result in displaying an empty value (or creating an event stream that cannot be summarized in a graph).
Step-by-StepStarting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
The event field errortime is set to the latest time value, either timestamp or @ingesttimestamp.
logscaleerrortime := if((@ingesttimestamp > @timestamp), then=@timestamp, else=@ingesttimestamp) / 1000
Event Result set
Determine a Score Based on Field Value
percentile(filesize, percentiles=[40,80],as=score)
| symbol := if(filesize > score_80, then=":+1:", else=if(filesize > score_40, then="so-so", else=":-1:"))
When summarizing and displaying data, it may be necessary to
derive a score or validity based on a test value. This can be
achieved using if()
by creating the score
value if the underlying field is over a threshold value.
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{{Aggregate}} 1{Conditional} result{{Result Set}} repo --> 0 0 --> 1 1 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Calculate the
percentile()
for the filesize field and determine what filesize that is above 40% of the overall event set, and 80% of the overall event set.logscalepercentile(filesize, percentiles=[40,80],as=score)
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{{Aggregate}} 1{Conditional} result{{Result Set}} repo --> 0 0 --> 1 1 --> result style 1 fill:#ff0000,stroke-width:4px,stroke:#000;
Compare whether the filesize is greater than 80% of the events, setting symbol to
:+1:
. Becauseif()
functions can be embedded, theelse
parameter is anotherif()
statement that sets symbol toso-so
if the size is greater than 40%, or:+1:
otherwise.logscale| symbol := if(filesize > score_80, then=":+1:", else=if(filesize > score_40, then="so-so", else=":-1:"))
Event Result set
Using if()
is the best way to make
conditional choices about values. The function has the benefit
of being able to be embedded into other statements, unlike
case
.
Set a Field Value Based on Tag Value
keyprocess := if(#eventType == "Spawn", then=ChildID, else=ProcessID)
When processing event data, there are occasions when a value needs to be determined from another field in the event. In this example, the field keyprocess is populated based on the #eventType tag.
Step-by-StepStarting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
Using the
if()
, set the value of keyprocess to the value of the ChildID if #eventType isSpawn
; otherwise, set keyprocess to ProcessID.logscalekeyprocess := if(#eventType == "Spawn", then=ChildID, else=ProcessID)
Event Result set
Using if()
provides a simplified way of
processing and parsing data when the test value can be easily
identified.
In this example, the process ID has been identified based on whether it is the original or a spawn (child) process.
Use Multiple if() Functions
score := if(x != "N/A", then=x, else=0) + if(y != "N/A", then=y, else=0)
Multiple if()
functions can be used in a
computation (eval/assign).
Starting with the source repository events
- flowchart LR; %%{init: {"flowchart": {"defaultRenderer": "elk"}} }%% repo{{Events}} 0{Conditional} result{{Result Set}} repo --> 0 0 --> result style 0 fill:#ff0000,stroke-width:4px,stroke:#000;
This computation checks if fields x or y is not a number, then
0
will be used instead.logscalescore := if(x != "N/A", then=x, else=0) + if(y != "N/A", then=y, else=0)
Event Result set
Setting the value based on an incoming value enables determination of a score triggered by a value.