Splunk Search

How do you use value or capture groups as regex's curly bracket number parameter?

mschaaf
Path Finder

In the code below, i want the explicit {5} to be replaced with a variable like {$session_length$}. Is this possible? If so, how? Thanks!

| makeresults 
| eval test="abc5defgHijk" 
| rex field=test "^.{3}(?<session_length>\d)(?<session>.{5})"
|fields session

I want the output of session="defgH".

1 Solution

arkadyz1
Builder

I'm with @ccl0utierk on this one - there is no way to grab that with just one rex command. You need a longer way: extract session_length first via eval or rex command first then use | eval session=substr(test,5,session_length) (where 5 is the position where session starts, 1-based so it skips the first 4 characters) to get the session.

View solution in original post

scombs
Path Finder

Here's another (late) solution.

| makeresults 
| eval test="abc5defgHijk" 
| eval session=substr( replace(test,"^.{3}\d",""),
    1, tonumber(replace(test,"^.{3}(\d).*","\1")) )
|fields session

 

0 Karma

woodcock
Esteemed Legend

Cool challenge; thanks!

0 Karma

woodcock
Esteemed Legend

Like this:

| makeresults 
| eval test="abc5defgHijk" 
| rex field=test "^.{3}(?<session_length>\d)"
| eval {session_length} = session_length
| foreach 1* 2* 3* 4* 5* 6* 7* 8* 9*
    [ rex field=test "^.{3}(?<session_length>\d)(?<session>.{<<FIELD>>})" ]
| fields - 0 1 2 3 4 5 6 7 8 9

arkadyz1
Builder

I'm with @ccl0utierk on this one - there is no way to grab that with just one rex command. You need a longer way: extract session_length first via eval or rex command first then use | eval session=substr(test,5,session_length) (where 5 is the position where session starts, 1-based so it skips the first 4 characters) to get the session.

ccl0utier
Splunk Employee
Splunk Employee

Indeed, this is where I was leading. 😉

0 Karma

woodcock
Esteemed Legend

Look at my solution. It actually works exactly as you would like, @mschaaf, without the downsides of this answer.

0 Karma

arkadyz1
Builder

Unless there are other fields in the original event, starting with a digit, correct?

I like the elegance of your answer, but what are the downsides of mine?

0 Karma

woodcock
Esteemed Legend

You have hard-coded the 5, mine gets it from a a field, which is what the OP, @mschaaf, was asking.

0 Karma

arkadyz1
Builder

No, I did not hard-code the length - 5 was the length of the prefix (.{3}\d)+1 (substr is 1-based), the other 5 gets taken from session_length - look closer :). My solution will take 'defg' from 'abc4defgHijk' - please check.
Here is a search I've just run:
| makeresults | eval test="abc4defgHijk" | rex field=test "^.{3}(?<session_length>\d)" | eval session=substr(test,5,session_length)

0 Karma

woodcock
Esteemed Legend

My mistake, I misread your solution. I see it now. I will delete my entire comment thread tomorrow. Thanks for setting me straight.

0 Karma

arkadyz1
Builder

No, please don't. It shows the weakness anyway: how do I make it more generic and calculate the starting offset instead of hard-coding it? I actually hate seeing those constants in the code. I'd say something like
| rex field=test "(?<prefix>.{3})(?<session_length>\d)" | eval session=substr(test,1+len(prefix)+len(session_length),session_length)
is more to my liking. How's that for a solution?

woodcock
Esteemed Legend

I like it just as much as mine. Let's UpVote eachother and agree to a draw.

0 Karma

arkadyz1
Builder

I upvoted yours quite some time ago. Also, it's not a competition - there is more than one way to do something, and it's great. I actually learned something from your answer - never used foreach command, nor {{session_length}} syntax, and just being aware of it is great.

0 Karma

woodcock
Esteemed Legend

Most people do not know that replace can take values out of fields for it's arguments. It is a very special command in that regard and a super powerful tool for this kind of thing.

0 Karma

ccl0utier
Splunk Employee
Splunk Employee

Mschaaf,

As far as I know, the REX command doesn't support a variable for the regex parameter. Can you give us an example of your data?
There might be other ways to do what you want to do?

0 Karma

Vijeta
Influencer

To get 'defgH" you can use below rex

rex field=test "\d{1}+(?<sub>.\S{3})"
0 Karma

arkadyz1
Builder

I downvoted this post because the answer is plain wrong - please test your suggestions before posting.
here is a search i ran to check your answer:
| makeresults | eval test="abc5defghijk" | rex field=test "\d{1}+(?<sub>.\s{3})"
you can change that digit 5 inside test to any other digit you want and sub will always be "defg".

0 Karma

Vijeta
Influencer

I see that. Thanks for letting me know .

0 Karma
Get Updates on the Splunk Community!

Enter the Splunk Community Dashboard Challenge for Your Chance to Win!

The Splunk Community Dashboard Challenge is underway! This is your chance to showcase your skills in creating ...

.conf24 | Session Scheduler is Live!!

.conf24 is happening June 11 - 14 in Las Vegas, and we are thrilled to announce that the conference catalog ...

Introducing the Splunk Community Dashboard Challenge!

Welcome to Splunk Community Dashboard Challenge! This is your chance to showcase your skills in creating ...