skip to Main Content

I have a question about refactoring a function that calls other async functions depending on a variable. Currently, I am using a switch case statement and the name of the variable is the same as the name of the function. Here is an example of the current implementation:

const option = "create";

const create = async(req, res) => {
  // do create stuff
}

const update = async(req, res) => {
  // do update stuff
}

// etc.

switch (option) {
  case "create": {
    return await create(req, res);
  }
  case "update": {
    return await update(req, res);
  }
  default: {
    return res.status(500).json({ message: "Unable to process your request" });
  }
} 

Since the name of the option variable is always the same as the name of the function, I am wondering if there is a way to dynamically call the function based on the value of the option variable without the need for the switch case statement since it appears to be alot of repetition especially with the variable name and method name matching.

3

Answers


  1. Option 1: eval

    let add = (a, b) => a + b;
    let sub = (a, b) => a - b;
    
    let option = "add";
    
    console.log(eval(option)(2, 4));
    
    option = "sub";
    
    console.log(eval(option)(2, 4));

    Option 2: store references to your functions in an object.

    let add = (a, b) => a + b;
    let sub = (a, b) => a - b;
    
    let myFunctions = {
      add: add,
      sub: sub,
    }
    
    let option = "add";
    
    console.log(myFunctions[option](2, 4));
    
    option = "sub";
    
    console.log(myFunctions[option](2, 4));
    Login or Signup to reply.
  2. Unlike variables, you actually can access the name of a function in Javascript:

    function testFn() {
      console.log('hello world');
    }
    
    console.log(`The function's name is ${testFn.name}`);

    So in theory, you could do something like this:

    const create = (req, res) => {
      console.log('create');
    }
    
    const update = (req, res) => {
      console.log('update');
    }
    
    const fns = [create, update];
    
    function callFns(option) {
      const matchedFn = fns.find((fn) => fn.name === option);
      matchedFn();
    }
    
    callFns('update')

    However, since they will always match, storing them in a hash would be cleaner/more readable code and be more performant as it doesn’t require looping through an array:

    const create = (req, res) => {
      console.log('create');
    }
    
    const update = (req, res) => {
      console.log('update');
    }
    
    const fns = {create, update};
    
    function callFns(option) {
      fns[option]();
    }
    
    callFns('update')
    Login or Signup to reply.
  3. One way is to create an object of the possible values of option, and based on the values corresponding functions will be called.

    Demo:

    const option = "create";
    
    const create = async (req, res) => {
      console.log("create function called");
      // do create stuff
    };
    
    const update = async (req, res) => {
      console.log("update function called");
      //do update stuff
    };
    
    const optionFunctions = {
      create,
      update
    }
    
    async function processRequest(req, res) {
      if (option in optionFunctions) {
        const selectedFunction = optionFunctions[option];
        await selectedFunction(req, res);
      } else {
        res.status(500).json({ message: "Unable to process your request" });
      }
    }
    
    //test
    processRequest({}, {});
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search