2

我正在开发一个物联网项目,该项目使用 Electric Imp 和 PubNub 进行通信,使用 Parse 进行数据记录、云代码等。

出于某种原因,我在 IMP IDE 中的代码对 PubNub 频道进行了多次调用,而我只想将事件广播一次。

这是代码:

#require "PubNub.class.nut:1.1.0"
#require "Parse.class.nut:1.0.1"
// Log the URLs we need
server.log("");
server.log("------------------- RESTART CYCLE ------------------")
server.log("Agent Loaded. Agent URL: " + http.agenturl());

local impID = imp.configparams.deviceid;
local reqCount = 0;
local myResponse = [];


// Connect to PubNub
const publishKey = "#####################";
const subscribeKey = "#####################";
pubNub <- PubNub(publishKey, subscribeKey);


// Subscribe to PubNub Channel
pubNub.subscribe([impID, "iPlugComm"], function(err, result, timetoken) {
    if (err != null) {
        server.log(err);
        return;
    }
    parseComm(result,timetoken);
});

// Connect to Parse.com
const APP_ID = "#####################";
const REST_API_KEY = "#####################";
parse <- Parse(APP_ID, REST_API_KEY);

server.log("imp id = "+impID);
server.log("----------------------------------------------------")
server.log("");

// Process URI Requests
function requestHandler(request, response) {
  try {
    // check if the user myCommand led as a query parameter
    if ("myCommand" in request.query) {
        local myVar = request.query.myCommand;
        response.header("Access-Control-Allow-Origin", "*");
        myResponse.append(response);
        device.send("myCommand", myVar);
    }else{
        response.send(500, "Invalid Command Sent");
    }
  } 
  catch (ex) {
    response.send(500, "Invalid Command Sent: " + ex);
  }
}

// Parse Incoming PubNub Message
function parseComm(result, timetoken){
  local time = timetoken;
  local idx = 1;
  local deviceID,
        deviceName, 
        deviceMode, 
        deviceMessage, 
        deviceAction, 
        deviceChannel;
  foreach (channel, data in result) {
      // logstr += ("Channel: " + channel + ": " + data["deviceName"]);
      deviceID =  data["deviceID"];
      deviceName = data["deviceName"];
      deviceMode = data["deviceMode"];
      deviceMessage = data["deviceMessage"];
      deviceAction = data["deviceAction"];
      deviceChannel = channel;
      if (idx++ < result.len()) {
          logstr += ", ";
      }
  }
  server.log("COMM on channel '"+deviceChannel+"' from "+ deviceName +": "+deviceMessage+".");
}

// Log Device Connection to Parse.com
local logINIT = parse.createObject("EventLog", {
  "deviceID" : impID,
  "deviceType" : "Electric Imp",
  "deviceMode" : "Slave",
  "deviceState" : "Online",
  "deviceName": "Agent-"+impID,
  "deviceMessage": "Imp restarted.",
  "deviceURL": http.agenturl()
})
logINIT.save(function(err, data) {
  if (err != null) server.log ("Could not update object: " + err.error)
});

device.onconnect(function() {
  server.log("Device CONNECTED to agent.");
  // Publish Connection
  pubNub.publish("iPlugComm", { 
      deviceID = impID,
      deviceName = "Agent-"+impID,
      deviceMode = "Slave",
      deviceMessage = "Imp Agent Restarted",
      deviceAction = "null",
  });
});

device.ondisconnect(function() {
    server.log("Device DISCONNECTED from agent");
    server.log("Device CONNECTED to agent.");
    // Publish Connection
    pubNub.publish("iPlugComm", { 
        deviceID = impID,
        deviceName = "Agent-"+impID,
        deviceMode = "Slave",
        deviceMessage = "Imp Device Disconnected",
        deviceAction = "null",
    });
});

// register the HTTP handler
http.onrequest(requestHandler);

我想要的只是广播每个连接/事件一次....但是正如您从我的 server.log 中看到的那样,我似乎使用每个新的“构建和运行”命令进行了两次广播。

------------------- RESTART CYCLE ------------------
2015-10-29 10:31:21 UTC-3   [Agent] Agent Loaded. Agent URL: https://agent.electricimp.com/#####
2015-10-29 10:31:21 UTC-3   [Agent] imp id = #########
2015-10-29 10:31:21 UTC-3   [Agent] ----------------------------------------------------
2015-10-29 10:31:21 UTC-3   [Agent] 
2015-10-29 10:31:21 UTC-3   [Agent] Device CONNECTED to agent.
2015-10-29 10:31:21 UTC-3   [Agent] COMM on channel '(null : (nil))' from (null : (nil)): (null : (nil)).
2015-10-29 10:31:22 UTC-3   [Agent] Device CONNECTED to agent.
2015-10-29 10:31:22 UTC-3   [Agent] Published data at 14461254820532282
2015-10-29 10:31:22 UTC-3   [Agent] COMM on channel 'iPlugComm' from Agent-237f476938a609ee: Imp Agent Restarted.
2015-10-29 10:31:22 UTC-3   [Agent] Published data at 14461254821522215
2015-10-29 10:31:22 UTC-3   [Agent] COMM on channel 'iPlugComm' from Agent-237f476938a609ee: Imp Agent Restarted.
2015-10-29 10:31:22 UTC-3   [Status]    Device connected
2015-10-29 10:31:22 UTC-3   [Device]    IMP Device Started

有人看到我的错误在哪里吗?这可能是一个愚蠢的错误,因为我不熟悉 Squirrel。

4

1 回答 1

3

忽略第一条 COMM 消息(这很奇怪),问题似乎只是 device.onconnect 事件触发了两次。这是我们这边的一个已知问题(它只发生在构建和运行之后。)

解决此问题的一种方法可能是设置一个短的“去抖动”计时器:

local debounce = false;
device.onconnect(function() {
    if (debounce) return;
    // Do stuff
    debounce = true;
    imp.wakeup(1, function() {
        debounce = false;
    });
});
于 2015-11-03T08:09:27.480 回答