Defining bash function dynamically using eval

6,647

Solution 1

Escaping $ should be enough to make this work:

eval "parent_function() { echo \$(delegate_function); }"

Solution 2

In bash, like in most languages, eval is something to avoid. See, for example, Greg's FAQ: Eval command and security issues

You can define parent_function like this:

parent_function=delegate_function

Anytime that you want to use parent_function to dispatch delegate_function, just run:

$ $parent_function
output from delegate

Example of dynamic function update

Let's define delegate_function and parent_function and run $parent_function:

$ delegate_function() { echo "delegate version 1"; }
$ parent_function=delegate_function
$ $parent_function
delegate version 1

Now let's change delegate_function and run $parent_function again:

$ delegate_function() { echo "delegate version 2"; }
$ $parent_function
delegate version 2

$parent_function instantly updates to run the new version of delegate_function.

Example of dynamic choice of name

Let's create our delegate function:

$ delegate_function() { echo "delegate function executed"; }

Let's assign some name:

$ parent_function=some_name

Now, let's demonstrate dynamic assignment of that name:

$ typeset $parent_function=delegate_function
$ $some_name
delegate function executed
Share:
6,647

Related videos on Youtube

Benny Abramovici
Author by

Benny Abramovici

Developer who enjoys sharing knowledge. https://ksharma.dev Open source projects: Github

Updated on September 18, 2022

Comments

  • Benny Abramovici
    Benny Abramovici almost 2 years

    I'm trying to define a bash function dynamically using following code:

    delegate_function() { echo "output from delegate"; }
    eval "parent_function() { echo $(delegate_function); }"
    

    The intent is to have parent function dynamically dispatch to the delegate when executed. However due to the way eval works my function is being defined as follows:

    kshitiz:/tmp$ type parent_function
    parent_function is a function
    parent_function () 
    { 
        echo output from delegate
    }
    

    How can I instead have the definition as:

     parent_function () 
     { 
         echo $(delegate_function);
     }
    

    Is there a way to escape some part of the string from being evaluated by eval?

  • Wildcard
    Wildcard about 8 years
    That link should be trumpeted far and wide; thanks for providing it.
  • Benny Abramovici
    Benny Abramovici about 8 years
    Though I appreciate the warning about pitfalls of eval, this does not satisfy my requirements as it hard codes the parent function name, while I need it to be dynamic. adonis' answer provides the right solution.
  • Benny Abramovici
    Benny Abramovici about 8 years
    @John1024 Sorry what I meant is that parent_function is hardcoded in code. Its name should come from contents of a variable. Sometimes grandpa_function other times xt738_function.
  • Benny Abramovici
    Benny Abramovici about 8 years
    Background: I want to automatically define shell based wrappers for my golang functions. My shell script will scan a directory for golang files, read the function names and then define bash functions with same names that internally invoke the golang functions. There's no security risk here as I'm not evaluating user input, just defining a convenient means to access my own golang functions.