mirror of
https://github.com/gSpotx2f/luci-app-internet-detector.git
synced 2025-12-06 03:26:50 +03:00
v1.7. New optional checking feature: URL test.
This commit is contained in:
@@ -5,7 +5,7 @@
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=internet-detector
|
||||
PKG_VERSION:=1.6.7
|
||||
PKG_VERSION:=1.7.0
|
||||
PKG_RELEASE:=1
|
||||
PKG_MAINTAINER:=gSpot <https://github.com/gSpotx2f/luci-app-internet-detector>
|
||||
|
||||
|
||||
@@ -8,6 +8,7 @@ config instance 'internet'
|
||||
option description 'Default instance'
|
||||
list hosts '8.8.8.8'
|
||||
list hosts '1.1.1.1'
|
||||
list urls 'https://www.google.com'
|
||||
option check_type '0'
|
||||
option tcp_port '53'
|
||||
option interval_up '30'
|
||||
|
||||
@@ -12,32 +12,8 @@ local uci = require("uci")
|
||||
-- Default settings
|
||||
|
||||
local InternetDetector = {
|
||||
mode = 0, -- 0: disabled, 1: Service, 2: UI detector
|
||||
loggingLevel = 6,
|
||||
hostname = "OpenWrt",
|
||||
appName = "internet-detector",
|
||||
libDir = "/usr/lib/lua",
|
||||
pingCmd = "/bin/ping",
|
||||
pingParams = "-c 1",
|
||||
uiRunTime = 30,
|
||||
noModules = false,
|
||||
uiAvailModules = { mod_public_ip = true },
|
||||
debug = false,
|
||||
serviceConfig = {
|
||||
hosts = {
|
||||
[1] = "8.8.8.8",
|
||||
[2] = "1.1.1.1",
|
||||
},
|
||||
check_type = 0, -- 0: TCP, 1: ICMP
|
||||
tcp_port = 53,
|
||||
icmp_packet_size = 56,
|
||||
interval_up = 30,
|
||||
interval_down = 5,
|
||||
connection_attempts = 2,
|
||||
connection_timeout = 2,
|
||||
iface = nil,
|
||||
instance = nil,
|
||||
},
|
||||
logLevels = {
|
||||
emerg = { level = syslog.LOG_EMERG, num = 0 },
|
||||
alert = { level = syslog.LOG_ALERT, num = 1 },
|
||||
@@ -48,8 +24,41 @@ local InternetDetector = {
|
||||
info = { level = syslog.LOG_INFO, num = 6 },
|
||||
debug = { level = syslog.LOG_DEBUG, num = 7 },
|
||||
},
|
||||
pingCmd = "/bin/ping",
|
||||
pingParams = "-c 1",
|
||||
curlExec = "/usr/bin/curl",
|
||||
curlParams = '-s --no-keepalive --head --user-agent "Mozilla/5.0 (X11; Linux x86_64; rv:142.0) Gecko/20100101 Firefox/142.0"',
|
||||
mode = 0, -- 0: disabled, 1: Service, 2: UI detector
|
||||
loggingLevel = 6,
|
||||
hostname = "OpenWrt",
|
||||
uiRunTime = 30,
|
||||
noModules = false,
|
||||
uiAvailModules = { mod_public_ip = true },
|
||||
debug = false,
|
||||
serviceConfig = {
|
||||
hosts = {
|
||||
[1] = "8.8.8.8",
|
||||
[2] = "1.1.1.1",
|
||||
},
|
||||
urls = {
|
||||
[1] = "https://www.google.com",
|
||||
},
|
||||
check_type = 0, -- 0: TCP, 1: ICMP
|
||||
tcp_port = 53,
|
||||
icmp_packet_size = 56,
|
||||
interval_up = 30,
|
||||
interval_down = 5,
|
||||
connection_attempts = 2,
|
||||
connection_timeout = 2,
|
||||
proxy_type = nil,
|
||||
proxy_host = nil,
|
||||
proxy_port = nil,
|
||||
iface = nil,
|
||||
instance = nil,
|
||||
},
|
||||
modules = {},
|
||||
parsedHosts = {},
|
||||
proxyString = "",
|
||||
uiCounter = 0,
|
||||
pidFile = nil,
|
||||
statusFile = nil,
|
||||
@@ -213,6 +222,13 @@ function InternetDetector:parseHosts()
|
||||
end
|
||||
end
|
||||
|
||||
function InternetDetector:parseUrls()
|
||||
self.parsedHosts = {}
|
||||
for k, v in ipairs(self.serviceConfig.urls) do
|
||||
self.parsedHosts[k] = { addr = v }
|
||||
end
|
||||
end
|
||||
|
||||
function InternetDetector:pingHost(host)
|
||||
local ping = string.format(
|
||||
"%s %s -W %d -s %d%s %s > /dev/null 2>&1",
|
||||
@@ -240,6 +256,7 @@ function InternetDetector:TCPConnectionToHost(host, port)
|
||||
"GETADDRINFO ERROR: %s, %s", errMsg, errNum))
|
||||
else
|
||||
local family = saTable[1].family
|
||||
|
||||
if family then
|
||||
local sock, errMsg, errNum = socket.socket(family, socket.SOCK_STREAM, 0)
|
||||
|
||||
@@ -307,6 +324,60 @@ function InternetDetector:TCPConnectionToHost(host, port)
|
||||
return retCode
|
||||
end
|
||||
|
||||
function InternetDetector:httpRequest(url)
|
||||
local retCode = 1, data
|
||||
local curl = string.format(
|
||||
'%s%s%s --connect-timeout %s %s "%s"; printf "\n$?";',
|
||||
self.curlExec,
|
||||
self.serviceConfig.iface and (" --interface " .. self.serviceConfig.iface) or "",
|
||||
self.proxyString,
|
||||
self.serviceConfig.connection_timeout,
|
||||
self.curlParams,
|
||||
url
|
||||
)
|
||||
local fh = io.popen(curl, "r")
|
||||
if fh then
|
||||
data = fh:read("*a")
|
||||
fh:close()
|
||||
if data ~= nil then
|
||||
local s, e = data:find("[0-9]+\n?$")
|
||||
retCode = tonumber(data:sub(s))
|
||||
data = data:sub(0, s - 2)
|
||||
if not data or data == "" then
|
||||
data = nil
|
||||
end
|
||||
end
|
||||
else
|
||||
retCode = 1
|
||||
end
|
||||
|
||||
self:debugOutput(string.format(
|
||||
"--- Curl ---\ntime = %s\n%s\nretCode = %s\ndata = [\n%s]\n",
|
||||
os.time(),
|
||||
curl,
|
||||
retCode,
|
||||
tostring(data)))
|
||||
return retCode, data
|
||||
end
|
||||
|
||||
function InternetDetector:getHTTPCode(data)
|
||||
local httpCode
|
||||
local respHeader = data:match("^HTTP/[^%c]+")
|
||||
if respHeader then
|
||||
httpCode = respHeader:match("%d%d%d")
|
||||
end
|
||||
return tonumber(httpCode)
|
||||
end
|
||||
|
||||
function InternetDetector:checkURL(url)
|
||||
local httpCode
|
||||
local retCode, data = self:httpRequest(url)
|
||||
if retCode == 0 and data then
|
||||
httpCode = self:getHTTPCode(data)
|
||||
end
|
||||
return (httpCode ~= 200) and 1 or 0
|
||||
end
|
||||
|
||||
function InternetDetector:exit()
|
||||
for _, e in ipairs(self.modules) do
|
||||
e:onExit()
|
||||
@@ -339,7 +410,25 @@ function InternetDetector:mainLoop()
|
||||
local checking = false
|
||||
local hostNum = 1
|
||||
local attempt = 1
|
||||
local checkFunc = (self.serviceConfig.check_type == 1) and self.pingHost or self.TCPConnectionToHost
|
||||
|
||||
local checkFunc = self.TCPConnectionToHost
|
||||
if self.serviceConfig.check_type == 1 then
|
||||
checkFunc = self.pingHost
|
||||
self:parseHosts()
|
||||
elseif self.serviceConfig.check_type == 2 then
|
||||
checkFunc = self.checkURL
|
||||
self:parseUrls()
|
||||
if (self.serviceConfig.proxy_type and self.serviceConfig.proxy_host and
|
||||
self.serviceConfig.proxy_port) then
|
||||
self.proxyString = string.format(
|
||||
" --proxy %s://%s:%d",
|
||||
self.serviceConfig.proxy_type,
|
||||
self.serviceConfig.proxy_host,
|
||||
self.serviceConfig.proxy_port)
|
||||
end
|
||||
else
|
||||
self:parseHosts()
|
||||
end
|
||||
|
||||
self:writeValueToFile(
|
||||
self.statusFile, self:statusJson(currentStatus, self.serviceConfig.instance))
|
||||
@@ -599,6 +688,11 @@ function InternetDetector:preRun()
|
||||
os.exit(1)
|
||||
end
|
||||
end
|
||||
if self.serviceConfig.check_type == 2 and not unistd.access(self.curlExec, "x") then
|
||||
io.stderr:write(string.format(
|
||||
"Error, %s is not available. You need to install curl.\n", self.curlExec))
|
||||
os.exit(1)
|
||||
end
|
||||
local ok, commonDir = pcall(dirent.files, self.commonDir)
|
||||
if ok then
|
||||
local instancePattern = "^" .. self.appNamePattern .. "%." .. self.serviceConfig.instance .. "%.[%d]+%.pid$"
|
||||
@@ -689,7 +783,6 @@ end
|
||||
|
||||
function InternetDetector:setServiceConfig(instance)
|
||||
if self:loadInstanceConfig(instance) then
|
||||
self:parseHosts()
|
||||
if self.mode == 2 then
|
||||
self.loggingLevel = 0
|
||||
self.noModules = true
|
||||
|
||||
@@ -10,7 +10,10 @@ local Module = {
|
||||
noModules = false,
|
||||
debug = false,
|
||||
serviceConfig = {
|
||||
iface = nil,
|
||||
iface = nil,
|
||||
proxy_type = nil,
|
||||
proxy_host = nil,
|
||||
proxy_port = nil,
|
||||
},
|
||||
},
|
||||
syslog = function(level, msg) return true end,
|
||||
@@ -24,7 +27,7 @@ local Module = {
|
||||
requestAttempts = 2,
|
||||
timeout = 3,
|
||||
curlExec = "/usr/bin/curl",
|
||||
curlParams = "-s",
|
||||
curlParams = '-s --no-keepalive --user-agent "Mozilla/5.0 (X11; Linux x86_64; rv:142.0) Gecko/20100101 Firefox/142.0"',
|
||||
providers = {
|
||||
opendns1 = {
|
||||
name = "opendns1", type = "dns", host = "myip.opendns.com",
|
||||
@@ -88,6 +91,7 @@ local Module = {
|
||||
ipScript = "",
|
||||
enableIpScript = false,
|
||||
status = nil,
|
||||
_proxyString = "",
|
||||
_provider = nil,
|
||||
_qtype = false,
|
||||
_currentIp = nil,
|
||||
@@ -177,6 +181,7 @@ function Module:sendUDPMessage(message, server, port)
|
||||
"GETADDRINFO ERROR: %s, %s", errMsg, errNum))
|
||||
else
|
||||
local family = saTable[1].family
|
||||
|
||||
if family then
|
||||
local sock, errMsg, errNum = socket.socket(family, socket.SOCK_DGRAM, 0)
|
||||
|
||||
@@ -266,12 +271,13 @@ function Module:decodeMessage(message)
|
||||
local NSCOUNT = message:sub(17, 20)
|
||||
local ARCOUNT = message:sub(21, 24)
|
||||
|
||||
-- Question section
|
||||
local questionSectionStarts = 25
|
||||
|
||||
local questionParts = self:parseParts(message, questionSectionStarts, {})
|
||||
local qtypeStarts = questionSectionStarts + (#table.concat(questionParts)) + (#questionParts * 2) + 1
|
||||
local qclassStarts = qtypeStarts + 4
|
||||
|
||||
-- Answer section
|
||||
local answerSectionStarts = qclassStarts + 4
|
||||
local numAnswers = math.max(
|
||||
tonumber(ANCOUNT, 16), tonumber(NSCOUNT, 16), tonumber(ARCOUNT, 16))
|
||||
@@ -351,9 +357,10 @@ end
|
||||
function Module:httpRequest(url)
|
||||
local retCode = 1, data
|
||||
local curl = string.format(
|
||||
'%s%s --connect-timeout %s %s "%s"; printf "\n$?";',
|
||||
'%s%s%s --connect-timeout %s %s "%s"; printf "\n$?";',
|
||||
self.curlExec,
|
||||
self.config.serviceConfig.iface and (" --interface " .. self.config.serviceConfig.iface) or "",
|
||||
self._proxyString,
|
||||
self.timeout,
|
||||
self.curlParams,
|
||||
url
|
||||
@@ -373,6 +380,14 @@ function Module:httpRequest(url)
|
||||
else
|
||||
retCode = 1
|
||||
end
|
||||
|
||||
self.debugOutput(string.format(
|
||||
"--- Curl ---\ntime = %s\n%s\nretCode = %s\ndata = [\n%s]\n",
|
||||
os.time(),
|
||||
curl,
|
||||
retCode,
|
||||
tostring(data))
|
||||
)
|
||||
return retCode, data
|
||||
end
|
||||
|
||||
@@ -454,6 +469,15 @@ function Module:init(t)
|
||||
self._enabled = false
|
||||
end
|
||||
end
|
||||
if (self.config.serviceConfig.proxy_type and
|
||||
self.config.serviceConfig.proxy_host and
|
||||
self.config.serviceConfig.proxy_port) then
|
||||
self._proxyString = string.format(
|
||||
" --proxy %s://%s:%d",
|
||||
self.config.serviceConfig.proxy_type,
|
||||
self.config.serviceConfig.proxy_host,
|
||||
self.config.serviceConfig.proxy_port)
|
||||
end
|
||||
end
|
||||
|
||||
function Module:run(currentStatus, lastStatus, timeDiff, timeNow, inetChecked)
|
||||
|
||||
Reference in New Issue
Block a user