# Best way of adding a value to global context array of objects

**URL:** <https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185>\
**Category:** General\
**Tags:** function-node\
**Created:** [1 January 2024 20:45 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185 "2024-01-01T20:45:35Z")\
**Posts on this page:** 12\
**Page:** 1

<div class="post-metadata">

**Author:** ![novski](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/novski/32/23243_2.png) [@novski](https://discourse.nodered.org/u/novski)\
**Post date:** [1 January 2024 20:45 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/1 "2024-01-01T20:45:35Z")

</div>

I have an array of objects (one property is the hostname of the device) stored in my global context.  
Now I would like to ping some of them and store the value of roundtrip in ms to it's to the related object.  
What is the best solution to do so?

I read a lot about `.map()` and `.forEach()` and the fact that I don't need to recreate the whole context array, but just add that property to an object in the array confuses me on how to do it best.  
Moreover, I am a bit worried about doing that every let's say 60s on my rpi4.

Is it safe to just itter over the array with an for loop and add that property where the hostname matches?

```auto
let hosts = global.get('hosts');
for (let i = 0; i < hosts.length; i++) {
    var e = hosts[i];
    if(e.host === msg.topic){
        global.set('hosts['+i+'].ping', msg.payload)
    }
}

```

---

<div class="post-metadata">

**Author:** ![ralphwetzel](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/ralphwetzel/32/53713_2.png) [@ralphwetzel](https://discourse.nodered.org/u/ralphwetzel)\
**Post date:** [1 January 2024 21:01 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/2 "2024-01-01T21:01:25Z")

</div>

Assuming you did a

```auto
const hosts = global.get("hosts")

```

at the beginning of your script, this

> [@novski](#):
>
> ` global.set('hosts['+i+'].ping', msg.payload)`

doesn't work. It is as easy as

```auto
e.ping = msg.payload

```

to put the new ping value back in the object.

Why? `const hosts = global.get("hosts")` puts a reference to the array stored in `global` context into `hosts`. `e` already is the array element you intend to update & again a reference. Thus you're directly updating the object stored in the array stored in `global` context. This is quite elegant - as long as you're aware what you're doing.

---

<div class="post-metadata">

**Author:** ![GogoVega](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/gogovega/32/71313_2.png) [@GogoVega](https://discourse.nodered.org/u/GogoVega)\
**Post date:** [1 January 2024 21:08 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/3 "2024-01-01T21:08:01Z")

</div>

Something like:

```js
const hosts = global.get('hosts') || [];
let changed = false;

const newHosts = hosts.map((h) => {
  if (h.host !== msg.topic) return;
  h.ping = msg.payload;
  changed = true;
});

if (changed) global.set('hosts', newHosts);

```

Whether you use a for loop or map method, in both cases you create a variable

---

<div class="post-metadata">

**Author:** ![novski](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/novski/32/23243_2.png) [@novski](https://discourse.nodered.org/u/novski)\
**Post date:** [2 January 2024 07:19 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/4 "2024-01-02T07:19:17Z")

</div>

That is indeed very elegant. I read a lot about those references but knowing where they happen seams like mysterious magic knowledge to me.

> [@novski](#):
>
> `global.set('hosts['+i+'].ping', msg.payload)`

this actually works.  
But as you say, it's somehow not elegant at all…

---

<div class="post-metadata">

**Author:** ![ralphwetzel](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/ralphwetzel/32/53713_2.png) [@ralphwetzel](https://discourse.nodered.org/u/ralphwetzel)\
**Post date:** [2 January 2024 08:57 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/5 "2024-01-02T08:57:50Z")

</div>

> [@novski](#):
>
> this actually works

👍 You're absolutely right; it does.  
That's the beauty of Node-RED; full of great user-friendly functionality... !

---

<div class="post-metadata">

**Author:** ![jbudd](https://avatars.discourse-cdn.com/v4/letter/j/5f8ce5/32.png) [@jbudd](https://discourse.nodered.org/u/jbudd)\
**Post date:** [2 January 2024 11:47 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/6 "2024-01-02T11:47:21Z")

</div>

> [@novski](#):
>
> I have an array of objects (one property is the hostname of the device)

Wouldn't this be simpler if your global context was an object (the key is the hostname of the device) instead of an array?

```auto
let hosts = global.get'hosts') || {}
hosts[msg.topic].ping = msg.payload
global.set ('hosts', hosts}

```

---

<div class="post-metadata">

**Author:** ![E1cid](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/e1cid/32/77971_2.png) [@E1cid](https://discourse.nodered.org/u/E1cid)\
**Post date:** [2 January 2024 13:04 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/7 "2024-01-02T13:04:10Z")

</div>

jbudd, but would be simpler to use a change node, and no code required at all.

 ![chrome_screenshot_2 Jan 2024 13_01_08 GMT](https://us1.discourse-cdn.com/flex026/uploads/nodered/original/3X/2/2/22dd68748d381a536b9cf1df5757a67ddc52a019.png)

@novski You could also add the host name to the object and return an array of objects if an array is required.

 ![chrome_screenshot_2 Jan 2024 13_07_49 GMT](https://us1.discourse-cdn.com/flex026/uploads/nodered/original/3X/7/f/7fac070425becb6741f711bdf5fb5f5749fdb4cd.png)

```auto
[{"id":"e44b7242b3d23e14","type":"inject","z":"d1395164b4eec73e","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"192.168.1.24","payload":"24","payloadType":"num","x":480,"y":2760,"wires":[["dce3b25a146989d2"]]},{"id":"dce3b25a146989d2","type":"change","z":"d1395164b4eec73e","name":"","rules":[{"t":"set","p":"host[msg.topic].ping","pt":"flow","to":"payload","tot":"msg"},{"t":"set","p":"host[msg.topic].host","pt":"flow","to":"topic","tot":"msg"},{"t":"set","p":"payload","pt":"msg","to":"[$flowContext(\"host\").*]","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":480,"y":2840,"wires":[["fcb4735590df7d69"]]},{"id":"fcb4735590df7d69","type":"debug","z":"d1395164b4eec73e","name":"debug 2461","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":670,"y":2840,"wires":[]}]

```

---

<div class="post-metadata">

**Author:** ![novski](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/novski/32/23243_2.png) [@novski](https://discourse.nodered.org/u/novski)\
**Post date:** [6 January 2024 13:30 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/8 "2024-01-06T13:30:15Z")

</div>

My global.hosts is not an object but an array.

---

<div class="post-metadata">

**Author:** ![E1cid](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/e1cid/32/77971_2.png) [@E1cid](https://discourse.nodered.org/u/E1cid)\
**Post date:** [6 January 2024 13:33 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/9 "2024-01-06T13:33:14Z")

</div>

Yes we know that, we are pointing out that if you set it as an object it would be simple to add/alter it, and you can still pull an array of objects from it, if you also require an array for other things.

---

<div class="post-metadata">

**Author:** ![novski](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/novski/32/23243_2.png) [@novski](https://discourse.nodered.org/u/novski)\
**Post date:** [6 January 2024 13:48 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/10 "2024-01-06T13:48:25Z")

</div>

It's the incoming message that stores it as an array.  
It does not make sense to rearrange it every time it gets written as it is the fritzbox node that querries my dhcp active leases.

---

<div class="post-metadata">

**Author:** ![E1cid](https://sea2.discourse-cdn.com/flex026/user_avatar/discourse.nodered.org/e1cid/32/77971_2.png) [@E1cid](https://discourse.nodered.org/u/E1cid)\
**Post date:** [6 January 2024 13:51 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/11 "2024-01-06T13:51:48Z")

</div>

> [@novski](#):
>
> It does not make sense to rearrange it every time it gets written

That is not what we are suggesting. The suggestion is to store it all the time as an object as this is easier to write to with out searching as to what array element to write to. It is only a suggestion you may do as you want.

---

<div class="post-metadata">

**Author:** ![system](https://us1.discourse-cdn.com/flex026/uploads/nodered/original/1X/d073cd938eafa2e558d7c2cd59003b3ef4963033.png) [@system](https://discourse.nodered.org/u/system)\
**Post date:** [20 January 2024 13:51 UTC](https://discourse.nodered.org/t/best-way-of-adding-a-value-to-global-context-array-of-objects/84185/12 "2024-01-20T13:51:53Z")

</div>

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