Is there a fast way to check if a file or directory exists ?
On an USB connected SATA SSD - RB5009 device, /file find name="filename" take 3 minutes. There are almost 200.000 files on SSD: Gentoo portage, distfiles including git clones, a container etc.
Tried other variants like full path, get content, but if file does not exist, script fails and stop. Is like a try block available ?
Also, please review the script, I’m new on Mikrotik scripting, it’s a little to big for a simple task.
In console is possible to collect /container shell container-name cmd, but in script I got nothing with or without as-value.
:global wanInterface "pppoe-digi"
:global wanIP "$wanIP"
:global webIPv6 "$webIPv6"
:local isRunning 0
:local isMounted 0
#/file/add name=usb1-part1/ip type=directory
#/file/add name=usb1-part1/ip/ipv4.txt type=file
#/file/add name=usb1-part1/ip/ipv6.txt type=file
:set isMounted [/disk/print count-only where partition-size=256059113472]
:if ($isMounted = 1) do={
:if ([:len $wanIP] = 0) do={
:set wanIP [/file/get usb1-part1/ip/ipv4.txt contents]
/log info "WAN IP restored from file"
}
:if ([:len $webIPv6] = 0) do={
:set webIPv6 [/file/get usb1-part1/ip/ipv6.txt contents]
/log info "Web IPv6 restored from file"
}
# Get the current IP on the interface
:local currentIPtemp [/ip address get ([find where interface=$wanInterface]->0) address]
# IP without netmask
:local currentIP [:pick $currentIPtemp 0 ([:len $currentIPtemp]-3)]
:set isRunning [/container print count-only where running]
:if ($isRunning = 1) do={
/container shell nginx cmd="ifconfig | grep inet6 | grep -v 'fe80\\|::1' | head -1 | awk '{print \$2;}' > /etc/nginx/scripts/addr.txt"
:local tempIP [/file get usb1-part1/docker/data/nginx/scripts/addr.txt contents ]
:local currentIPv6 [:put [ :pick $tempIP 0 [ :find $tempIP "\n" ] ] ];
:if ($currentIP !=$wanIP or $currentIPv6 !=$webIPv6) do={
:set wanIP $currentIP
:set webIPv6 $currentIPv6
/file/set usb1-part1/ip/ipv4.txt contents=$currentIP
/file/set usb1-part1/ip/ipv6.txt contents=$currentIPv6
/log info "WAN IP changed from $wanIP to $currentIP"
/log info "Web IPv6 changed from $webIPv6 to $currentIPv6"
:delay 3000
/system script run cloudns_update
}
} else={
/log error "NGINX container is not running"
}
} else={
/log error "SSD is not mounted. Reseat or reboot."
}
You could try (with full path) to get length of file, something loosely like:
:if ([:len [/file find name=mypath/myfile.ext]] > 0) do={
:put “FOUND IT”
}
this should return 0 if file is not found and the length of file if found.
For cmd in script: /container shell nginx cmd="ifconfig | grep inet6 | grep -v 'fe80\\|::1' | head -1 | awk '{print \$2;}' > /etc/nginx/scripts/addr.txt" there won’t be any value since command stdout is redirected to file.
Also stderr is not returned as value, so if command fails (or returns output for some reason into stderr) it won’t have value eather. Try to perform for eg. :put [/container/shell nginx cmd="ls" as-value] it should work. If you need to handle both, stdout and stderr outputs as return value redirect command output with2>&1, eg. :put [/container/shell nginx cmd="bad_command 2>&1" as-value].
This is the problem :local var [/container shell nginx cmd="ifconfig | grep inet6 | grep -v 'fe80\|::1' | head -1 | awk '{print $2;}'“ as-value] ; :put $var works only in terminal, not in script. Thats why decided to redirect it to a file to have an output somehow.
Depending on how this is run... the $2 may be an empty string, since RouterOS's string interpolation is trigger beforecmd is run. i.e. the variable substitution might be happening before even getting to the container's shell.