What's new

Asus/Merlin Script Tutorial

  • SNBForums Code of Conduct

    SNBForums is a community for everyone, no matter what their level of experience.

    Please be tolerant and patient of others, especially newcomers. We are all here to share and learn!

    The rules are simple: Be patient, be nice, be helpful or be gone!

JohnD5000

Very Senior Member
Does a tutorial on scripting exist for Asus/Merlin. Basic stuff like: how to load a script to the router, how to run a script, how to do basic debugging of script, what to backup scripts, etc for an Asus router running Merlin?

Thanks
 
On the one hand, I have needed help and sometimes been frustrated by what is not explicitly stated in the wiki and elsewhere. On the other hand, one must consider whether Merlin is right for you based on your knowledge and skills. For example, here is my backup script. I would not know where to begin explaining it to someone who has not written shell scripts.
Code:
#!/bin/sh
#
umask 022
myscript=$(basename $0 | cut -f 1 -d'.')
exec > ${myscript}.log 2>&1
#
mydatestring=`date +%Y_%m_%d_%H%M`
myskydir="/tmp/mnt/ent/skynet"
myentdir="/tmp/mnt/ent/entware"
mydivdir=${myentdir}/share/diversion/list
mypixdir=${myentdir}/var/cache/pixelserv
mystbcnf=${myentdir}/etc/stubby/stubby.yml
mycronuser="root"
mybackupdir="/tmp/mnt/smb/share/backup"
myfiledir=${mybackupdir}/file
mynvramdir=${mybackupdir}/nvram
mydbdir=${mybackupdir}/db
mylogdir=${mybackupdir}/log
#
mkdir ${mybackupdir}/file/${mydatestring}
find ${mybackupdir}/file -maxdepth 1 -type f -exec mv {} ${mybackupdir}/file/${mydatestring} \;
for myfile in ${mydivdir}/blacklist ${mypixdir}/ca.crt ${mypixdir}/ca.key /jffs/nvram/dhcp_hostnames /jffs/scripts/dnsmasq.postconf /jffs/scripts/firewall-start /jffs/configs/fstab /jffs/scripts/log-dhcp.sh /jffs/addons/ntpmerlin.d/ntp.conf /jffs/configs/profile.add /jffs/scripts/wan-start ${mydivdir}/wc_blacklist ${mydivdir}/whitelist /var/spool/cron/crontabs/${mycronuser}
do
        echo "==============================================================================================="
        ls -la ${myfile}
        cp ${myfile} ${myfiledir}
        echo "#"
        echo "Copied ${myfile} to ${myfiledir}"
        myname=`basename ${myfile}`
        /opt/bin/cksum ${mybackupdir}/file/${mydatestring}/${myname}
        /opt/bin/cksum ${mybackupdir}/file/${myname}
        diff ${mybackupdir}/file/${mydatestring}/${myname} ${mybackupdir}/file/${myname}
done
/opt/bin/firewall stats search manualbans > ${myfiledir}/skynet_manual_bans.txt
#
mkdir ${mybackupdir}/nvram/${mydatestring}
find ${mybackupdir}/nvram -maxdepth 1 -type f -exec mv {} ${mybackupdir}/nvram/${mydatestring} \;
for mynvram in custom_clientlist dhcp_staticlist dns_probe_content ntp_server0 ntp_server1 sshd_authkeys
do
        echo "==============================================================================================="
        nvram get ${mynvram}
        nvram get ${mynvram} > ${mynvramdir}/${mynvram}
        echo "#"
        echo "Backed up nvram variable ${mynvram} to ${mynvramdir}/${mynvram}"
        /opt/bin/cksum ${mybackupdir}/nvram/${mydatestring}/${mynvram}
        /opt/bin/cksum ${mybackupdir}/nvram/${mynvram}
        diff ${mybackupdir}/nvram/${mydatestring}/${mynvram} ${mybackupdir}/nvram/${mynvram}
