Email, when admin or other user login via winbox or so.

Hi

Can someone help me with a script
I wan’t to know how to create a script when a user login via winbox, ftp, ssh, telnet or api. To email the login time, date, user, from ip and if it is via winbox or so to a
certain email address. And even if a user tried to login and failed by putting an incorrect username or password.

Regards

AFAIK, there’s no “direct” way to do that.

What you can do is to schedule a script to search the system logs (at “/log”) at regular intervals. Login attempts are written there.

At every interval, check for entries newer than the last time the script was executed, collect them into a string that you’ll then send with “/tool e-mail send”. To keep track of when the script was executed, you could use a global variable that you’ll modify at the end of the script.

Something like this: http://forum.mikrotik.com/t/is-it-possible-to-run-a-script-on-login/55422/1

Use the scheduler to run it every 30 seconds, or however often you want.

I have tried the script but no luck. It did work once but the body of the email was empty. then I started over and paste it in the script again and now I don’t even recieved any emails.

I can sent out test emails and daily backups out of my router so my email settings are correct.


Script to check for specific new logs and send email alerts

Tested on RouterOS v5.7+

container to keep track of the last time stamp detected

:global lastTime;

find log entries where the message contains “logged in” or “login failure”

:local currentBuf [ :toarray [ /log find message~“logged in” || message~“login failure” ] ] ;

get number of log entries

:local currentLineCount [ :len $currentBuf ] ;

if any logs were found, proceed

if ($currentLineCount > 0) do={

based on number of entries, get time of last entry

:local currentTime “$[ /log get [ :pick $currentBuf ($currentLineCount -1) ] time ]”;

check currentTime length, if length is 15, log is from a previous day and begins with month/day

:if ([:len $currentTime] = 15 ) do={

trim currentTime so we are left only with time xx:xx:xx

:set currentTime [ :pick $currentTime 7 15 ];
}

the output for the body of the email, includes time stamp and log message

:local output “$currentTime $[/log get [ :pick $currentBuf ($currentLineCount-1) ] message ]”;

email function

:local sndEmail [:parse "/tool e-mail send to=> eugene@wan4u.co.za > subject="MikroTik alert $currentTime" body="$output"];

beep function

:local doBeep [:parse “:beep;:delay 150ms;:beep;”];

\

if the last time stamp has not been set, length will be 0 (after reboot, etc)

:if ([:len $lastTime] < 1 ) do={

update lastTime to match currentTime

:set lastTime $currentTime ;

send email and beep

$sndEmail;
$doBeep;

if lastTime has been set, continue

} else={

if lastTime does not match time stamp of the latest

:if ( $lastTime != $currentTime ) do={

update lastTime to match currentTime

:set lastTime $currentTime ;

send email and beep

$sndEmail;
$doBeep;
}
}
}

Any Idea what is wrong with my script.

Seems like you’re missing a quote on the email line. That is, instead of

:local sndEmail [:parse "/tool e-mail send to=eugene@wan4u.co.za subject=\"MikroTik alert $currentTime\" body=\"$output\"];

have it as

:local sndEmail [:parse "/tool e-mail send to=eugene@wan4u.co.za subject=\"MikroTik alert $currentTime\" body=\"$output\""];

Thanks it is working now.

One more question. I run a PPPOE server on my Mikrotik, but every time a user autenticates via PPPOE i ge a email for that as well how can i void this?

Regards

What does one of the PPPoE logs say when someone logs in?

To exclude some log entries, replace this line of the original script:
:local currentBuf [ :toarray [ /log find message~“logged in” || message~“login failure” ] ] ;With this:
:local removeThese {“PPPoE”;“any strings you want”}

:local tempBuf [:toarray [/log find message~“logged in” || message~“login failure”]]
:local currentBuf “”; :set currentBuf [:toarray $currentBuf]

:foreach i in=$tempBuf do={
:local toggle 1
:foreach j in=$removeThese do={
:if ([:typeof [:find [/log get $i message] “$j”]] = “num”) do={
:set toggle 0
}
}
:if ($toggle = 1) do={
:set currentBuf ( $currentBuf , $i)
}
}This will search through all the “logged in” and “login failure” logs that have been found and exclude any that contain the strings found in the removeThese array.

Hi

Thanks it is seems like it is now.