Monitorimi dhe kontrolli në distancë i pajisjeve të bazuara në Lunix/OpenWrt/Lede përmes portit 80…

Përshëndetje të gjithëve, kjo është përvoja ime e parë në Habré. Unë dua të shkruaj se si të menaxhoj pajisjet e rrjetit në një rrjet të jashtëm në një mënyrë jo standarde. Çfarë do të thotë jo standarde: në shumicën e rasteve, për të menaxhuar pajisjet në një rrjet të jashtëm ju nevojiten:

  • Adresa IP publike. Epo, ose nëse pajisja është pas NAT-së së dikujt, atëherë një IP publike dhe një port "përcjellur".
  • Tuneli (PPTP/OpenVPN/L2TP+IPSec, etj.) në nyjen qendrore përmes së cilës do të ishte i aksesueshëm.

Prandaj, do t'ju duhet "biçikleta ime" kur metodat standarde nuk ju përshtaten, për shembull:

  1. Pajisjet janë të vendosura prapa NAT dhe, përveç http-së së zakonshme (porti 80), gjithçka është e mbyllur. Kjo është një situatë krejtësisht normale për rrjetet e mëdha të korporatave federale. Ata mund të regjistrojnë portet, por jo menjëherë, jo shpejt dhe jo për ju.
  2. Kanal komunikimi i paqëndrueshëm dhe/ose "i ngushtë". Shpejtësi e ulët, humbje konstante. Dhimbje dhe zhgënjim kur përpiqeni të organizoni një tunel.
  3. Një kanal i shtrenjtë komunikimi, ku fjalë për fjalë çdo megabajt vlen. Për shembull, komunikimet satelitore. Plus vonesa të gjata dhe një brez "të ngushtë".
  4. Një situatë kur duhet të "mashtroni" një numër të madh ruterash të vegjël, në të cilët, nga njëra anë, është instaluar OpenWrt/Lede për të zgjeruar aftësitë, dhe nga ana tjetër, burimet (memoria) e ruterit nuk janë të mjaftueshme. për çdo gjë.

Shënoni numrin herë Çfarë ju pengon të instaloni një flash drive në portën USB të ruterit dhe të zgjeroni kujtesën e ruterit?

Më shpesh, kërkesat janë për koston e zgjidhjes në tërësi, por ndonjëherë edhe faktori i formës luan një rol kyç. Për shembull, ekziston një TP-Link ML3020 në vend, porta e tij e vetme USB përdoret për një modem 2G/3G, e gjithë kjo është e mbështjellë në një lloj kuti të vogël plastike dhe e vendosur diku lart, lart (në direk), larg, larg (në terren, 30 km nga stacioni bazë më i afërt i operatorit celular). Po, mund të lidhni një shpërndarës USB dhe të zgjeroni numrin e portave, por përvoja tregon se kjo është e rëndë dhe jo e besueshme.

Kështu, u përpoqa t'ju përshkruaj situatën time tipike: "diku larg, larg, ekziston një ruter shumë i rëndësishëm, i vetmuar dhe i vogël që funksionon Linux. Është e rëndësishme të dini të paktën një herë në ditë që ai është "gjallë" dhe, nëse është e nevojshme, i dërgohen komanda, për shembull, "zemër, rindizni!"

Le të kalojmë në zbatimin:

1) Në anën e ruterit, nëpërmjet cron, çdo 5/10/1440 minuta, ose kurdo që dëshironi, duhet të dërgoni një kërkesë http në server duke përdorur wget, të ruani rezultatin e kërkesës në një skedar, ta bëni skedarin të ekzekutueshëm , dhe ekzekutoni atë.

Linja ime cron duket diçka si kjo:

Skedari /etc/crontabs/root:

  */5 * * * * wget "http://xn--80abgfbdwanb2akugdrd3a2e5gsbj.xn--p1ai/a.php?u=user&p=password" -O /tmp/wa.sh && chmod 777 /tmp/wa.sh && /tmp/wa.sh

, ku:
xn--80abgfbdwanb2akugdrd3a2e5gsbj.xn--p1ai është domeni i serverit tim. Do të vërej menjëherë: po, ju mund të specifikoni një adresë specifike IP të serverit, ne e bënim këtë derisa shteti ynë, në një impuls të drejtë lufte, do të them, nuk e di, bllokoi hyrjen në pjesa e luanit të "reve" të DigitalOcean dhe Amazon. Nëse përdorni një domen simbolik, nëse ndodh një incident i tillë, mund të ngrini lehtësisht një re rezervë, ta ridrejtoni domenin tek ai dhe të rivendosni monitorimin e pajisjes.

