我需要一些强类型的全局变量。
正如这里提到的:在node.js中扩展TypeScript Global对象,为了向
global
变量添加字段,我需要添加一个.d.ts文件来扩展node.d中指定的Global
接口.ts。
此外,正如 Basarat 提到的:
您的文件需要清除任何根级别导入或导出。那 会将文件转换为模块并将其与全局断开连接 类型声明命名空间。
现在,我需要在
Global
接口上拥有字段,其类型是我创建的自定义接口:
declare namespace NodeJS{
interface Global {
foo: Foo
bar: Bar
}
}
我极不愿意使用
any
类型。
我可以将所有接口声明移动/复制到这个声明文件中,但这对我来说是一个糟糕的解决方案,因为 Foo 和 Bar 依次聚合了其他接口的许多字段,包括像 Moment 等第三方接口。
我需要解决这个悖论
这是一种方法。我不知道这是否是“正确”的做事方式,但它对我来说适用于 TypeScript 3.7.4。
src
中,请创建一个新文件夹 src/types
并在此文件夹中创建一个文件 global.d.ts
。import { Express } from 'express';
declare global {
namespace NodeJS {
interface Global {
__EXPRESS_APP__: Express;
}
}
}
declare namespace NodeJS {
interface Global {
__CONNECTION_COUNT__: number;
}
}
global.d.ts
文件中,确保 TypeScript 编译器拾取您的 src/types
文件(以及您可能添加到 tsconfig.json
的任何其他文件):{
"paths": {
"*": ["node_modules/*", "src/types/*"]
}
}
// Below, `app` will have the correct typings
const app = global.__EXPRESS_APP__;
我发现这个有效。
拥有一个文件,声明 NodeJS.Global 接口上具有 any 类型的属性。该文件必须不含导入或引用。
node.d.ts
declare namespace NodeJS{
interface Global {
foo: any
}
}
然后在第二个文件中声明一个具有正确类型的全局变量。
global.d.ts
import IFoo from '../foo'
declare global {
const foo:Ifoo
}
这对我有用(节点 v16.13.2)
types/global.d.ts
declare global {
var __root: string
}
export {}
注意
__root
使用 var
关键字声明。它也适用于 let
和 const
,但在这种情况下 __root
将具有 any
类型。我不知道为什么;)如果有人能解释这一点那就太好了。
tsconfig.json
{
"compilerOptions": {
"typeRoots": [
"types"
],
}
}
// app.ts (entry point)
import path from 'path'
global.__root = path.join(__dirname)
// anyFileInProject.ts
console.log(__root) // will display root directory
我找到了适用于nodejs v20.11.1、ts 5.4.5和vscode 1.88.1的工作解决方案
创建全局.d.ts:
type Logger = {
Info: (iMessage: string) => void
}
declare global {
var Foo: string;
var log: Logger;
}
export { };