# Dynamic field name with ruby

**URL:** <https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899>\
**Category:** Logstash\
**Created:** [February 25, 2019, 7:49pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899 "2019-02-25T19:49:32Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![camilisette](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/camilisette/32/68079_2.png) [@camilisette](https://discuss.elastic.co/u/camilisette)\
**Post date:** [February 25, 2019, 7:49pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/1 "2019-02-25T19:49:32Z")

</div>

I have a curl response that looks like this.

> {  
> "tables": [  
> {  
> "name": "PrimaryResult",  
> "columns": [  
> {  
> "name": "Category",  
> "type": "string"  
> },  
> {  
> "name": "count\_",  
> "type": "long"  
> }  
> ],  
> "rows": [  
> [  
> "Administrative",  
> 111651142  
> ],  
> [  
> "Recommendation",  
> 5846  
> ],  
> [  
> "Policy",  
> 15664560  
> ],  
> [  
> "Alert",  
> 110135  
> ],  
> [  
> "Security",  
> 2101  
> ],  
> [  
> "Autoscale",  
> 27  
> ]  
> ]  
> }  
> ]  
> }

I am able to extract individual events by using this configuration:

```
input {
  exec {
    command => "curl -X POST 'https://api.loganalytics.io/v1/workspaces/DEMO_WORKSPACE/query' -d '{\"query\": \"AzureActivity | summarize count() by Category\"}' -H 'x-api-key: DEMO_KEY' -H 'Content-Type: application/json'"
    interval => 60
    type => "json"
  }
}

filter{
  json { source => "message" }
  split { field => "[tables][0][rows]" }
  mutate {
    add_field => {
      "%{[tables][0][columns][0][name]}" => "%{[tables][0][rows][0]}"
      "%{[tables][0][columns][1][name]}" => "%{[tables][0][rows][1]}"
    }
    remove_field => ["tables","message","command"]
  }
}

output {
  stdout { codec => "rubydebug" }
}

```

How do I modify this so that it will add fields dynamically? I saw that this can be done through ruby filter but I'm not familiar with ruby.

---

<div class="post-metadata">

**Author:** ![Badger](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/badger/32/25190_2.png) [@Badger](https://discuss.elastic.co/u/Badger)\
**Post date:** [February 25, 2019, 8:32pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/2 "2019-02-25T20:32:53Z")

</div>

> [@camilisette](#):
>
> How do I modify this so that it will add fields dynamically?

What do you want the output to look like?

Also, why do you do the split?

---

<div class="post-metadata">

**Author:** ![camilisette](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/camilisette/32/68079_2.png) [@camilisette](https://discuss.elastic.co/u/camilisette)\
**Post date:** [February 25, 2019, 8:38pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/3 "2019-02-25T20:38:18Z")

</div>

Expected results would be something like this,

> {  
> "count\_" =\> "5846",  
> "type" =\> "json",  
> "Category" =\> "Recommendation",  
> "@version" =\> "1",  
> "@timestamp" =\> 2019-02-25T20:35:03.667Z,  
> "host" =\> "elk-stack-logstash"  
> }  
> {  
> "count\_" =\> "110135",  
> "type" =\> "json",  
> "Category" =\> "Alert",  
> "@version" =\> "1",  
> "@timestamp" =\> 2019-02-25T20:35:03.667Z,  
> "host" =\> "elk-stack-logstash"  
> }  
> {  
> "count\_" =\> "2099",  
> "type" =\> "json",  
> "Category" =\> "Security",  
> "@version" =\> "1",  
> "@timestamp" =\> 2019-02-25T20:35:03.667Z,  
> "host" =\> "elk-stack-logstash"  
> }  
> {  
> "count\_" =\> "27",  
> "type" =\> "json",  
> "Category" =\> "Autoscale",  
> "@version" =\> "1",  
> "@timestamp" =\> 2019-02-25T20:35:03.667Z,  
> "host" =\> "elk-stack-logstash"  
> }

Each row is one event and the value of it is matched to its column name.

I used split to split each row as a separate event.

---

<div class="post-metadata">

**Author:** ![Badger](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/badger/32/25190_2.png) [@Badger](https://discuss.elastic.co/u/Badger)\
**Post date:** [February 25, 2019, 8:44pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/4 "2019-02-25T20:44:33Z")

</div>

That's what your existing filter produces. What is the point of implementing in Ruby?

---

<div class="post-metadata">

**Author:** ![camilisette](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/camilisette/32/68079_2.png) [@camilisette](https://discuss.elastic.co/u/camilisette)\
**Post date:** [February 25, 2019, 9:01pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/5 "2019-02-25T21:01:32Z")

</div>

Because there's a possibility that there will be more columns that what I define. So I wanted to use ruby to add fields dynamically.

---

<div class="post-metadata">

**Author:** ![Badger](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/badger/32/25190_2.png) [@Badger](https://discuss.elastic.co/u/Badger)\
**Post date:** [February 25, 2019, 9:03pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/6 "2019-02-25T21:03:52Z")

</div>

> [@camilisette](#):
>
> "%{[tables][0][columns][0][name]}" =\> "%{[tables][0][rows][0]}"  
> "%{[tables][0][columns][1][name]}" =\> "%{[tables][0][rows][1]}"

So you want to include [2], [3] etc. if they exist?

---

<div class="post-metadata">

**Author:** ![camilisette](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/camilisette/32/68079_2.png) [@camilisette](https://discuss.elastic.co/u/camilisette)\
**Post date:** [February 25, 2019, 9:21pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/7 "2019-02-25T21:21:16Z")

</div>

Yes. So I wont need to manually define in the case that there would be more columns.

---

<div class="post-metadata">

**Author:** ![Badger](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/badger/32/25190_2.png) [@Badger](https://discuss.elastic.co/u/Badger)\
**Post date:** [February 25, 2019, 10:06pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/8 "2019-02-25T22:06:27Z")

</div>

Try

```
    split { field => "[tables][0][rows]" }
    ruby {
        code => '
            rows = event.get("[tables][0][rows]")
            cols = event.get("[tables][0][columns]")
            rows.each_index { |i|
                v = rows[i]
                k = cols[i]["name"]
                event.set(k,v)
            }
        '
    }

```

Error handling is left as an exercise for the reader.

---

<div class="post-metadata">

**Author:** ![system](https://us1.discourse-cdn.com/elastic/original/3X/1/a/1ac57faf039f6b580b3f104ef42a2a89e41014de.png) [@system](https://discuss.elastic.co/u/system)\
**Post date:** [March 25, 2019, 10:06pm UTC](https://discuss.elastic.co/t/dynamic-field-name-with-ruby/169899/9 "2019-03-25T22:06:34Z")

</div>

This topic was automatically closed 28 days after the last reply. New replies are no longer allowed.
