mirror of
https://github.com/kiddin9/op-packages.git
synced 2026-10-31 01:25:13 +08:00
✨ Sync 2026-09-09 01:26:15
This commit is contained in:
1 parent
2b23b9049b
commit
7e90b2cbf7
27 files changed
+1113
No files matched your search
@@ -0,0 +1,11 @@
|
|||||||
|
include $(TOPDIR)/rules.mk
|
||||||
|
|
||||||
|
PKG_NAME:=luci-app-smart-reboot
|
||||||
|
LUCI_TITLE:=LuCI support for smart-reboot
|
||||||
|
LUCI_DEPENDS:=+smart-reboot
|
||||||
|
PKG_LICENSE:=Apache-2.0
|
||||||
|
|
||||||
|
include $(TOPDIR)/feeds/luci/luci.mk
|
||||||
|
|
||||||
|
# call BuildPackage - OpenWrt buildroot signature
|
||||||
|
|
||||||
@@ -0,0 +1,93 @@
|
|||||||
|
'use strict';
|
||||||
|
'require view';
|
||||||
|
'require form';
|
||||||
|
'require network';
|
||||||
|
'require uci';
|
||||||
|
|
||||||
|
return view.extend({
|
||||||
|
load: function() {
|
||||||
|
return Promise.all([
|
||||||
|
network.getNetworks(),
|
||||||
|
network.getDevices()
|
||||||
|
]);
|
||||||
|
},
|
||||||
|
|
||||||
|
render: function(data) {
|
||||||
|
var m, s, o;
|
||||||
|
var networks = data[0] || [];
|
||||||
|
var devices = data[1] || [];
|
||||||
|
var ifaceMap = {};
|
||||||
|
|
||||||
|
m = new form.Map('smart-reboot', _('Smart Reboot'),
|
||||||
|
_('Reboot only when the network is idle at the configured dawn time.'));
|
||||||
|
|
||||||
|
s = m.section(form.TypedSection, 'settings', _('Settings'));
|
||||||
|
s.anonymous = true;
|
||||||
|
|
||||||
|
o = s.option(form.Flag, 'enabled', _('Enable'));
|
||||||
|
o.rmempty = false;
|
||||||
|
|
||||||
|
o = s.option(form.DummyValue, 'last_auto_reboot', _('Last automatic reboot'));
|
||||||
|
o.cfgvalue = function(section_id) {
|
||||||
|
return uci.get('smart-reboot', section_id, 'last_auto_reboot') || _('Never');
|
||||||
|
};
|
||||||
|
|
||||||
|
o = s.option(form.Value, 'time', _('Reboot time (HH:MM)'));
|
||||||
|
o.placeholder = '04:00';
|
||||||
|
o.rmempty = false;
|
||||||
|
o.validate = function(section_id, value) {
|
||||||
|
if (!value || !value.match(/^([01][0-9]|2[0-3]):[0-5][0-9]$/))
|
||||||
|
return _('Time format must be HH:MM (24-hour). Example: 04:00');
|
||||||
|
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
|
||||||
|
o = s.option(form.Flag, 'all_ifaces', _('Select all interfaces'));
|
||||||
|
o.rmempty = false;
|
||||||
|
|
||||||
|
o = s.option(form.MultiValue, 'ifaces', _('Monitored interfaces'));
|
||||||
|
o.widget = 'select';
|
||||||
|
o.size = 8;
|
||||||
|
o.depends('all_ifaces', '0');
|
||||||
|
o.depends('all_ifaces', '');
|
||||||
|
|
||||||
|
networks.forEach(function(netif) {
|
||||||
|
var logical = netif.getName();
|
||||||
|
var dev = netif.getL3Device() || netif.getL2Device() || netif.getDevice();
|
||||||
|
var ifname = dev && dev.getName ? dev.getName() : null;
|
||||||
|
|
||||||
|
if (!ifname || ifname === 'lo')
|
||||||
|
return;
|
||||||
|
|
||||||
|
ifaceMap[ifname] = ifaceMap[ifname] || { labels: [] };
|
||||||
|
if (logical && ifaceMap[ifname].labels.indexOf(logical) < 0)
|
||||||
|
ifaceMap[ifname].labels.push(logical);
|
||||||
|
});
|
||||||
|
|
||||||
|
(devices || []).forEach(function(dev) {
|
||||||
|
var name = dev.getName();
|
||||||
|
if (!name || name === 'lo')
|
||||||
|
return;
|
||||||
|
|
||||||
|
ifaceMap[name] = ifaceMap[name] || { labels: [] };
|
||||||
|
});
|
||||||
|
|
||||||
|
Object.keys(ifaceMap).sort().forEach(function(ifname) {
|
||||||
|
var labels = ifaceMap[ifname].labels;
|
||||||
|
var text = labels.length ? '%s (%s)'.format(labels.join(', '), ifname) : ifname;
|
||||||
|
o.value(ifname, text);
|
||||||
|
});
|
||||||
|
|
||||||
|
o = s.option(form.Value, 'sample_seconds', _('Idle sampling duration (seconds)'));
|
||||||
|
o.datatype = 'uinteger';
|
||||||
|
o.placeholder = '120';
|
||||||
|
o.rmempty = false;
|
||||||
|
|
||||||
|
o = s.option(form.Value, 'byte_threshold', _('Idle threshold (bytes)'));
|
||||||
|
o.datatype = 'uinteger';
|
||||||
|
o.placeholder = '262144';
|
||||||
|
o.rmempty = false;
|
||||||
|
|
||||||
|
return m.render();
|
||||||
|
}
|
||||||
|
});
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: ar\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "إعادة تشغيل ذكية"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "أعد التشغيل فقط عندما تكون الشبكة خاملة في وقت الفجر المحدد."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "الإعدادات"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "تمكين"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "آخر إعادة تشغيل تلقائية"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "أبدًا"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "وقت إعادة التشغيل (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "يجب أن يكون تنسيق الوقت HH:MM (24 ساعة). مثال: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "تحديد جميع الواجهات"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "الواجهات المُراقبة"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "مدة أخذ عينات الخمول (ثوانٍ)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "حد الخمول (بايت)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: de\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Intelligenter Neustart"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Nur neu starten, wenn das Netzwerk zur konfigurierten Zeit im Leerlauf ist."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Einstellungen"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Aktivieren"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Letzter automatischer Neustart"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Nie"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Neustartzeit (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Zeitformat muss HH:MM (24-Stunden) sein. Beispiel: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Alle Schnittstellen auswählen"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Überwachte Schnittstellen"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Leerlauf-Abtastdauer (Sekunden)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Leerlauf-Schwellenwert (Bytes)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: es\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Reinicio inteligente"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Reiniciar solo cuando la red esté inactiva a la hora de madrugada configurada."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Configuración"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Habilitar"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Último reinicio automático"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Nunca"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Hora de reinicio (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "El formato de hora debe ser HH:MM (24 horas). Ejemplo: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Seleccionar todas las interfaces"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Interfaces monitorizadas"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Duración de muestreo de inactividad (segundos)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Umbral de inactividad (bytes)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: fr\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Redémarrage intelligent"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Redémarrer uniquement lorsque le réseau est inactif à l'heure d'aube configurée."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Paramètres"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Activer"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Dernier redémarrage automatique"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Jamais"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Heure de redémarrage (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Le format de l'heure doit être HH:MM (24h). Exemple : 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Sélectionner toutes les interfaces"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Interfaces surveillées"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Durée d'échantillonnage d'inactivité (secondes)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Seuil d'inactivité (octets)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: id\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Reboot Cerdas"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Reboot hanya saat jaringan idle pada waktu dini hari yang dikonfigurasi."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Pengaturan"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Aktifkan"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Reboot otomatis terakhir"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Tidak pernah"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Waktu reboot (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Format waktu harus HH:MM (24 jam). Contoh: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Pilih semua antarmuka"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Antarmuka yang dipantau"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Durasi sampling idle (detik)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Ambang idle (byte)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: it\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Riavvio intelligente"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Riavvia solo quando la rete è inattiva all'ora dell'alba configurata."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Impostazioni"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Abilita"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Ultimo riavvio automatico"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Mai"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Ora di riavvio (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Il formato orario deve essere HH:MM (24 ore). Esempio: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Seleziona tutte le interfacce"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Interfacce monitorate"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Durata campionamento inattività (secondi)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Soglia inattività (byte)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: ja\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "スマート再起動"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "設定した早朝時刻に、ネットワークがアイドル状態のときのみ再起動します。"
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "設定"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "有効化"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "前回の自動再起動"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "なし"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "再起動時刻 (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "時刻形式は HH:MM(24時間)で入力してください。例: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "すべてのインターフェースを選択"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "監視対象インターフェース"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "アイドル判定サンプリング時間(秒)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "アイドル閾値(バイト)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "스마트 재부팅"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "설정한 새벽 시각에 네트워크가 유휴 상태일 때만 재부팅합니다."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "설정"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "활성화"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "마지막 자동 재부팅"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "없음"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "재부팅 시각 (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "시간 형식은 HH:MM(24시간제)이어야 합니다. 예: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "전체 인터페이스 선택"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "모니터링 인터페이스"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "유휴 샘플링 시간(초)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "유휴 임계값(바이트)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: nl\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Slimme herstart"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Herstart alleen wanneer het netwerk inactief is op de ingestelde ochtendtijd."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Instellingen"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Inschakelen"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Laatste automatische herstart"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Nooit"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Herstarttijd (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Tijdnotatie moet HH:MM (24-uurs) zijn. Voorbeeld: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Alle interfaces selecteren"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Gemonitorde interfaces"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Duur van inactiviteitsmeting (seconden)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Inactiviteitsdrempel (bytes)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: pl\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Inteligentny restart"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Uruchom ponownie tylko wtedy, gdy sieć jest bezczynna o skonfigurowanej porze nad ranem."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Ustawienia"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Włącz"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Ostatni automatyczny restart"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Nigdy"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Godzina restartu (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Format czasu musi być HH:MM (24-godzinny). Przykład: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Wybierz wszystkie interfejsy"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Monitorowane interfejsy"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Czas próbkowania bezczynności (sekundy)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Próg bezczynności (bajty)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: pt_BR\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Reinicialização inteligente"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Reinicia somente quando a rede estiver ociosa no horário de madrugada configurado."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Configurações"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Ativar"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Última reinicialização automática"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Nunca"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Horário de reinicialização (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "O formato de hora deve ser HH:MM (24 horas). Exemplo: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Selecionar todas as interfaces"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Interfaces monitoradas"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Duração da amostragem de ociosidade (segundos)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Limite de ociosidade (bytes)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: ru\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Умная перезагрузка"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Перезагружать только когда сеть неактивна в заданное раннее время."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Настройки"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Включить"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Последняя автоматическая перезагрузка"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Никогда"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Время перезагрузки (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Формат времени должен быть HH:MM (24 часа). Пример: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Выбрать все интерфейсы"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Отслеживаемые интерфейсы"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Длительность проверки простоя (сек.)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Порог простоя (байт)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: th\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "รีบูตอัจฉริยะ"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "รีบูตเฉพาะเมื่อเครือข่ายว่างในเวลาช่วงเช้ามืดที่ตั้งค่าไว้"
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "การตั้งค่า"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "เปิดใช้งาน"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "รีบูตอัตโนมัติครั้งล่าสุด"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "ไม่เคย"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "เวลารีบูต (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "รูปแบบเวลาต้องเป็น HH:MM (24 ชั่วโมง) ตัวอย่าง: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "เลือกทุกอินเทอร์เฟซ"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "อินเทอร์เฟซที่เฝ้าตรวจ"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "ระยะเวลาสุ่มตัวอย่างสถานะว่าง (วินาที)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "เกณฑ์สถานะว่าง (ไบต์)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: tr\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Akıllı Yeniden Başlatma"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Yalnızca ağ, ayarlanan şafak saatinde boşta olduğunda yeniden başlat."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Ayarlar"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Etkinleştir"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Son otomatik yeniden başlatma"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Asla"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Yeniden başlatma saati (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Saat biçimi HH:MM (24 saat) olmalıdır. Örnek: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Tüm arayüzleri seç"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "İzlenen arayüzler"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Boşta örnekleme süresi (saniye)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Boşta eşiği (bayt)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: uk\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Розумне перезавантаження"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Перезавантажувати лише коли мережа неактивна у заданий ранковий час."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Налаштування"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Увімкнути"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Останнє автоматичне перезавантаження"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Ніколи"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Час перезавантаження (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Формат часу має бути HH:MM (24-годинний). Приклад: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Вибрати всі інтерфейси"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Інтерфейси моніторингу"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Тривалість перевірки простою (секунди)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Поріг простою (байти)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: vi\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "Khởi động lại thông minh"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "Chỉ khởi động lại khi mạng nhàn rỗi vào thời điểm rạng sáng đã cấu hình."
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "Cài đặt"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "Bật"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "Lần khởi động lại tự động gần nhất"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "Chưa từng"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "Thời gian khởi động lại (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "Định dạng thời gian phải là HH:MM (24 giờ). Ví dụ: 04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "Chọn tất cả giao diện"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "Giao diện được giám sát"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "Thời lượng lấy mẫu nhàn rỗi (giây)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "Ngưỡng nhàn rỗi (byte)"
|
||||||
Symlink
+1
@@ -0,0 +1 @@
|
|||||||
|
zh_Hans
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: zh_Hans\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "智能重启"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "仅在设定的凌晨时间且网络空闲时才重启。"
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "设置"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "启用"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "上次自动重启"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "从未"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "重启时间 (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "时间格式必须为 HH:MM(24小时制)。示例:04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "选择所有接口"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "监控接口"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "空闲采样时长(秒)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "空闲阈值(字节)"
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
msgid ""
|
||||||
|
msgstr "Content-Type: text/plain; charset=UTF-8\nLanguage: zh_Hant\n"
|
||||||
|
|
||||||
|
msgid "Smart Reboot"
|
||||||
|
msgstr "智慧重新啟動"
|
||||||
|
|
||||||
|
msgid "Reboot only when the network is idle at the configured dawn time."
|
||||||
|
msgstr "僅在設定的清晨時間且網路閒置時才重新啟動。"
|
||||||
|
|
||||||
|
msgid "Settings"
|
||||||
|
msgstr "設定"
|
||||||
|
|
||||||
|
msgid "Enable"
|
||||||
|
msgstr "啟用"
|
||||||
|
|
||||||
|
msgid "Last automatic reboot"
|
||||||
|
msgstr "上次自動重新啟動"
|
||||||
|
|
||||||
|
msgid "Never"
|
||||||
|
msgstr "從不"
|
||||||
|
|
||||||
|
msgid "Reboot time (HH:MM)"
|
||||||
|
msgstr "重新啟動時間 (HH:MM)"
|
||||||
|
|
||||||
|
msgid "Time format must be HH:MM (24-hour). Example: 04:00"
|
||||||
|
msgstr "時間格式必須為 HH:MM(24 小時制)。例如:04:00"
|
||||||
|
|
||||||
|
msgid "Select all interfaces"
|
||||||
|
msgstr "選擇所有介面"
|
||||||
|
|
||||||
|
msgid "Monitored interfaces"
|
||||||
|
msgstr "監控介面"
|
||||||
|
|
||||||
|
msgid "Idle sampling duration (seconds)"
|
||||||
|
msgstr "閒置取樣時長(秒)"
|
||||||
|
|
||||||
|
msgid "Idle threshold (bytes)"
|
||||||
|
msgstr "閒置閾值(位元組)"
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
{
|
||||||
|
"admin/system/smart-reboot": {
|
||||||
|
"title": "Smart Reboot",
|
||||||
|
"order": 95,
|
||||||
|
"action": {
|
||||||
|
"type": "view",
|
||||||
|
"path": "system/smart-reboot"
|
||||||
|
},
|
||||||
|
"depends": {
|
||||||
|
"acl": [
|
||||||
|
"luci-app-smart-reboot"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
{
|
||||||
|
"luci-app-smart-reboot": {
|
||||||
|
"description": "Grant access to smart-reboot UCI config",
|
||||||
|
"read": {
|
||||||
|
"uci": [
|
||||||
|
"smart-reboot"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"write": {
|
||||||
|
"uci": [
|
||||||
|
"smart-reboot"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,47 @@
|
|||||||
|
include $(TOPDIR)/rules.mk
|
||||||
|
|
||||||
|
PKG_NAME:=smart-reboot
|
||||||
|
PKG_RELEASE:=1
|
||||||
|
|
||||||
|
include $(INCLUDE_DIR)/package.mk
|
||||||
|
|
||||||
|
define Package/smart-reboot
|
||||||
|
SECTION:=utils
|
||||||
|
CATEGORY:=Utilities
|
||||||
|
TITLE:=Smart reboot based on network idle state
|
||||||
|
DEPENDS:=+busybox +uci +ucode +ucode-mod-uci +ucode-mod-log
|
||||||
|
endef
|
||||||
|
|
||||||
|
define Package/smart-reboot/description
|
||||||
|
Reboot router at configured dawn time only when monitored interfaces are idle.
|
||||||
|
endef
|
||||||
|
|
||||||
|
define Package/smart-reboot/conffiles
|
||||||
|
/etc/config/smart-reboot
|
||||||
|
endef
|
||||||
|
|
||||||
|
define Build/Compile
|
||||||
|
true
|
||||||
|
endef
|
||||||
|
|
||||||
|
define Package/smart-reboot/install
|
||||||
|
$(INSTALL_DIR) $(1)/etc/config
|
||||||
|
$(INSTALL_CONF) ./files/etc/config/smart-reboot $(1)/etc/config/smart-reboot
|
||||||
|
|
||||||
|
$(INSTALL_DIR) $(1)/etc/init.d
|
||||||
|
$(INSTALL_BIN) ./files/etc/init.d/smart-reboot $(1)/etc/init.d/smart-reboot
|
||||||
|
|
||||||
|
$(INSTALL_DIR) $(1)/usr/sbin
|
||||||
|
$(INSTALL_BIN) ./files/usr/sbin/smart-reboot-check $(1)/usr/sbin/smart-reboot-check
|
||||||
|
endef
|
||||||
|
|
||||||
|
define Package/smart-reboot/postinst
|
||||||
|
#!/bin/sh
|
||||||
|
[ -n "$$IPKG_INSTROOT" ] || {
|
||||||
|
/etc/init.d/smart-reboot enable >/dev/null 2>&1
|
||||||
|
/etc/init.d/smart-reboot restart >/dev/null 2>&1
|
||||||
|
}
|
||||||
|
exit 0
|
||||||
|
endef
|
||||||
|
|
||||||
|
$(eval $(call BuildPackage,smart-reboot))
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
config settings 'settings'
|
||||||
|
option enabled '1'
|
||||||
|
option time '04:00'
|
||||||
|
option all_ifaces '0'
|
||||||
|
option last_auto_reboot ''
|
||||||
|
list ifaces 'wan'
|
||||||
|
option sample_seconds '120'
|
||||||
|
option byte_threshold '262144'
|
||||||
@@ -0,0 +1,68 @@
|
|||||||
|
#!/bin/sh /etc/rc.common
|
||||||
|
|
||||||
|
START=95
|
||||||
|
STOP=10
|
||||||
|
|
||||||
|
CRON_FILE="/etc/crontabs/root"
|
||||||
|
MARKER="# smart-reboot"
|
||||||
|
|
||||||
|
. /lib/functions.sh
|
||||||
|
|
||||||
|
cron_cleanup() {
|
||||||
|
[ -f "$CRON_FILE" ] || return 0
|
||||||
|
sed -i "\\|$MARKER|d" "$CRON_FILE"
|
||||||
|
}
|
||||||
|
|
||||||
|
cron_append() {
|
||||||
|
local minute="$1"
|
||||||
|
local hour="$2"
|
||||||
|
echo "$minute $hour * * * /usr/sbin/smart-reboot-check $MARKER" >> "$CRON_FILE"
|
||||||
|
}
|
||||||
|
|
||||||
|
gen_schedule() {
|
||||||
|
local enabled hour minute time
|
||||||
|
|
||||||
|
config_load smart-reboot
|
||||||
|
config_get enabled settings enabled '0'
|
||||||
|
config_get time settings time ''
|
||||||
|
|
||||||
|
case "$time" in
|
||||||
|
[0-1][0-9]:[0-5][0-9]|2[0-3]:[0-5][0-9])
|
||||||
|
hour="${time%:*}"
|
||||||
|
minute="${time#*:}"
|
||||||
|
hour=$((10#$hour))
|
||||||
|
minute=$((10#$minute))
|
||||||
|
;;
|
||||||
|
*)
|
||||||
|
config_get hour settings hour '4'
|
||||||
|
config_get minute settings minute '0'
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
cron_cleanup
|
||||||
|
|
||||||
|
[ "$enabled" = "1" ] || return 0
|
||||||
|
[ -n "$hour" ] || return 0
|
||||||
|
[ -n "$minute" ] || return 0
|
||||||
|
|
||||||
|
cron_append "$minute" "$hour"
|
||||||
|
}
|
||||||
|
|
||||||
|
reload_service() {
|
||||||
|
start_service
|
||||||
|
}
|
||||||
|
|
||||||
|
start_service() {
|
||||||
|
[ -f "$CRON_FILE" ] || touch "$CRON_FILE"
|
||||||
|
gen_schedule
|
||||||
|
/etc/init.d/cron restart >/dev/null 2>&1
|
||||||
|
}
|
||||||
|
|
||||||
|
stop_service() {
|
||||||
|
cron_cleanup
|
||||||
|
/etc/init.d/cron restart >/dev/null 2>&1
|
||||||
|
}
|
||||||
|
|
||||||
|
service_triggers() {
|
||||||
|
procd_add_reload_trigger "smart-reboot"
|
||||||
|
}
|
||||||
@@ -0,0 +1,171 @@
|
|||||||
|
#!/usr/bin/ucode
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
import * as uci from "uci";
|
||||||
|
import * as log from "log";
|
||||||
|
import * as fs from "fs";
|
||||||
|
|
||||||
|
const CFG = "smart-reboot";
|
||||||
|
const SECTION = "settings";
|
||||||
|
const LOCK_FILE = "/var/lock/smart-reboot.lock";
|
||||||
|
|
||||||
|
function shquote(s) {
|
||||||
|
return "'" + replace(s, /'/g, "'\\''") + "'";
|
||||||
|
}
|
||||||
|
|
||||||
|
function cmd_out(cmd) {
|
||||||
|
let f = fs.popen(cmd, "r");
|
||||||
|
if (!f)
|
||||||
|
return "";
|
||||||
|
|
||||||
|
let out = f.read("all") ?? "";
|
||||||
|
f.close();
|
||||||
|
return trim(out);
|
||||||
|
}
|
||||||
|
|
||||||
|
let cursor = uci.cursor();
|
||||||
|
|
||||||
|
function cfg_get(key, def) {
|
||||||
|
let val = cursor.get(CFG, SECTION, key);
|
||||||
|
|
||||||
|
if (val == null)
|
||||||
|
return def;
|
||||||
|
|
||||||
|
if (type(val) == "string" && !length(val))
|
||||||
|
return def;
|
||||||
|
|
||||||
|
return val;
|
||||||
|
}
|
||||||
|
|
||||||
|
function logger(msg) {
|
||||||
|
log.syslog(log.LOG_INFO, msg);
|
||||||
|
}
|
||||||
|
|
||||||
|
function set_last_auto_reboot() {
|
||||||
|
let ts = cmd_out("date '+%Y-%m-%d %H:%M:%S'");
|
||||||
|
cursor.set(CFG, SECTION, "last_auto_reboot", ts);
|
||||||
|
cursor.commit(CFG);
|
||||||
|
}
|
||||||
|
|
||||||
|
function list_all_ifaces() {
|
||||||
|
let out = [];
|
||||||
|
for (let path in fs.glob("/sys/class/net/*")) {
|
||||||
|
let name = fs.basename(path);
|
||||||
|
if (name && name != "lo")
|
||||||
|
push(out, name);
|
||||||
|
}
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
function parse_ifaces(raw) {
|
||||||
|
if (!raw)
|
||||||
|
return [];
|
||||||
|
|
||||||
|
if (type(raw) == "array")
|
||||||
|
return raw;
|
||||||
|
|
||||||
|
return filter(split(raw, /[ \t\r\n]+/), v => length(v));
|
||||||
|
}
|
||||||
|
|
||||||
|
function sum_iface_bytes(ifaces) {
|
||||||
|
let total = 0;
|
||||||
|
|
||||||
|
for (let iface in ifaces) {
|
||||||
|
if (!iface)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
let rx = trim(fs.readfile(`/sys/class/net/${iface}/statistics/rx_bytes`) ?? "0");
|
||||||
|
let tx = trim(fs.readfile(`/sys/class/net/${iface}/statistics/tx_bytes`) ?? "0");
|
||||||
|
total += int(rx || "0") + int(tx || "0");
|
||||||
|
}
|
||||||
|
|
||||||
|
return total;
|
||||||
|
}
|
||||||
|
|
||||||
|
function parse_time(time_str) {
|
||||||
|
if (!time_str || index(time_str, ":") < 0)
|
||||||
|
return null;
|
||||||
|
|
||||||
|
let parts = split(time_str, ":");
|
||||||
|
if (length(parts) != 2)
|
||||||
|
return null;
|
||||||
|
|
||||||
|
let hour = int(parts[0]);
|
||||||
|
let minute = int(parts[1]);
|
||||||
|
|
||||||
|
if (hour < 0 || hour > 23 || minute < 0 || minute > 59)
|
||||||
|
return null;
|
||||||
|
|
||||||
|
return { hour, minute };
|
||||||
|
}
|
||||||
|
|
||||||
|
function main() {
|
||||||
|
log.openlog("smart-reboot", log.LOG_PID);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Acquire an exclusive non-blocking lock on the lock file using the
|
||||||
|
* native ucode fs.file.lock() API instead of shelling out to `lock`. This
|
||||||
|
* avoids spawning a new process on every invocation and is what the
|
||||||
|
* reviewer suggested.
|
||||||
|
*/
|
||||||
|
let lockfd = fs.open(LOCK_FILE, "w+");
|
||||||
|
if (!lockfd || !lockfd.lock("xn"))
|
||||||
|
return 0; /* cannot obtain lock */
|
||||||
|
|
||||||
|
/* helper to release and close the handle */
|
||||||
|
function cleanup() {
|
||||||
|
if (lockfd) {
|
||||||
|
lockfd.lock("u");
|
||||||
|
lockfd.close();
|
||||||
|
lockfd = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let enabled = cfg_get("enabled", "0");
|
||||||
|
if (enabled != "1") {
|
||||||
|
cleanup();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
let parsed = parse_time(cfg_get("time", ""));
|
||||||
|
let hour = parsed ? parsed.hour : int(cfg_get("hour", "4"));
|
||||||
|
let minute = parsed ? parsed.minute : int(cfg_get("minute", "0"));
|
||||||
|
|
||||||
|
let sample_seconds = int(cfg_get("sample_seconds", "120"));
|
||||||
|
let byte_threshold = int(cfg_get("byte_threshold", "262144"));
|
||||||
|
let all_ifaces = cfg_get("all_ifaces", "0");
|
||||||
|
let ifaces = parse_ifaces(cfg_get("ifaces", []));
|
||||||
|
|
||||||
|
if (all_ifaces == "1") {
|
||||||
|
ifaces = list_all_ifaces();
|
||||||
|
}
|
||||||
|
else if (!length(ifaces)) {
|
||||||
|
logger("No monitored interfaces configured. Set smart-reboot.settings.ifaces or enable all_ifaces.");
|
||||||
|
cleanup();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
let now = localtime(time());
|
||||||
|
if (now.hour != hour || now.min != minute) {
|
||||||
|
cleanup();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
let start_bytes = sum_iface_bytes(ifaces);
|
||||||
|
/* use built-in sleep (milliseconds) instead of shelling out */
|
||||||
|
sleep(sample_seconds * 1000);
|
||||||
|
let end_bytes = sum_iface_bytes(ifaces);
|
||||||
|
let delta = end_bytes - start_bytes;
|
||||||
|
|
||||||
|
if (delta <= byte_threshold) {
|
||||||
|
logger(`Network idle detected (delta=${delta} bytes, threshold=${byte_threshold}), rebooting now`);
|
||||||
|
set_last_auto_reboot();
|
||||||
|
system("/sbin/reboot");
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
logger(`Skip reboot, network is active (delta=${delta} bytes, threshold=${byte_threshold})`);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* release lock before exiting */
|
||||||
|
cleanup();
|
||||||
|
exit(main());
|
||||||
Reference in new issue
Block a user