I can’t find a way to add an element to a global array inside a for loop.
The array content is being replaced by the last element.
:global interfaces;
:foreach i in=[/interface bridge port find where pvid=80] do={
:local bport [interface bridge port get number=$i];
:put ("$bport"->"interface");
:set $interfaces ($interfaces $bport);
}
:put $interfaces;
Clearly Mikrotik scripting syntax is a pita; honestly, it’s a simple array push function.
I really hope that someone can help me find out the reason why this isn’t working properly.
Close. You need to declare the outer array & use parens+comma to concat values to the array.
:global interfaces [:toarray “”]
:foreach i in=[/interface bridge port find where pvid=80] do={
:local bport [/interface bridge port get number=$i];
:put ($bport->“interface”);
:set $interfaces ($interfaces,$bport);
}
Well, it's just a random exercise since I'm learning Mikrotik scripting, but the thing is to save every interface data configuration on an array while I'm looping through bridge interfaces with pvid=to some vlan id. Anyway, could you break it down for me, please? I'm a bit confused with the [get $i interface]
Just that?
:global interfaces [/interface bridge port print detail as-value where pvid=80]
:put $interfaces
:put “$($interfaces->0->“interface”) is on the bridge $($interfaces->0->“bridge”)”
Obviously “put” print results on terminal only if something with pvid=80 exist…
I want to understand how to push an element to an array inside a for / foreach loop!
Besides I can make use of the information generated inside a for loop and make something with it later.
I need to understand the mechanics of a simple element push to an array inside a for loop.
You “push” to an array by concatenating new values, as shown above. There is NO push/pop, only index and re-assignment. But you do have to declare the array when initializing it using [:toarray “”] as the value to create an array type.
I can see now that Mikrotik scripting is the practical result of a collection of wild runs!
I thought that shell scripting was stupid enough but when compared is kinda refreshing…
The syntax is Dantesque and the complexity of possibilities is just outstanding in a bad way.
There must be a valid reason why this doesn’t work, but I can’t understand why since the iface local variable is reassigned in every loop with a new interface array! Perhaps the reason is the array architecture in itself.
:global interfaces [:toarray ""]
:foreach i in=[/interface bridge port find where pvid=80] do={
:local iface [interface bridge port get number=$i];
:set interfaces ($interfaces, $iface);
}
:put $interfaces;
And it’s perfectly logical, you can’t have two keys with the same name in the same array…
:global example [:toarray ""]
:set example ($example,{"interface"="ether1";"arr1"="yes"})
:set example ($example,{"interface"="ether2";"arr2"="yes"})
:put $example
on results is present both arr1 and arr2, but only one interface, and obviously is the last set.
arr1=yes;arr2=yes;interface=ether2
What you try to do, you want to do wrong.
If you do things randomly and don’t read what I write, that’s your business.
Fix it yourself.
As I said earlier, it’s an array-related architecture thing…
I now understand arrays in Mikrotik scripting do not work as I believed.
Anyways, thank you for pointing that out to me.
What kind of key-value data type supports different value for same key in any programing/script language? How that will be even possible? Key must be unique.
Create main interfaces array and on each iteration add to it key-valye array for interface data. Then you can access values later by iterating $interfaces array or directly by index $interfaces->$index->“key”, etc…
Like this for eg.:
:global interfaces [:toarray ""]
/interface bridge port
:foreach i in=[find where pvid=10] do={
:put ([get $i]->"interface")
:set interfaces ($interfaces, {[get $i]})
}
:put "-----------"
:foreach i in=$interfaces do={
:put ($i->"interface")
}
For sure, but the user, as example, want just obtain one array with all port interfaces data inside, and whay I have proposed is the fast way without cycles…
Stylistically, @rextended example in #6 is spot on. e.g. why use a foreach+find+get when there is a "/xxx print detail as-value" that get the key-value array for you in one command & then do whatever further operations on that KV array from print...