Executing command from variable

I want to add an item to either the ipv4 or ipv6 address list and want to keep my script generic. Is it possible to do something like:

:local command "/ip/firewall/address-list/add"

or

:local command "/ipv6/firewall/address-list/add"

then

$command $args

or is the only way to do this with an :if statement?

is not called “command” but “function”, read MikroTik documentation about how create functions,
and this function requre at least two parameters like:

$function $addrListName $IP

Thanks for the correction, but I’m still not quite clear. Are you suggesting something like this?

:global fn do={
  :if ($v = 4) do={
    /ip/firewall/address-list/add address=$addr list=$list
  } else={
    /ipv6/firewall/address-list/add address=$addr list=$list
  }
}
$fn v=4 addr=1.2.34 list=foo
$fn v=6 addr=1::2 list=foo

So I still need an if statement rather than putting /ip/firewall/address-list in a variable?

You do not need any “:if” if you do not want…

:global fn4 do={ /ip firewall address-list add list=$1 address=$2 }
:global fn6 do={ /ipv6 firewall address-list add list=$1 address=$2 }

$fn4 “foo” 1.2.3.4
$fn4 “foo” 1.2.3.0/22
$fn6 “foo” 1:2:3:4::
$fn6 “foo” 1:2:3:4::/64

I see. However, that doesn’t actually simplify things. The point is I’m either in ipv4 mode or ipv6 mode and want to add the current address to either the ipv4 or ipv6 address list depending on which mode I’m in. Hence I wanted to put “/ip/firewall/address-list” or “/ipv6/firewall/address-list” into a variable (or similar) so that I could issue the appropriate one depending on which mode I’m in. It seem like I need to use that function so that I can send the mode to it and it has the if statement. I think I know what to do now, so thanks for your help.

Assuming is ROS v6 with IPv6 packet enabled, or v7, and just for teaching
because before add one address must be checked if the address is already present, or it do error and exit:

Automatic IP type detection with or without netmask (and also if is valid or not): On IPv6 do not support prefix/netmask

:global addIP do={
    :local addList $1
    :local addIP   $2
    :local addType 0

:if ($2~"((25[0-5]|(2[0-4]|[01]?[0-9]?)[0-9])\\.){3}(25[0-5]|(2[0-4]|[01]?[0-9]?)[0-9])(\\/(3[0-2]|[0-2]?[0-9])){0,1}") do={:set addType 4}

    :if ([:typeof [:toip6 $2]] = "ip6") do={:set addType 6}

    # this do not work on RouterOS because a bug
    #:if ([:typeof [:toip6 $2]] = "ip6-prefix") do={:set addType 6}

    :local ftest [:find $2 "/" -1]
    :local ltest [:len $2]
    :if ($ftest > 0) do={
        :local testip [:pick $2 0 $ftest]
        :local testmk [:pick $2 $ftest $ltest]
        :if ( ([:typeof [:toip6 $testip]] = "ip6") and ($testmk~"^\\/(12[0-8]|(1[0-1]|0?[0-9]?)[0-9])\$") ) do={:set addType 6}
    }

    :if ($addType = 4) do={
        /ip firewall address-list add list=$addList address=$addIP
    }
    :if ($addType = 6) do={
        /ipv6 firewall address-list add list=$addList address=$addIP
    }
 }

Based on the parameter:

:global addIP do={
    :local addList $1
    :local addIP   $2
    :local addType $3

    :if ($addType = 4) do={
        /ip firewall address-list add list=$addList address=$addIP
    }
    :if ($addType = 6) do={
        /ipv6 firewall address-list add list=$addList address=$addIP
    }
 }


$addIP "my list" 1.2.3.4 4
$addIP "my list" 1.2.3.0/24 4
$addIP "myipv6 list" 1:2:3:4:: 6
$addIP "myipv6 list" 1:2:3:4::/64 6

I like that. Thank you