Home > Software design >  Node setInterval to modify global variable and access it from other module
Node setInterval to modify global variable and access it from other module

Time:01-05

I need to check every 4 seconds if an ip is alive.

I'm using a global variable global.baseip (I know it's bad practice, I am only trying it out with setInterval)

global.baseip = "http://10.***.**.**:8048/TESTDEV02/ODataV4/Company('****')";

setInterval(function(){
  getip();
  console(baseip); //this gives the correct value
}, 4000); 
 var getip = function() {
  var hosts = [["10.***.**.**", 8048]];
  hosts.forEach(function (item) {
    var sock = new net.Socket();
    sock.setTimeout(2500);
    sock
      .on("connect", function () {
        baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
        sock.destroy();
      })
      .on("error", function (e) {
        baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
      })
      .connect(item[1], item[0]);
  })
}

Then, I use baseip in other modules/files but it's always undefined. Any help would be appreciated

CodePudding user response:

Don't use a global. Though you may get it to work as you have discovered it is not easy to get it to work and is easy to forget something that causes your code to not work. It is also messing with node's internals and is deliberately working against the way node.js was designed. Node.js was explicitly designed to prevent people from using global variables. Therefore if you want to use global variables you need to somehow work around those protections.

Instead a simpler and more stable way to do this is to use a module.

One thing people don't realise about Commonjs modules is that they are singletons. This is a consequence of the module caching behavior. What this means is that if you import a module into 10 different files then you are not creating ten different objects that represent your module but all 10 files share a single object (the definition of the Singleton design pattern). Note that this works not only in node.js but also other Commonjs based systems like Webpack, React.js (jsx) and Typescript.

The code is really simple. So simple in fact that it makes no sense to use this method because trying to circumvent the module system is far more complicated:

// shared.js

let shard_object = {
    baseip: "http://10.***.**.**:8048/TESTDEV02/ODataV4/Company('****')"
}

module.exports = shared_object;

Note: You can of course write the above much simpler or much more complicated. I wrote it the way I did for clarity

Then you can share the module above with your other modules:

// getip.js

const shared = require('./shared');

var getip = function() {
  var hosts = [["10.***.**.**", 8048]];
  hosts.forEach(function (item) {
    var sock = new net.Socket();
    sock.setTimeout(2500);
    sock
      .on("connect", function () {
        shared.baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
        sock.destroy();
      })
      .on("error", function (e) {
        shared.baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
      })
      .connect(item[1], item[0]);
  })
}

module.exports = getip;

and it works as expected:

// main.js

const getip = require('./getip');
const shared = require('./shared');

setInterval(function(){
  getip();
  console(shared.baseip); // this gives the correct value
}, 4000); 

CodePudding user response:

Because you define another variable with the same name inside the scope, you are in reality making changes to that variable. Just get rid of it, so you can work with the real baseip.

 var getip = function() {
  //var baseip; //This variable is overshadowing your global variable
  var hosts = [["10.***.**.**", 8048]];
  hosts.forEach(function (item) {
    var sock = new net.Socket();
    sock.setTimeout(2500);
    sock
      .on("connect", function () {
        baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
        sock.destroy();
      })
      .on("error", function (e) {
        baseip =
          "http://'10.***.**.**':8048/TESTDEV02/ODataV4/Company('****')";
      })
      .connect(item[1], item[0]);
  })
}

  •  Tags:  
  • Related