Node.js 全局变量

发布于 2024-10-27 03:41:14 字数 351 浏览 5 评论 0原文

我在这里问: Node.js 需要继承吗?

我被告知我可以通过省略变量来将变量设置为全局范围。

这对我不起作用。

也就是说,以下内容不会使 _ 在所需文件上可用。

_ = require('underscore');

我可以使用 Express.js 的 app.set 进行设置,并在其他地方使用它。

这是应该如何运作的吗?

I asked here:
Does Node.js require inheritance?

And I was told that I can set variables to the global scope by leaving out the variable.

This does not work for me.

That is, the following does not make the _ available on required files.

_ = require('underscore');

I can set with Express.js's app.set and have it available elsewhere though.

Is that how this is supposed to work?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

蔚蓝源自深海 2024-11-03 03:41:14

您可以像这样使用 global

global._ = require('underscore')

You can use global like so:

global._ = require('underscore')
童话里做英雄 2024-11-03 03:41:14

在 Node.js 中,您可以通过“global”或“GLOBAL”对象设置全局变量:

GLOBAL._ = require('underscore'); // But you "shouldn't" do this! (see note below)

或者更有用...

GLOBAL.window = GLOBAL;  // Like in the browser

从 Node.js 源代码中,您可以看到这些变量彼此具有别名:

node-v0.6.6/src/node.js:
28:     global = this;
128:    global.GLOBAL = global;

在上面的代码中, “这个”是全球背景。通过 CommonJS 模块系统(Node.js 使用的),“this”对象内部模块(即“您的代码”)不是全局上下文。为了证明这一点,请参见下面我喷出“this”对象,然后喷出巨大的“GLOBAL”对象的地方。

console.log("\nTHIS:");
console.log(this);
console.log("\nGLOBAL:");
console.log(global);

