Splunk Search

Subsearch as eval expression works with strings, but not fields

Splunk Employee
Splunk Employee

I have a situation where I want to use a subsearch to resolve to a conditional expression in an if statement - a.k.a. eval x = [mysubsearch]using return.

When I return a string literal the eval works.

However, when return a field whose value is that same string the eval does not work.

Anybody know why or how to address this?

examples:

works:

search:
| makeresults | eval foo = [|makeresults | eval str = "if(1<2, 1, 0)" | return $str] | table foo

result:

`foo

1`

does not work:

search:
| makeresults | eval a = "if(1<2, 1, 0)", foo = [|makeresults | eval str = a | return $str] | table foo

result:
FATAL: Error in 'eval' command: Failed to parse the provided arguments. Usage: eval dest_key = expression

0 Karma
1 Solution

SplunkTrust
SplunkTrust

First, you need to understand when subsearches are performed. Basically, they are performed first, before the search they are part of.

Therefore, in your first (working) example, $str is returned by the subsearch, THEN the eval foo is performed.

In your second example, the subsearch is executed, but the token "a" has no value at all on the right side of the subsearch eval. The middle statement in the subsearch is therefore | eval str = |, which is invalid. (It is not interpreted the same as | eval str = null() | would have been.)

For certain kinds of subsearches, such as those created by map, you can have a token that is filled in from the outer search. Those tokens will have a $ before and after them. For instance, something like this would work, subject to the restrictions of map...

| makeresults 
| eval a = "if(1<2, 1, 0)" 
| map search="makeresults | eval foo = [|makeresults | eval str = $a$ | return $str] " 
| table foo

View solution in original post

SplunkTrust
SplunkTrust

First, you need to understand when subsearches are performed. Basically, they are performed first, before the search they are part of.

Therefore, in your first (working) example, $str is returned by the subsearch, THEN the eval foo is performed.

In your second example, the subsearch is executed, but the token "a" has no value at all on the right side of the subsearch eval. The middle statement in the subsearch is therefore | eval str = |, which is invalid. (It is not interpreted the same as | eval str = null() | would have been.)

For certain kinds of subsearches, such as those created by map, you can have a token that is filled in from the outer search. Those tokens will have a $ before and after them. For instance, something like this would work, subject to the restrictions of map...

| makeresults 
| eval a = "if(1<2, 1, 0)" 
| map search="makeresults | eval foo = [|makeresults | eval str = $a$ | return $str] " 
| table foo

View solution in original post

Splunk Employee
Splunk Employee

I do understand that point. Perhaps my confusion comes from this other scenario that someone shared:
| makeresults | eval a = "if(1<2, 1, 0)", foo = [|makeresults | eval str = "a" | return $str] | table foo

Which yields:

`foo

if(1<2, 1, 0)`

0 Karma

Splunk Employee
Splunk Employee

I'll just chalk that up to "strange occurrences"

0 Karma

SplunkTrust
SplunkTrust

Before the search executes, the subsearch in brackets executes and sets the value to the right of the equals sign to "a". The middle statement executed in the search thus reads...

| eval a = "if(1<2, 1, 0)", foo = a

Your output seems pretty reasonable for that code.

0 Karma

Splunk Employee
Splunk Employee

Mostly a guess, but I believe it is not working, because your subsearch is parsed before your outer eval assigns the value to field a, which results in your subsearch eval to be eval str = NULL.
If I change your search to | makeresults | eval a = "if(1<2, 1, 0)" | eval foo = [|makeresults | eval a = 123 | eval str = a | return $str] | table foo
the error disappears, because a is defined within the subsearch. Obviously, it doesn't have the outcome you are looking for.

Now, whether that is a bug or intended behavior, I cannot say.