Mikrotik script for logs notifications/alert script via Telegram, ROS 7
Change "BotToken", "MyID"
:local BotToken "Token"
:local MyID "UserID"
:local findPosix do={
:local string [:tostr $1];
:local posix $2;
:local posix0 $posix;
:local fstart [:tonum $3];
:local fend 0;
:if ($fstart < 0) do={ :set fstart 0 };
:local substr [:pick $string $fstart [:len $string]];
:if ([:len $string] > 0 && [:len $posix] > 0 && $fstart <[:len $string] && ($substr ~ $posix)) do={
:while ($fstart < [:len $string]) do={
:set posix $posix0;
:if ([:pick $posix 0] != "^") do={
:set posix ("^".$posix);
:local continue true;
:while ($continue && $fstart < [:len $string]) do={
:if ([:pick $string $fstart [:len $string]] ~ $posix) do={
:set continue false;
} else={:set fstart ($fstart + 1);};
}
}
:if ($fstart < [:len $string]) do={
:if ([:pick $posix ([:len $posix] -1)] != "\$") do={
:set posix ($posix."\$");
:local continue true;
:set fend [:len $string];
:while ($fend > $fstart && $continue) do={
:if ([:pick $string $fstart $fend] ~ $posix) do={:set continue false} else={:set fend ($fend - 1)};
}
} else={:set fend [:len $string];}
}
:if ($fend > $fstart) do={:return {[:pick $string $fstart $fend] ; $fstart ;$fend};};
:set fstart ($fstart +1);
:set fend 0;
:put "Unidentified error";
}
}
:return {[]; []; []};
};
:local date [system clock get date]
:local currentTime [system clock get time]
:local logs
:local logAll [:toarray [log find]]
:local logCnt [ :len $logAll ];
:local index 0;
:local timeLog;
:global lastTimeLog;
:local lastTime;
:local today true
if ([:len $lastTimeLog] < 1) do={
:log info ("<extra-log> Time of the last log entry was not found. Set to -1m");
# GMT time=+02:00
# :local currentTimeStamp [:totime ([:timestamp]+2h)]
:local currentTimeStamp [ :totime [ ([:timestamp] + ([system clock get gmt-offset] . "s") )] ]
:set lastTimeLog ($currentTimeStamp-1m);
}
:do {
:set index ($index + 1);
:local currentLog [:pick $logAll ($logCnt - $index)]
:local htime [log get $currentLog time]
if ([:len $htime] > 8) do={
if ([:len $htime] > 14) do={
# previous year
:set timeLog ([ :totime ($htime) ]);
} else={
# yesterday
:set timeLog ([ :totime ([:pick [$date] 0 4] . "-" . $htime) ]);
}
} else={
# today
# if block for fix when next day after 00:00:00 and recieve log with time only
:if ( ($htime <= $currentTime) && $today) do={
:set timeLog ([ :totime ($date . " " . $htime) ]);
} else={ :set today false; :set timeLog; }
}
:if ( $timeLog > $lastTimeLog ) do={
:set logs ($logs, $currentLog)
}
if ( ($index = 1) || ( ([:len $lastTime] < 1) && ([:len $timeLog] > 12) ) ) do={
:set lastTime $timeLog;
}
} while=((([:len $timeLog] < 1) || ($timeLog > $lastTimeLog)) && ($index < $logCnt));
:if (([:len $lastTime] > 12) && ($lastTime > $lastTimeLog)) do={
:set lastTimeLog $lastTime;
}
:if ([:len $logs] > 0 ) do={
:local TelegramMsg
:local Msgcounter 0
:local finded false
:local mac
:local comment
:local hostname
:for index from=([:len $logs]-1) to=0 step=-1 do={
:local i [:pick $logs $index ]
:local imessage [log get $i message]
:local topics [log get $i topics]
:local processLogs false;
:if ( ($topics ~"critical") || ($topics ~"error") || ($topics ~"warning") ) do={
:set processLogs true;
} else= {
:if ( ($topics ~"info") && \
($imessage ~"banned" || \
$imessage ~"login failure" || \
$imessage ~"authentication failed" || \
$imessage ~">: connected" || \
$imessage ~"logged in" || \
$imessage ~"changed" || \
$imessage ~"<extra-log>") ) do={
:set processLogs true;
}
}
#Skip flood messages
:if ( $imessage ~"unknown msg!" || \
$imessage ~"msg too short") do={
:set processLogs false;
}
:if ( $processLogs = true ) do={
:set finded false
:if ($imessage ~ "[0-F][0-F]:[0-F][0-F]:[0-F][0-F]:[0-F][0-F]:[0-F][0-F]:[0-F][0-F]") do={
:if ($finded = false) do={
:foreach k in=[ip dhcp-server lease find] do={
:set mac [ip dhcp-server lease get $k value-name=mac-address]
:if ($imessage ~ "$mac") do={
:set comment [ip dhcp-server lease get $k value-name=comment]
:set hostname [ip dhcp-server lease get $k value-name=host-name]
:if ($comment != "" || $hostname != "") do={
:set imessage ($imessage . " / " . $hostname . " / " . $comment)
:set finded true
}
}
}
}
:if ($finded = false) do={
:foreach h in=[ip hotspot ip-binding find] do={
:set mac [ip hotspot ip-binding get $h value-name=mac-address]
:if ($imessage ~ "$mac") do={
:set comment [ip hotspot ip-binding get $h value-name=comment]
:if ($comment != "") do={
:set imessage ($imessage . " / " . $comment)
:set finded true
}
}
}
}
:if ($finded = false) do={
:foreach w in=[interface wifi access-list find] do={
:set mac [interface wifi access-list get $w value-name=mac-address]
:if ($imessage ~ "$mac") do={
:set comment [interface wifi access-list get $w value-name=comment]
:if ($comment != "") do={
:set imessage ($imessage . " / " . $comment)
:set finded true
}
}
}
}
}
:local logTime [ log get $i time ]
:local trueLogTime ([:pick $date 0 11]." ". $logTime )
if ([:len $logTime] > 8) do={
:set trueLogTime $logTime
}
:set Msgcounter ($Msgcounter + 1)
if ($Msgcounter < 16 ) do={
#Only First 15 Logs For Telegram
# Strip message length
:if ([:len $imessage] > 130) do={
:set imessage [:pick $imessage 0 130]
}
:local emojiIcon ""
if ( $topics ~"critical" ) do={
:set emojiIcon "\E2\98\A0\EF\B8\8F"
}
if ( $topics ~"error" ) do={
:set emojiIcon "\F0\9F\94\A5"
}
if ( $topics ~"warning" ) do={
:set emojiIcon "\E2\9D\97"
}
if ( $topics ~"info" ) do={
:set emojiIcon "\E2\9D\95"
}
:set TelegramMsg ($TelegramMsg.$trueLogTime." - " . $emojiIcon . " - ".$imessage."%0A%0A")
}
}
}
:if ([:len $TelegramMsg] > 0 ) do={
# Hide IP's from log
:local regex "[0-2]\?[0-9]\?[0-9]\?[.][0-2]\?[0-9]\?[0-9]\?[.][0-2]\?[0-9]\?[0-9]\?[.][0-2]\?[0-9]\?[0-9]\?";
:local startPosition 0;
:local ArrRezult {"";"";""};
:do {
:set ArrRezult [$findPosix $TelegramMsg $regex $startPosition];
:if ([:len [:pick $ArrRezult 0]] > 0) do={
:local subStart [:pick $ArrRezult 1];
:local subEnd [:pick $ArrRezult 2];
:local ipaddress [:put ([:pick $ArrRezult 0]|0.0.255.255)];
:if ($ipaddress != "192.168.255.255") do={
:set ipaddress ([:pick $ipaddress 0 [:find $ipaddress "255.255"]] . "***.***" )
:set TelegramMsg ([:pick $TelegramMsg 0 $subStart] . $ipaddress . [:pick $TelegramMsg $subEnd [:len $TelegramMsg]]);
}
:set startPosition ($subEnd);
}
} while ([:len [:pick $ArrRezult 0]] > 0)
:local TelMsgFix
:local achar
:set TelegramMsg ("[\F0\9F\94\94]%20Logs%20Monitor%20Alert%20:%0A".$TelegramMsg)
# Replace " " With "%20" For Telegram String
:if ([:find $TelegramMsg " " -1] > 0) do={
set achar ""
set TelMsgFix ""
:for i from=0 to=([:len $TelegramMsg] -1) step=1 do={
:set achar value=[:pick $TelegramMsg $i]
:if ($achar = " ") do={ :set achar value="%20" }
:set TelMsgFix value=($TelMsgFix.$achar)
}
} else={:set TelMsgFix value=($TelegramMsg)}
:do {
tool fetch url="https://api.telegram.org/bot$BotToken/sendmessage?chat_id=$MyID&text=$TelMsgFix" mode=https keep-result=no
log info "[LOGMON] Telegram message Sended."
} on-error={
log error "[LOGMON] Failed to send Telegram message.";
}
}
}