如何在node.js中使用全局变量?


78

例如,我想使用自定义记录器:

logger = require('basic-logger'),
logger.setLevel('info')

var customConfig = {
showMillis: true,
showTimestamp: true
}

var log = new logger(customConfig)

如何在其他模块而不是console.log中使用此记录器?



1
这回答了你的问题了吗?node.js标准模块的全局变量?
KyleMit

1
仅供参考globalGLOBAL每个节点的弃用警告
KyleMit

Answers:


115

大多数人建议不要使用全局变量。如果要在不同模块中使用相同的记录器类,则可以执行此操作

logger.js

  module.exports = new logger(customConfig);

foob​​ar.js

  var logger = require('./logger');
  logger('barfoo');

如果确实需要全局变量,则可以执行以下操作:

global.logger = new logger(customConfig);

28
不要使用全局变量!如果您开始使用多个进程运行应用程序,那么您将被搞砸。
TheHippo 2012年

30
在某些情况下,即使有多个过程,Hippo全局变量也可以。例如,如果多个进程拥有自己的logger对象实例,则logger不会有任何问题。
2013年

140
我无聊看到有关“不使用全局变量”的评论。在某些情况下,全局变量是唯一的工作方式。我通常使用它来存储常量值,例如“ global.email ='contact@domain.com'”,并在整个项目中使用它。如果明天我想在整个项目中进行更改,则只需要在app.js中进行更改(在这种情况下为Node示例)。除了使用global之外,我不知道在Node中执行此操作的另一种方法。因此,请不要明确地说“不要使用全局变量”,而要说“明智地使用全局变量”。

36
@Eagle我真的不明白为什么您不能导入定义电子邮件变量的配置文件。
Pickels

28
可以,但是我的抱怨不是关于是否可以使用配置文件,而是关于是否可以以安全的方式使用全局变量。我可以。

49
global.myNumber; //Delclaration of the global variable - undefined
global.myNumber = 5; //Global variable initialized to value 5. 
var myNumberSquared = global.myNumber * global.myNumber; //Using the global variable. 

在全局变量方面,Node.js与客户端JavaScript不同。仅仅因为在Node.js脚本的顶部使用了单词var,并不意味着该变量将可被所需的所有对象(例如“ basic-logger”)访问。

要使某些内容具有全局性,只需在变量名称前加上“ global”一词和一个点。因此,如果我希望company_id是全局的,则将其称为global.company_id。但是要小心,global.company_id和company_id是同一件事,因此请勿将全局变量命名为与任何其他脚本中的任何其他变量相同的事物-将在您的服务器或同一代码内任何其他位置运行的任何其他脚本。


1
这是不同的,因为在构建时每个文件/模块都隐式包装在IIFE中,因此var实际上是IIFE本地的。
superluminary

28

您可以使用global或GLOBAL来定义它,nodejs支持两者。

例如

global.underscore = require("underscore");

要么

GLOBAL.underscore = require("underscore");

22

我建议每次使用全局检查时,是否已经通过简单检查定义了变量

if (!global.logger){
  global.logger = require('my_logger');
}

我发现它有更好的表现


@ wiktus239这是一项检查,因为它不需要再次加载模块-因此性能更好。
suprxd

1
答案很好,if可以使用它来不必要地重新定义全局,但我想指出的是,require加载不会超过一次。它将所有内容加载一次并缓存结果。因此,if不需要避免模块解析和加载,但是避免反复从缓存中重新分配值很有用。
rsp

6

明智地使用全局变量可以在Node中使用

在节点中声明全局变量:

a = 10;
GLOBAL.a = 10;
global.a = 10;

以上所有命令使用不同的语法执行相同的操作。

在不打算更改全局变量时使用它们

这是使用全局变量时可能发生的事的示例:

// app.js
a = 10; // no var or let or const means global

// users.js
app.get("/users", (req, res, next) => {
   res.send(a); // 10;
});

// permissions.js
app.get("/permissions", (req, res, next) => {
   a = 11; // notice that there is no previous declaration of a in the permissions.js, means we looking for the global instance of a.
   res.send(a); // 11;
});

解释:

运行用户首先进行路由,并获得10;

然后运行权限路由并接收11;

然后,再次运行用户路由,并收到11条而不是10条;

全局变量可以被超越!

现在考虑将express和assignin res对象用作全局对象。您最终会收到异步错误,损坏并关闭服务器。

什么时候使用全局变量?

正如我所说的-当var不会被更改时。无论如何,建议您使用process.env配置文件中的对象。



3

如果您的应用是用TypeScript编写的,请尝试

(global as any).logger = // ...

要么

Object.assign(global, { logger: // ... })

但是,我只会在React Native__DEV__处于测试环境中时才这样做。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.