Timer NodeMCU计时器意外停止
我有一个NodeMCU Lua应用程序,它使用两个计时器。每个计时器调用一个函数,该函数导致向本地服务器发出HTTP请求 经过几次迭代后,其中一个计时器停止,另一个计时器继续。计时器停止前的迭代次数似乎是随机的。我已经运行了很多次测试脚本,而计时器停止的时间点从来都不一样。注意:停止的计时器并不总是相同的 下面是一些可靠地演示此问题的测试代码:Timer NodeMCU计时器意外停止,timer,lua,nodemcu,Timer,Lua,Nodemcu,我有一个NodeMCU Lua应用程序,它使用两个计时器。每个计时器调用一个函数,该函数导致向本地服务器发出HTTP请求 经过几次迭代后,其中一个计时器停止,另一个计时器继续。计时器停止前的迭代次数似乎是随机的。我已经运行了很多次测试脚本,而计时器停止的时间点从来都不一样。注意:停止的计时器并不总是相同的 下面是一些可靠地演示此问题的测试代码: ctr1=0 ctr2=0 local function doCmdChk() ctr1 = ctr1 + 1 http.get( "
ctr1=0
ctr2=0
local function doCmdChk()
ctr1 = ctr1 + 1
http.get( "http://192.168.2.38/ICmd.py?i=" .. ctr1 , nil,
function(rspCode, payload)
tmr.start(1)
end)
end
local function sendData()
ctr2 = ctr2 + 1
local msgBdy = '{"s":"' .. ctr2 .. '","i":"test23", "d":"heap='..node.heap()..'"}'
http.post("http://192.168.2.38/DeviceScan.py", "Content-Type: text/json\r\n", msgBdy,
function(rspCode, payload)
tmr.start(2)
end)
end
--mainline start:
tmr.alarm(1, 3000, tmr.ALARM_SEMI, doCmdChk)
tmr.alarm(2, 5000, tmr.ALARM_SEMI, sendData)
我的应用程序不会像测试代码那样快速发出HTTP请求,但当应用程序运行几个小时后,最终会出现相同的结果(即其中一个计时器停止运行)。缩短HTTP请求之间的时间会使错误更快发生
有人遇到过这个问题吗?有人对如何解决这个问题有什么想法吗?(无法可靠地发送连续HTTP请求是此应用程序的一个障碍)。我对NodeMCU了解不多,但根据参考手册,在收到响应时会调用
HTTP.post
和HTTP.get
回调函数。因此,计时器只有在收到响应时才会重新启动。有没有可能会有延误或者你永远得不到回复
在第三方人员响应后重新启动计时器会增加可变延迟,因此不应非常精确。我不希望它像一些测试代码那样精确
对于调试,我建议您打印调用回调之间的实际延迟或post/get和响应之间的延迟。解决方案是设置标志,以便在任何给定时间只有一个http请求未完成。下面是前面的测试脚本,其中包括以下标志:
ctr1=0
ctr2=0
sendFlag=true
local function doCmdChk()
if sendFlag then
sendFlag=false
ctr1 = ctr1 + 1
http.get( "http://192.168.2.38/ICmd.py?i=" .. ctr1 , nil,
function(rspCode, payload)
sendFlag=true
tmr.start(1)
end)
else
tmr.alarm(3, 1000, tmr.ALARM_SINGLE, doCmdChk)
end
end
local function sendData()
if sendFlag then
sendFlag=false
ctr2 = ctr2 + 1
local msgBdy = '{"s":"' .. ctr2 .. '","i":"test23", "d":"heap='..node.heap()..'"}'
http.post("http://192.168.2.38/DeviceScan.py", "Content-Type: text/json\r\n", msgBdy,
function(rspCode, payload)
sendFlag=true
tmr.start(2)
end)
else
tmr.alarm(3, 1000, tmr.ALARM_SINGLE, sendData)
end
end
--mainline start:
tmr.alarm(1, 3000, tmr.ALARM_SEMI, doCmdChk)
tmr.alarm(2, 5000, tmr.ALARM_SEMI, sendData)
我运行了这个脚本几个小时,两个http发送函数都继续按预期工作
我尝试了node.task.post()选项,测试脚本如下:
ctr1=0
ctr2=0
local function doCmdChk()
ctr1 = ctr1 + 1
http.get( "http://192.168.2.38/ICmd.py?i=" .. ctr1 , nil,
function(rspCode, payload)
sendFlag=true
tmr.start(1)
end)
end
local function sendData()
ctr2 = ctr2 + 1
local msgBdy = '{"s":"' .. ctr2 .. '","i":"test23", "d":"heap='..node.heap()..'"}'
http.post("http://192.168.2.38/DeviceScan.py", "Content-Type: text/json\r\n", msgBdy,
function(rspCode, payload)
sendFlag=true
tmr.start(2)
end)
end
--mainline start:
tmr.alarm(1, 3000, tmr.ALARM_SEMI, function() node.task.post(node.task.MEDIUM_PRIORITY, doCmdChk) end)
tmr.alarm(2, 5000, tmr.ALARM_SEMI, function() node.task.post(node.task.HIGH_PRIORITY, sendData) end)
但是在运行了几个小时后,其中一个http回调没有被调用,因此一定发生了冲突。您对回调函数的评论很有趣。我在Nodemcu有一个案例,其中两个http请求一个接一个地发出,对第二个请求的响应从未调用回调函数。在http调用之间插入1秒延迟解决了此问题。我想知道这两个独立运行的计时器是否会造成类似的情况(两个http请求紧密地在一起)。我将做一些测试,看看是否会发生这样的碰撞。