done
nvram getall > ${mynvramdir}/nvram_getall
#
mkdir ${mybackupdir}/db/${mydatestring}
find ${mybackupdir}/db -maxdepth 1 -type f -exec mv {} ${mybackupdir}/db/${mydatestring} \;
for mydb in /jffs/.sys/TrafficAnalyzer/TrafficAnalyzer.db /jffs/.sys/nc/nt_center.db /tmp/db/visdata.db /tmp/mnt/ent/traffic/tomato_rstats_0c9d9201f098.gz /var/lib/misc/rstats-history.gz /var/lib/misc/rstats-speed.gz
do
        echo "==============================================================================================="
        ls -la ${mydb}
        cp ${mydb} ${mydbdir}
        echo "#"
        echo "Copied ${mydb} to ${mydbdir}"
        myname=`basename ${mydb}`
done
#
mkdir ${mybackupdir}/log/${mydatestring}
find ${mybackupdir}/log -maxdepth 1 -type f -exec mv {} ${mybackupdir}/log/${mydatestring} \;
for mylog in /tmp/syslog.log /opt/var/log/dnsmasq.log /jffs/amtm-disk-check.log /tmp/log-dhcp.sh.log
do
        echo "==============================================================================================="
        ls -la ${mylog}
        cp ${mylog} ${mylogdir}
        echo "#"
        echo "Copied ${mylog} to ${mylogdir}"
        myname=`basename ${mylog}`
        chmod 644 ${mylogdir}/${myname}
done
echo "==============================================================================================="
#
 
@JohnD5000 I have not written a single script myself. However, I can do minor edits if needed (if someone provides the changes required). :)

This huge leap for me came by simply using amtm and YazFi and following along (or at least trying to) with others when they were troubleshooting various issues.

The amtm Step-by-Step Guide in my signature was my gateway to this new world. Hopefully, it can be useful to you too. At least as an introduction. :)

After attempting that guide, please come back with any questions. Many here to help you out!
 
On the other hand, one must consider whether Merlin is right for you based on your knowledge and skills.
Well stated. I will use a statement like this when someone asks whether he/she should switch from stock ASUS firmware. The benefit really depends on the knowledge/skills of the user. Most casual users want an appliance that just "works" with little user participation.

And thanks for posting your script as a practical example. As a career software c/C++ developer I admit I suck at scripting. On my work platforms I could more easily write a C program to do the task than write/debug a shell script. Tutorials tend to show useless examples, so it is nice to see non-trivial examples.
 
Last edited:
And, on the other hand, someone who is asking to learn should be encouraged, no matter their current skill level too. :)
 
Hi, thanks for all the responses. A little background. I have Putty & WINSCP loaded on my PC, Merlin running on my router. I have atmt & Skynet running too (followed a post a while ago). I have never written a script from scratch, but I had a need and, due to help of others here on SNB, I think I have a script that will run and do what I want to do.

What I want to do is:

1) Load the script up (using putty and WINSCP as needed) but I don't know the file structures on where the scripts get loaded, naming of scripts, etc.).

2) Once I get script loaded to router, I want to create a cron job that will run the script every x minutes (say every 15 minutes)​

I'd also like to backup everything before hand (I know how to backup settings from GUI but does this backup the scripts too?) There is option to backup JFFS partition in GUI, is that the scripts? Then know how to backup & restore every thing in case I mess a lot up.

So, basic stuff, but confusing when doing it the first time.

Thanks
 
1) Load the script up (using putty and WINSCP as needed) but I don't know the file structures on where the scripts get loaded, naming of scripts, etc.).
https://github.com/RMerl/asuswrt-merlin/wiki/User-scripts
https://github.com/RMerl/asuswrt-merlin/wiki/User-scripts#creating-scripts
2) Once I get script loaded to router, I want to create a cron job that will run the script every x minutes (say every 15 minutes)
https://github.com/RMerl/asuswrt-merlin/wiki/Scheduled-tasks-(cron-jobs)
https://github.com/RMerl/asuswrt-merlin/wiki/Scheduled-LED-control
 
Ill just throw this out there as some basics to read up on, coding/scripting can be addictive but requires understanding what you're doing and lots of testing/debugging. I've been tinkering with Bash/Ash scripting over the years and everytime I open an old script it takes me 10 mins to read through and re teach myself everything I coded there

Read about different types of Linux shells (Merlin firmware uses an Ash shell which is actually quite limited) this will give you an idea of useable commands to run
Creating and setting variables, reading variables
Creating and calling functions


