1

Scenario: I am developing a chrome extension and I have a bunch of listeners I need to add in the foreground.

What I would like to do: create an object named 'listeners' containing only functions (functions that will run addListeners), and a function called 'init' that would iterate my 'listeners' object and dynamically execute every function.

Why: I would like to add new listeners to the object without worrying about having to call them directly one by one in my init function. I know it would not be too much of a hassle doing so but it would be interesting if I could make the thing more dynamic.

Is this possible?

Something like:

const listeners = {
    func1: function (){...},
    func2: function (){...},
    func3: function (){...}
}

function init(){
    for (let func in listeners){
        //somehow execute func

        //func() appearently does not work
        //()=>func appearently does not work
    }
}

init();

Diego Senra
  • 61
  • 1
  • 6
  • 1
    Does this answer your question? [Iterate through object properties](https://stackoverflow.com/questions/8312459/iterate-through-object-properties) or [How do I loop through or enumerate a JavaScript object?](https://stackoverflow.com/questions/684672/how-do-i-loop-through-or-enumerate-a-javascript-object) – Ivar Sep 07 '21 at 09:12
  • Why use object structure for listeners? I think array structure is handier in your case. – ikhvjs Sep 07 '21 at 09:14

4 Answers4

1

Try this:

const listeners = {
    func1: function () {
        console.log(1);
    },
    func2: function () {
        console.log(2);
    },
    func3: function () {
        console.log(3);
    }
}

function init() {
    for (let func in listeners) {
        listeners[func]();
    }
}

init();
angel.bonev
  • 2,154
  • 3
  • 20
  • 30
  • Thanks, that's what i needed! My problem was more conceptual about how a for in loop works, our friends above gave me a quick and good explanation – Diego Senra Sep 08 '21 at 09:09
1

The for...in loop iterates the keys of the object, so the func variable is a string, and not a function. To run the function use listeners[func]();.

You can use Object.values() to get an of functions, and then iterate it with for...of:

const listeners = {
  func1(){ console.log(1); },
  func2(){ console.log(2); },
  func3(){ console.log(3); }
}

function init(){
  for (const func of Object.values(listeners)){
    func()
  }
}

init();

Or do the same with Array.forEach():

const listeners = {
  func1(){ console.log(1); },
  func2(){ console.log(2); },
  func3(){ console.log(3); }
}

const init = () => Object.values(listeners).forEach(func => func())

init();
Ori Drori
  • 183,571
  • 29
  • 224
  • 209
  • Thanks, that's what i needed! My problem was more conceptual about how a for in loop works, thanks for the explanation and the array suggestion. – Diego Senra Sep 08 '21 at 09:08
1

you will just need to do it like that listeners[func]() in the loop , in for in loop, keys are the one iterated, so you call items like that obj/array[key] func in your case and while you have functions you need to add (). check inspect in this fiddler link

M. N
  • 11
  • 1
  • 5
  • Thanks, that's what i needed! My problem was more conceptual about how a for in loop works, thanks for the explanation. – Diego Senra Sep 08 '21 at 09:07
1

On top of the other answers. I think Array structure is more appropriate in your case.

const listeners = [
  function () {
    console.log(1);
  },
  function () {
    console.log(2);
  },
  function () {
    console.log(3);
  },
];

function init() {
  listeners.forEach(func => func());
}

init();
ikhvjs
  • 5,316
  • 2
  • 13
  • 36
  • Would you mind explaining why do you think an array would be a better option in this case? – Diego Senra Sep 08 '21 at 09:10
  • @DiegoSenra, you may ask yourself what are you going to achieve? If you want to iterate some items and you don't need to specify one item. Why don't you try to use an array to store all the items instead of object structure? The built-in JS array method is very easy to loop for items. – ikhvjs Sep 08 '21 at 09:17