/* Outputs ...

THIS:
{}

GLOBAL:
{ ArrayBuffer: [Function: ArrayBuffer],
  Int8Array: { [Function] BYTES_PER_ELEMENT: 1 },
  Uint8Array: { [Function] BYTES_PER_ELEMENT: 1 },
  Int16Array: { [Function] BYTES_PER_ELEMENT: 2 },
  Uint16Array: { [Function] BYTES_PER_ELEMENT: 2 },
  Int32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Uint32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Float32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Float64Array: { [Function] BYTES_PER_ELEMENT: 8 },
  DataView: [Function: DataView],
  global: [Circular],
  process:
   { EventEmitter: [Function: EventEmitter],
     title: 'node',
     assert: [Function],
     version: 'v0.6.5',
     _tickCallback: [Function],
     moduleLoadList:
      [ 'Binding evals',
        'Binding natives',
        'NativeModule events',
        'NativeModule buffer',
        'Binding buffer',
        'NativeModule assert',
        'NativeModule util',
        'NativeModule path',
        'NativeModule module',
        'NativeModule fs',
        'Binding fs',
        'Binding constants',
        'NativeModule stream',
        'NativeModule console',
        'Binding tty_wrap',
        'NativeModule tty',
        'NativeModule net',
        'NativeModule timers',
        'Binding timer_wrap',
        'NativeModule _linklist' ],
     versions:
      { node: '0.6.5',
        v8: '3.6.6.11',
        ares: '1.7.5-DEV',
        uv: '0.6',
        openssl: '0.9.8n' },
     nextTick: [Function],
     stdout: [Getter],
     arch: 'x64',
     stderr: [Getter],
     platform: 'darwin',
     argv: [ 'node', '/workspace/zd/zgap/darwin-js/index.js' ],
     stdin: [Getter],
     env:
      { TERM_PROGRAM: 'iTerm.app',
        'COM_GOOGLE_CHROME_FRAMEWORK_SERVICE_PROCESS/USERS/DDOPSON/LIBRARY/APPLICATION_SUPPORT/GOOGLE/CHROME_SOCKET': '/tmp/launch-nNl1vo/ServiceProcessSocket',
        TERM: 'xterm',
        SHELL: '/bin/bash',
        TMPDIR: '/var/folders/2h/2hQmtmXlFT4yVGtr5DBpdl9LAiQ/-Tmp-/',
        Apple_PubSub_Socket_Render: '/tmp/launch-9Ga0PT/Render',
        USER: 'ddopson',
        COMMAND_MODE: 'unix2003',
        SSH_AUTH_SOCK: '/tmp/launch-sD905b/Listeners',
        __CF_USER_TEXT_ENCODING: '0x12D732E7:0:0',
        PATH: '/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:~/bin:/usr/X11/bin',
        PWD: '/workspace/zd/zgap/darwin-js',
        LANG: 'en_US.UTF-8',
        ITERM_PROFILE: 'Default',
        SHLVL: '1',
        COLORFGBG: '7;0',
        HOME: '/Users/ddopson',
        ITERM_SESSION_ID: 'w0t0p0',
        LOGNAME: 'ddopson',
        DISPLAY: '/tmp/launch-l9RQXI/org.x:0',
        OLDPWD: '/workspace/zd/zgap/darwin-js/external',
        _: './index.js' },
     openStdin: [Function],
     exit: [Function],
     pid: 10321,
     features:
      { debug: false,
        uv: true,
        ipv6: true,
        tls_npn: false,
        tls_sni: true,
        tls: true },
     kill: [Function],
     execPath: '/usr/local/bin/node',
     addListener: [Function],
     _needTickCallback: [Function],
     on: [Function],
     removeListener: [Function],
     reallyExit: [Function],
     chdir: [Function],
     debug: [Function],
     error: [Function],
     cwd: [Function],
     watchFile: [Function],
     umask: [Function],
     getuid: [Function],
     unwatchFile: [Function],
     mixin: [Function],
     setuid: [Function],
     setgid: [Function],
     createChildProcess: [Function],
     getgid: [Function],
     inherits: [Function],
     _kill: [Function],
     _byteLength: [Function],
     mainModule:
      { id: '.',
        exports: {},
        parent: null,
        filename: '/workspace/zd/zgap/darwin-js/index.js',
        loaded: false,
        exited: false,
        children: [],
        paths: [Object] },
     _debugProcess: [Function],
     dlopen: [Function],
     uptime: [Function],
     memoryUsage: [Function],
     uvCounters: [Function],
     binding: [Function] },
  GLOBAL: [Circular],
  root: [Circular],
  Buffer:
   { [Function: Buffer]
     poolSize: 8192,
     isBuffer: [Function: isBuffer],
     byteLength: [Function],
     _charsWritten: 8 },
  setTimeout: [Function],
  setInterval: [Function],
  clearTimeout: [Function],
  clearInterval: [Function],
  console: [Getter],
  window: [Circular],
  navigator: {} }
*/

** 注意:关于设置“GLOBAL._”,一般来说你应该这样做 var _ = require('underscore');。是的,您可以在每个使用 Underscore.js 的文件中执行此操作,就像在 Java 中 import com.foo.bar; 一样。这使得更容易弄清楚您的代码在做什么,因为文件之间的链接是“显式的”。这有点烦人,但却是一件好事。 ……这就是讲道。

每条规则都有一个例外。我恰好有一个实例需要设置“GLOBAL._”。我正在创建一个用于定义“配置”文件的系统,这些文件基本上是 JSON,但“用 JavaScript 编写”以提供更多的灵活性。此类配置文件没有“require”语句,但我希望它们能够访问 Underscore.js(整个系统基于 Underscore.js 和 Underscore.js 模板),因此在评估“配置”,我会设置“GLOBAL._”。所以,是的,对于每条规则,都有一个例外。但你最好有一个非常好的理由,而不仅仅是“我厌倦了输入‘require’,所以我想打破惯例”。

In Node.js, you can set global variables via the "global" or "GLOBAL" object:

GLOBAL._ = require('underscore'); // But you "shouldn't" do this! (see note below)

or more usefully...

GLOBAL.window = GLOBAL;  // Like in the browser