a.php është emri i skriptit nga ana e serverit. Po, e di që është gabim të emërtosh variabla dhe emra skedarësh me të njëjtën shkronjë... Unë sugjeroj që në këtë mënyrë të kursejmë disa bajt kur dërgojmë një kërkesë :)
u - emri i përdoruesit, identifikimi i harduerit
p - fjalëkalimi
“-O /tmp/wa.sh” është një skedar në ruterin në distancë ku do të ruhet përgjigja e serverit, për shembull komanda e rindezjes.

Shënimi numër dy: Ahhh, pse përdorim wget dhe jo curl, sepse përmes curl mund të dërgoni kërkesa https jo me GET, por me POST? Ahhh sepse, si në shakanë e vjetër "NE ngjitet në kavanoz!" curl përfshin biblioteka të enkriptimit me madhësi rreth 2 MB dhe për shkak të kësaj nuk ka gjasa që të mund të grumbulloni një imazh për një TP-LINK ML3020 të vogël, për shembull. Dhe me wget - ju lutem.

2) Nga ana e serverit (kam Ubuntu) do të përdorim Zabbix. Pse: Unë dua që ajo të jetë e bukur (me grafikë) dhe e përshtatshme (dërgoni komanda përmes menysë së kontekstit). Zabbix ka një gjë kaq të mrekullueshme si agjenti zabbix. Nëpërmjet agjentit, ne do të thërrasim një skript PHP në server, i cili do të kthejë informacion nëse ruteri ynë është regjistruar gjatë periudhës së kërkuar kohore. Për të ruajtur informacionin në lidhje me kohën e regjistrimit, komandat për pajisjet, përdor MySQL, një tabelë e veçantë për përdoruesit me afërsisht fushat e mëposhtme:

		CREATE TABLE `users` (
		  `id` varchar(25) NOT NULL,
		  `passwd` varchar(25) NOT NULL,
		  `description` varchar(150) NOT NULL,
		  `category` varchar(30) NOT NULL,
		  `status` varchar(10) NOT NULL,
		  `last_time` varchar(20) NOT NULL, // время последнего соединения
		  `last_ip` varchar(20) NOT NULL, // IP последнего соединения 
		  `last_port` int(11) NOT NULL, // порт последнего соединения
		  `task` text NOT NULL, // задача которую получает роутер
		  `reg_task` varchar(150) NOT NULL, // "регулярная" задача, если мы захотим чтобы задача выполнялась всегда при регистрации
		  `last_task` text NOT NULL, // лог задач
		  `response` text NOT NULL, // сюда пишется ответ устройства
		  `seq` int(11) NOT NULL
		) ENGINE=InnoDB DEFAULT CHARSET=utf8;

Të gjitha burimet mund të shkarkohen nga depoja e Git në: https://github.com/BazDen/iotnet.online.git
Tani skriptet PHP të vendosura në anën e serverit (për lehtësi, ato mund të vendosen në dosjen /usr/share/zabbix/):

skedar a.php:

<?php
// Получаем входные параметры: имя пользователя, пароль и сообщение от удаленного роутера
// Зачем нужен message ? Это способ ответа роутера, например если вы захотите посмотреть содержимое файла роутера
	$user=$_REQUEST['u'];
	$password=$_REQUEST['p'];
	$message=$_REQUEST['m'];
	
	// Подключаемся к нашей базе данных (MySQL)
	$conn=new mysqli("localhost","db_login","db_password","DB_name");
	if (mysqli_connect_errno()) {
		exit();
	}
	$conn->set_charset("utf8");
	// здесь ищем наш роутер в таблице базы данных
	$sql_users=$conn->prepare("SELECT task, reg_task, response, last_time FROM users WHERE id=? AND passwd=? AND status='active';");
	$sql_users->bind_param('ss', $user, $password);
	$sql_users->bind_result($task, $reg_task, $response, $last_time);
	$sql_users->execute();
	$sql_users->store_result();
	if (($sql_users->num_rows)==1){
		$sql_users->fetch();
		// здесь мы роутеру отправляем его задачи
		echo $task;
		echo "n";
		echo $reg_task;
		// вот здесь мы пишем время ответа и сам ответ роутера
		$response_history="[".date("Y-m-d H:i")."] ".$message;
		// задачу отправили, теперь надо ее удалить,а после удаления отметить в логах, что такая-то задача выполнена
		$last_ip=$_SERVER["REMOTE_ADDR"];
		$last_port=$_SERVER["REMOTE_PORT"];
		$ts_last_conn_time=$last_time;
		$sql_users=$conn->prepare("UPDATE users SET task='', seq=1 WHERE (id=?);");
		$sql_users->bind_param('s', $user);
		$sql_users->execute();
		if (strlen($message)>1){
			$sql_users=$conn->prepare("UPDATE users SET response=?, seq=1 WHERE (id=?);");
			$sql_users->bind_param('ss', $response_history, $user);
			$sql_users->execute();
		}
		// теперь надо сохранить время регистрации пользователя, его айпи и сообщение от него. Пока только сообщение
		$ts_now=time();
		$sql_users=$conn->prepare("UPDATE users SET last_time=?, last_ip=?, last_port=? WHERE (id=?);");
		$sql_users->bind_param('ssss', $ts_now, $last_ip, $last_port, $user);
		$sql_users->execute();
	}
	// если мы не нашли роутер в нашей базе данных, или его статус "неактивный", то ему ... будет отправлена команда reboot....
	// Почему так жестоко ? Потому что роутеры иногда пропадают, а это маленький способ проучить "новых владельцев". 
	else
	{
	echo "reboot";
	}
	$sql_users->close();
	?>

