Search code examples
stringpowershellfunctionparametersswitch-statement

How to convert a string that currently has a switch parameter into a function in powershell


I have a string like this:

"CleanUp -All"

How do you convert it into a callable function in PowerShell including the switch?

I tried calling "&" in front of the entire string.

I tried splitting up the string into parts and calling them together.

I used the "&" to call the first part of the string "CleanUp" into a function but I don't know how to convert the switch parameter to use it.


Solution

    • A string containing a command line - i.e. a command name/path plus arguments - can not be invoked with &, the call operator - & only operates solely on a command name/path, requiring any arguments to be passed separately - see this answer.

    • While you can use Invoke-Expression to execute a string containing an entire command line:

      • Use of Invoke-Expression (iex) is best avoided in general.

      • Such an invocation (iex 'CleanUp -All') does not act like a function in two respects:

        • It requires renewed parsing of the command line in repeat invocations.

        • It doesn't accept additional arguments - unless you use string interpolation to make them part of the string passed to iex.

    • The better solution is to create a script block, which is only parsed once and can be re-invoked on demand with & (or, if the intent is to directly execute in the caller's scope, with ., the dot-sourcing operator):

      # Create a script block from the command-line string, which you can
      # invoke on demand with & or . - e.g.: & $sb
      $sb = [scriptblock]::Create('CleanUp -All')
      
      • If you additionally want to support pass-through arguments, append @args to the command-line string:

        $sb = [scriptblock]::Create('CleanUp -All' + ' @args')
        
      • If you want to create an actual, named function, Invoke-Expression is the simplest solution, after all:

        # Define function 'Foo' which calls CleanUp -All with pass-through
        # arguments, if any.
        iex ('function Foo { ' + 'CleanUp -All' + ' @args }')