While needing to update a bunch of routers with new SSL certificates for the hotspot config the other day, I realised there is currently no way to import a certificate in RouterOS via a scripted function (at least not that I’ve discovered prior to v6.3).
As such I set out to find a way to update routers with a single copy/paste block of code that would work across all versions and could also be run using a system such as router-tools or via an API interface and came up with the following.
#Add all required Scripts /system script add name=script1 policy=\ ftp,reboot,read,write,policy,test,winbox,password,sniff,sensitive,api \ source="\r\ \n/tool fetch url=http://example.com/ssl/CARoot1.crt\r\ \n/tool fetch url=http://example.com/ssl/CARoot2.crt\r\ \n/tool fetch url=http://example.com/ssl/hotspot.crt\r\ \n/tool fetch url=http://example.com/ssl/hotspot.key\r\ \n:execute script2\r\ \n:delay 10s\r\ \n:execute script3\r\ \n:delay 5s\r\ \n:execute script4\r\ \n\r\ \n" add name=script2 policy=\ ftp,reboot,read,write,policy,test,winbox,password,sniff,sensitive,api \ source="\r\ \n/certificate remove 0\r\ \n/certificate remove 1\r\ \n/certificate remove 2\r\ \n/certificate remove 3\r\ \n/certificate remove 4\r\ \n/certificate remove 5\r\ \n/certificate remove 6\r\ \n/certificate remove 7\r\ \n/certificate remove 8\r\ \n/certificate remove 9\r\ \n" add name=script3 policy=\ ftp,reboot,read,write,policy,test,winbox,password,sniff,sensitive,api \ source="\r\ /ip hotspot profile set 0 ssl-certificate=cert3\r\ \n/ip hotspot profile set 1 ssl-certificate=cert3\r\ \n/ip hotspot profile set 2 ssl-certificate=cert3\r\ \n/ip hotspot profile set 3 ssl-certificate=cert3\r\ \n/ip hotspot profile set 4 ssl-certificate=cert3\r\ \n/ip hotspot profile set 5 ssl-certificate=cert3\r\ \n/ip hotspot profile set 6 ssl-certificate=cert3\r\ \n/ip hotspot profile set 7 ssl-certificate=cert3\r\ \n/ip hotspot profile set 8 ssl-certificate=cert3\r\ \n/ip hotspot profile set 9 ssl-certificate=cert3\r\ \n" add name=script4 policy=\ ftp,reboot,read,write,policy,test,winbox,password,sniff,sensitive,api \ source="\r\ \n/system script remove script1\r\ \n/system script remove script2\r\ \n/system script remove script3\r\ \n/system script remove script4\r\ \n" #Save script run command as variable :global cmd "/system script run script1" #Execute command (to run asynchronously) :execute $cmd #wait 5 seconds, script1 downloads the new certificates #script 2 performs the existing certificate removal process :delay 5s #import new ones with carriage return for passphrase /certificate import file-name=CARoot1.crt /certificate import file-name=CARoot2.crt /certificate import file-name=hotspot.crt passwordhere /certificate import file-name=hotspot.key passwordhere #log so we know this has completed :log info "certificates added" #after 10 seconds have passed scripts3,4 will be run #script3 updates all hotspot profiles to use the newly imported certificate #script4 removes all the scripts created for this update
In short, what this block does is creates the scripts required to:
a) download new certificates from a website/folder/ftp-server
b) removes the existing certificate listing
c) imports the new certificates (which itself can’t be done via a script)
d) updates all hotspot profiles to use the new certificate
It does this by creating the scripts and running the first one using the :execute command which causes it to be run asynchronously. You may recall I used a similar function in the http load/bandwidth tester script to run multiple fetch commands. This is then followed by a delay to allow the first part of the script (downloading and then removing existing certs) to be completed and then itself go into a 10 second delay before the new certificates are imported from terminal directly (passphases and all).
After all this is completed the final 2 scripts update the hotspot profiles to use the new certificate, then remove all the scripts that were created in the process.