Skedari Agent.php (ky është skripti i agjentit zabbix i quajtur):

<?php
	// файл агента Zabbix. Данный скрипт обращается к таблице users и получает "1" если устройство регистрировалось с момента последнего обращения
	// user и password - учетные данные оборудования
	$user = $argv[1];
	$password = $argv[2];
	
	// подключаемся к нашей базе данных
	$conn=new mysqli("localhost","db_user","db_password","db_name");
	if (mysqli_connect_errno()) {
		exit();
		}
	$conn->set_charset("utf8");
	$sql_users=$conn->prepare("SELECT seq FROM users WHERE id=? AND passwd=? AND status='active';");
	$sql_users->bind_param('ss', $user, $password);
	$sql_users->bind_result($seq);
	$sql_users->execute();
	$sql_users->store_result();
	// обмен данными происходит через поле seq. При регистрации железка ставит данное поле в "1"
	if (($sql_users->num_rows)==1){
		$sql_users->fetch();
		echo $seq;
	}
		
	// обнуляем $seq. 
	$sql_users=$conn->prepare("UPDATE users SET seq=0 WHERE id=? AND passwd=? AND status='active';");
	$sql_users->bind_param('ss', $user, $password);
	$sql_users->execute();
	$sql_users->close();
?>		

Epo, faza përfundimtare: regjistrimi i një agjenti dhe shtimi i orareve.

Nëse nuk e keni instaluar ende agjentin zabbix, atëherë:

apt-get install zabbix-agent

Redaktoni skedarin /etc/zabbix/zabbix_agentd.conf.

Shtoni rreshtin:

UserParameter=test,php /usr/share/zabbix/agent.php user password

, ku:
testi është emri i agjentit tonë
"Fjalëkalimi i përdoruesit php /usr/share/zabbix/agent.php" - një skript i quajtur që tregon të dhënat e regjistrimit të pajisjes.

Shtimi i grafikëve: hapni ndërfaqen e internetit zabbix, zgjidhni nga menyja:
Cilësimet -> Nyjet e rrjetit -> Krijo një nyje rrjeti. Këtu mjafton të specifikoni emrin e hostit të rrjetit, grupin e tij dhe ndërfaqen e paracaktuar të agjentit:

Monitorimi dhe kontrolli në distancë i pajisjeve të bazuara në Lunix/OpenWrt/Lede përmes portit 80…

Tani duhet të shtojmë një element të dhënash për këtë nyje rrjeti. Kushtojini vëmendje dy fushave: "çelësi" - ky është pikërisht parametri që kemi shkruar në skedarin /etc/zabbix/zabbix_agentd.conf (në rastin tonë është test) dhe "intervali i përditësimit" - e vendosa në 5 minuta , sepse dhe pajisjet gjithashtu regjistrohen në server një herë në pesë minuta.

Monitorimi dhe kontrolli në distancë i pajisjeve të bazuara në Lunix/OpenWrt/Lede përmes portit 80…

Epo, le të shtojmë një grafik. Unë rekomandoj të zgjidhni "Mbush" si stilin e interpretimit.

Monitorimi dhe kontrolli në distancë i pajisjeve të bazuara në Lunix/OpenWrt/Lede përmes portit 80…

Prodhimi është diçka shumë lakonike, për shembull si kjo:

Monitorimi dhe kontrolli në distancë i pajisjeve të bazuara në Lunix/OpenWrt/Lede përmes portit 80…

Në pyetjen e arsyeshme: "a ia vlente?", Unë do t'i përgjigjem: mirë, natyrisht, shihni "arsye për krijimin e një biçiklete" në fillim të artikullit.

Nëse përvoja ime e parë grafomane ngjall interesin e lexuesve, atëherë në artikujt e mëposhtëm dua të përshkruaj se si të dërgoj komanda në pajisjet në distancë. Ne gjithashtu arritëm të zbatonim të gjithë skemën për pajisjet e bazuara në RouterOS (Mikrotik).

Burimi: www.habr.com

Shto një koment