# Using values from an array as field names to contain values from another array

**URL:** <https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478>\
**Category:** Elasticsearch\
**Created:** [October 8, 2024, 6:22pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478 "2024-10-08T18:22:39Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![ccweirsw](https://avatars.discourse-cdn.com/v4/letter/c/f04885/32.png) [@ccweirsw](https://discuss.elastic.co/u/ccweirsw)\
**Post date:** [October 8, 2024, 6:22pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/1 "2024-10-08T18:22:40Z")

</div>

I am ingesting event logs from Office 365. Some of these documents contain objects that look like this:

```auto
"DeviceProperties": [
          {
            "Value": "Windows10",
            "Name": "OS"
          },
          {
            "Value": "Edge",
            "Name": "BrowserType"
          },
          {
            "Value": "some-uuid-here",
            "Name": "SessionId"
          }
        ],

```

What I am trying to do is map or (if required) modify this so that queries like

```auto
o365.audit.DeviceProperties.SessionId:"some-uuid-here"
o365.audit.DeviceProperties.OS:"Windows10"
o365.audit.DeviceProperties.BrowserType:"Edge"

```

work the way I'd (naively) expect them to. Neither nested or flattened field types seem to handle this correctly by default. Is there some way to associate the "Name" property as a subfield name with the corresponding "Value" in each object?

---

<div class="post-metadata">

**Author:** ![RabBit\_BR](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/rabbit_br/32/82261_2.png) [@RabBit\_BR](https://discuss.elastic.co/u/RabBit_BR)\
**Post date:** [October 8, 2024, 6:50pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/2 "2024-10-08T18:50:53Z")

</div>

Hi @ccweirsw

I believe that using flattend or nested you would have to combine each pair of properties in your query.

```auto
     {
          "term": {
            "DeviceProperties.Name": {
              "value": "OS"
            }
          }
        },
        {
          "term": {
            "DeviceProperties.Value": {
              "value": "Windows10"
            }
          }
        }

```

Another option that is close to the way you want to search would be indexing as below:

```auto
{
  "DeviceProperties": {
    "OS": "Windows10",
    "BrowserType": "Edge",
    "SessionId": "some-uuid-here"
  }
}

```

---

<div class="post-metadata">

**Author:** ![ccweirsw](https://avatars.discourse-cdn.com/v4/letter/c/f04885/32.png) [@ccweirsw](https://discuss.elastic.co/u/ccweirsw)\
**Post date:** [October 8, 2024, 9:51pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/3 "2024-10-08T21:51:36Z")

</div>

Are you saying that modifying the source document to look more like that is what would be needed? Any suggestions on an efficient way to do that at ingest time?

Thanks

---

<div class="post-metadata">

**Author:** ![RabBit\_BR](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/rabbit_br/32/82261_2.png) [@RabBit\_BR](https://discuss.elastic.co/u/RabBit_BR)\
**Post date:** [October 9, 2024, 11:11am UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/4 "2024-10-09T11:11:01Z")

</div>

Yes, because the way it is indexed you will not be able to perform the queries, confirm below:

> [@ccweirsw](#):
>
> ```auto
> o365.audit.DeviceProperties.SessionId:"some-uuid-here"
> o365.audit.DeviceProperties.OS:"Windows10"
> o365.audit.DeviceProperties.BrowserType:"Edge"
> 
> ```

> [@ccweirsw](#):
>
> Any suggestions on an efficient way to do that at ingest time?

How do you ingest this data?

---

<div class="post-metadata">

**Author:** ![ccweirsw](https://avatars.discourse-cdn.com/v4/letter/c/f04885/32.png) [@ccweirsw](https://discuss.elastic.co/u/ccweirsw)\
**Post date:** [October 9, 2024, 1:45pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/5 "2024-10-09T13:45:44Z")

</div>

Logs are ingested from Filebeat.

I think I have a solution to this that uses pipeline processors that I'll post when I've tested it properly. Your comment helped me realize I had to modify the source if I was going to get the behavior I wanted.

---

<div class="post-metadata">

**Author:** ![ccweirsw](https://avatars.discourse-cdn.com/v4/letter/c/f04885/32.png) [@ccweirsw](https://discuss.elastic.co/u/ccweirsw)\
**Post date:** [October 15, 2024, 2:58pm UTC](https://discuss.elastic.co/t/using-values-from-an-array-as-field-names-to-contain-values-from-another-array/368478/6 "2024-10-15T14:58:44Z")

</div>

```auto
{
    "foreach": {
      "field": "o365.audit.DeviceProperties",
      "processor": {
        "set": {
          "field": "_temp_.DeviceProperties.{{{_ingest._value.Name}}}",
          "value": "{{{_ingest._value.Value}}}"
        }
      },
      "tag": "deviceproperties-rewrite",
      "ignore_failure": true,
      "description": "Copies key:value pairs out of o365.audit.DeviceProperties to a temp field"
    }
  },
  {
    "remove": {
      "field": "o365.audit.DeviceProperties",
      "ignore_missing": true,
      "tag": "deviceproperties-remove-original"
    }
  },
  {
    "rename": {
      "field": "_temp_.DeviceProperties",
      "target_field": "o365.audit.DeviceProperties",
      "ignore_missing": true,
      "tag": "deviceproperties-rename",
      "description": "Copy the new key:value structure back to the original field"
    }
  },

```

This is an excerpt of the ingest pipeline that solved the issue. Just uses a foreach processor to copy all the field names and values I want to a temp field, remove the original one, and then copy the data back in the format I want to use.