And as mentioned check the User-Scripts section in the Merlin wiki like Colin linked to above

In summary and quick and dirty

Create a script and save it and name it something.sh (note the first line of your script must be #!/bin/sh to tell the router how to execute it)
Winscp to your router and copy the file to /jffs/scripts
Alternatively you can SSH into the router and use the 'nano' command (linux text editor) and type your script directly in the console and use ctrl+x to save and exit.

SSH into your router
Run command chmod a+rx /jffs/scripts/*
might also have to run command dos2unix /jffs/scripts/something.sh to properly format your windows generated file to Linux line endings.
Run script by typing 'sh /jffs/scripts/something.sh'

for backing up jffs you can use the option in the GUI or just simply drag and drop in Winscp from the router to your PC to backup the files.

And heres an example of a cron job
https://github.com/RMerl/asuswrt-merlin/wiki/Scheduled-Reboot
For you create a file called init-start under /jffs/scripts using the steps above
In that file should be
Code:
#!/bin/sh
cru a myscript "*/2 * * * * /jffs/scripts/something.sh"
you will need to reboot your router I think to initialize the cru command with the init-start script

Hope this helps get you down the learning path.
 
Last edited:
Thanks, I'll review these in more detail when I have time. Just a general question, do scripts have a naming structure as "namescript.sh"?

scripts dont require .sh on the end but its good practice to help identify what a file actually is
 
If you are developing scripts, I highly recommend learning how to edit them on the router. It gets very cumbersome editing then copying them from your PC, running chmod to make them executable, etc.

I've used vi for so many years that it is second-nature. In fact, on my PC sometimes forget when using a full-screen editor (like Word or Notes) and type 'i' or 'a' before typing. And I find myself ending by hitting the <ESC> key. I often find I've entered ESC:wq when I'm finished and want to save the file and exit :)

The vi installed (at least with the ASUS firmware) seems to be stripped-down compared to what I'm used to using.So there are some things I've had to learn not to do. I'm not aware of any other file editor native to the router. If so, what else is there?

Anyway, I highly recommend learning how to use the native editor(s) instead of copying scripts - especially during the debugging phase.

Update: ooops - had to edit to remove an extraneous 'i' :)
 
The vi installed (at least with the ASUS firmware) seems to be stripped-down compared to what I'm used to using.So there are some things I've had to learn not to do. I'm not aware of any other file editor native to the router. If so, what else is there?

Theres also nano. Its personal preference really, some like vi some like nano.

Most coders/scripters prefer vi as it requires using a key to begin editing where as a key slip in nano could go un-noticed and ruin your code.
 
Unfortunately nano (and a whole bunch of other commands) is missing in the OEM ASUS firmware. So I use the lowest common denominator. Plus, I'm very old-school and am stuck in my ways. I can't even use twitter:)
 
Unfortunately nano (and a whole bunch of other commands) is missing in the OEM ASUS firmware.

Its quite possible nano only comes with Merlins version, Im honestly not 100%
 
If you are developing scripts, I highly recommend learning how to edit them on the router. It gets very cumbersome editing then copying them from your PC, running chmod to make them executable, etc.

I've used vi for so many years that it is second-nature. In fact, on my PC sometimes forget when using a full-screen editor (like Word or Notes) and type 'i' or 'a' before typing. And I find myself ending by hitting the <ESC> key. I often find I've entered ESC:wq when I'm finished and want to save the file and exit :)

The vi installed (at least with the ASUS firmware) seems to be stripped-down compared to what I'm used to using.So there are some things I've had to learn not to do. I'm not aware of any other file editor native to the router. If so, what else is there?

Anyway, I highly recommend learning how to use the native editor(s) instead of copying scripts - especially during the debugging phase.

Update: ooops - had to edit to remove an extraneous 'i' :)
I happen to have entware, so I downloaded and use a full version of vi. I just need to remember to invoke it with "vim".
 
Theres also nano. Its personal preference really, some like vi some like nano.

Most coders/scripters prefer vi as it requires using a key to begin editing where as a key slip in nano could go un-noticed and ruin your code.
Or vi users are showing their age ;-)
 

Latest threads

Sign Up For SNBForums Daily Digest

Get an update of what's new every day delivered to your mailbox. Sign up here!
Top