From the Node.js source, you can see that these are aliased to each other:

node-v0.6.6/src/node.js:
28:     global = this;
128:    global.GLOBAL = global;

In the code above, "this" is the global context. With the CommonJS module system (which Node.js uses), the "this" object inside of a module (i.e., "your code") is not the global context. For proof of this, see below where I spew the "this" object and then the giant "GLOBAL" object.

console.log("\nTHIS:");
console.log(this);
console.log("\nGLOBAL:");
console.log(global);

/* Outputs ...

THIS:
{}

GLOBAL:
{ ArrayBuffer: [Function: ArrayBuffer],
  Int8Array: { [Function] BYTES_PER_ELEMENT: 1 },
  Uint8Array: { [Function] BYTES_PER_ELEMENT: 1 },
  Int16Array: { [Function] BYTES_PER_ELEMENT: 2 },
  Uint16Array: { [Function] BYTES_PER_ELEMENT: 2 },
  Int32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Uint32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Float32Array: { [Function] BYTES_PER_ELEMENT: 4 },
  Float64Array: { [Function] BYTES_PER_ELEMENT: 8 },
  DataView: [Function: DataView],
  global: [Circular],
  process:
   { EventEmitter: [Function: EventEmitter],
     title: 'node',
     assert: [Function],
     version: 'v0.6.5',
     _tickCallback: [Function],
     moduleLoadList:
      [ 'Binding evals',
        'Binding natives',
        'NativeModule events',
        'NativeModule buffer',
        'Binding buffer',
        'NativeModule assert',
        'NativeModule util',
        'NativeModule path',
        'NativeModule module',
        'NativeModule fs',
        'Binding fs',
        'Binding constants',
        'NativeModule stream',
        'NativeModule console',
        'Binding tty_wrap',
        'NativeModule tty',
        'NativeModule net',
        'NativeModule timers',
        'Binding timer_wrap',
        'NativeModule _linklist' ],
     versions:
      { node: '0.6.5',
        v8: '3.6.6.11',
        ares: '1.7.5-DEV',
        uv: '0.6',
        openssl: '0.9.8n' },
     nextTick: [Function],
     stdout: [Getter],
     arch: 'x64',
     stderr: [Getter],
     platform: 'darwin',
     argv: [ 'node', '/workspace/zd/zgap/darwin-js/index.js' ],
     stdin: [Getter],
     env:
      { TERM_PROGRAM: 'iTerm.app',
        'COM_GOOGLE_CHROME_FRAMEWORK_SERVICE_PROCESS/USERS/DDOPSON/LIBRARY/APPLICATION_SUPPORT/GOOGLE/CHROME_SOCKET': '/tmp/launch-nNl1vo/ServiceProcessSocket',
        TERM: 'xterm',
        SHELL: '/bin/bash',
        TMPDIR: '/var/folders/2h/2hQmtmXlFT4yVGtr5DBpdl9LAiQ/-Tmp-/',
        Apple_PubSub_Socket_Render: '/tmp/launch-9Ga0PT/Render',
        USER: 'ddopson',
        COMMAND_MODE: 'unix2003',
        SSH_AUTH_SOCK: '/tmp/launch-sD905b/Listeners',
        __CF_USER_TEXT_ENCODING: '0x12D732E7:0:0',
        PATH: '/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:~/bin:/usr/X11/bin',
        PWD: '/workspace/zd/zgap/darwin-js',
        LANG: 'en_US.UTF-8',
        ITERM_PROFILE: 'Default',
        SHLVL: '1',
        COLORFGBG: '7;0',
        HOME: '/Users/ddopson',
        ITERM_SESSION_ID: 'w0t0p0',
        LOGNAME: 'ddopson',
        DISPLAY: '/tmp/launch-l9RQXI/org.x:0',
        OLDPWD: '/workspace/zd/zgap/darwin-js/external',
        _: './index.js' },
     openStdin: [Function],
     exit: [Function],
     pid: 10321,
     features:
      { debug: false,
        uv: true,
        ipv6: true,
        tls_npn: false,
        tls_sni: true,
        tls: true },
     kill: [Function],
     execPath: '/usr/local/bin/node',
     addListener: [Function],
     _needTickCallback: [Function],
     on: [Function],
     removeListener: [Function],
     reallyExit: [Function],
     chdir: [Function],
     debug: [Function],
     error: [Function],
     cwd: [Function],
     watchFile: [Function],
     umask: [Function],
     getuid: [Function],
     unwatchFile: [Function],
     mixin: [Function],
     setuid: [Function],
     setgid: [Function],
     createChildProcess: [Function],
     getgid: [Function],
     inherits: [Function],
     _kill: [Function],
     _byteLength: [Function],
     mainModule:
      { id: '.',
        exports: {},
        parent: null,
        filename: '/workspace/zd/zgap/darwin-js/index.js',
        loaded: false,
        exited: false,
        children: [],
        paths: [Object] },
     _debugProcess: [Function],
     dlopen: [Function],
     uptime: [Function],
     memoryUsage: [Function],
     uvCounters: [Function],
     binding: [Function] },
  GLOBAL: [Circular],
  root: [Circular],
  Buffer:
   { [Function: Buffer]
     poolSize: 8192,
     isBuffer: [Function: isBuffer],
     byteLength: [Function],
     _charsWritten: 8 },
  setTimeout: [Function],
  setInterval: [Function],
  clearTimeout: [Function],
  clearInterval: [Function],
  console: [Getter],
  window: [Circular],
  navigator: {} }
*/

** Note: regarding setting "GLOBAL._", in general you should just do var _ = require('underscore');. Yes, you do that in every single file that uses Underscore.js, just like how in Java you do import com.foo.bar;. This makes it easier to figure out what your code is doing because the linkages between files are 'explicit'. It is mildly annoying, but a good thing. .... That's the preaching.

There is an exception to every rule. I have had precisely exactly one instance where I needed to set "GLOBAL._". I was creating a system for defining "configuration" files which were basically JSON, but were "written in JavaScript" to allow a bit more flexibility. Such configuration files had no 'require' statements, but I wanted them to have access to Underscore.js (the entire system was predicated on Underscore.js and Underscore.js templates), so before evaluating the "configuration", I would set "GLOBAL._". So yeah, for every rule, there's an exception somewhere. But you had better have a darn good reason and not just "I get tired of typing 'require', so I want to break with the convention".

不必你懂 2024-11-03 03:41:14

当项目变大时,使用 GLOBAL 关键字的其他解决方案对于维护/可读性(+命名空间污染和错误)来说是一场噩梦。我已经多次看到这个错误并且修复它很麻烦。

使用 JavaScript 文件,然后使用模块导出。

示例:

文件 globals.js

var Globals = {
    'domain':'www.MrGlobal.com';
}

module.exports = Globals;

然后,如果您想使用这些,请使用 require

var globals = require('globals'); // << globals.js path
globals.domain // << Domain.

The other solutions that use the GLOBAL keyword are a nightmare to maintain/readability (+namespace pollution and bugs) when the project gets bigger. I've seen this mistake many times and had the hassle of fixing it.

Use a JavaScript file and then use module exports.

Example:

File globals.js

var Globals = {
    'domain':'www.MrGlobal.com';
}

module.exports = Globals;

Then if you want to use these, use require.

var globals = require('globals'); // << globals.js path
globals.domain // << Domain.
一个人的夜不怕黑 2024-11-03 03:41:14

使用全局命名空间,如 global.MYAPI = {}

global.MYAPI._ = require('underscore')

所有其他发帖者都讨论了所涉及的不良模式。因此,抛开讨论不谈,全局定义变量(OP 的问题)的最佳方法是通过名称空间。

提示:使用命名空间进行开发

Use a global namespace like global.MYAPI = {}:

global.MYAPI._ = require('underscore')

All other posters talk about the bad pattern involved. So leaving that discussion aside, the best way to have a variable defined globally (OP's question) is through namespaces.

Tip: Development Using Namespaces

独守阴晴ぅ圆缺 2024-11-03 03:41:14

您可以只使用全局对象。

var X = ['a', 'b', 'c'];
global.x = X;

console.log(x);
//['a', 'b', 'c']

You can just use the global object.

var X = ['a', 'b', 'c'];
global.x = X;

console.log(x);
//['a', 'b', 'c']
李不 2024-11-03 03:41:14

我同意使用 global/GLOBAL 命名空间来设置全局的任何内容都是不好的做法,并且理论上根本不使用它(理论上是操作词)。但是(是的,操作员)我确实使用它来设置自定义错误类:

// Some global/configuration file that gets called in initialisation

global.MyError = [Function of MyError];

是的,这是禁忌,但是如果您的站点/项目在整个地方使用自定义错误,您基本上需要在任何地方定义它,或者至少在某个地方定义它 抛出

  1. 首先定义 Error 类 在
  2. 错误的脚本中
  3. 在捕获错误的脚本中

在全局命名空间中定义自定义错误可以帮我省去 require' 的麻烦荷兰国际集团我的客户错误库。成像抛出自定义错误,其中自定义错误未定义。

I agree that using the global/GLOBAL namespace for setting anything global is bad practice and don't use it at all in theory (in theory being the operative word). However (yes, the operative) I do use it for setting custom Error classes:

// Some global/configuration file that gets called in initialisation

global.MyError = [Function of MyError];

Yes, it is taboo here, but if your site/project uses custom errors throughout the place, you would basically need to define it everywhere, or at least somewhere to:

  1. Define the Error class in the first place
  2. In the script where you're throwing it
  3. In the script where you're catching it

Defining my custom errors in the global namespace saves me the hassle of require'ing my customer error library. Imaging throwing a custom error where that custom error is undefined.

遇到 2024-11-03 03:41:14

如果您尝试全局访问字符串,我建议使用dotenv

安装方式:

npm i dotenv

然后在项目的根目录中创建文件.env并设置所有您想要全局的变量,例如:

DB_HOST='localhost'
DB_DATABASE='my_database'
DB_USER='my_user'
DB_PASSWORD='my_password'

ADMIN_EMAIL='[email protected]'
CITY='Some city'
# ... etc

您甚至可以在启动服务器时通过命令行设置这些变量,如下所示:

NODE_ENV=dev PORT=5000 npm run start-dev

另外,如果您使用 git,您可能需要添加 .env< /code> 到您的 .gitignore 以确保您不会意外提交敏感信息。

然后只需在 server.js 文件(或要执行的第一个文件)的开头包含以下内容即可。

require('dotenv').config()

要在代码中的任何位置使用这些变量,只需使用 process.env。 VARIABLE_NAME

例如:

app.listen(process.env.PORT, () => {
    console.log(`Server is running on port ${process.env.PORT}.`)
})

注意:我知道这并不能直接回答问题,因为它是关于全局存储字符串而不是 Underscore.js,但我认为为了完整性我会包含它。

In case you are trying to access strings globally, I recommend using dotenv:

Install with:

npm i dotenv

Then create the file .env in the project's root directory and set all of the variables you want to be global, for example:

DB_HOST='localhost'
DB_DATABASE='my_database'
DB_USER='my_user'
DB_PASSWORD='my_password'

ADMIN_EMAIL='[email protected]'
CITY='Some city'
# ... etc

You can even set these variables by the command line when starting the server like this:

NODE_ENV=dev PORT=5000 npm run start-dev

Also, if you use git, you likely want to add .env to your .gitignore to make sure you don't accidentally commit sensitive information.

Then just include the following at the beginning of your server.js file (or whatever the first file to be executed is)

require('dotenv').config()

To use these variables anywhere in your code, just use process.env.VARIABLE_NAME.

For example:

app.listen(process.env.PORT, () => {
    console.log(`Server is running on port ${process.env.PORT}.`)
})

Note: I understand this doesn't directly answer the question since it is about storing strings globally instead of Underscore.js, but I thought I would include it for completeness.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文