如何在 Electron 上使用带有 TypeScript 类型支持的 require 内部函数或条件?

Posted

技术标签:

【中文标题】如何在 Electron 上使用带有 TypeScript 类型支持的 require 内部函数或条件?【英文标题】:How can I use require inside functions or conditions with TypeScript type support on Electron? 【发布时间】:2021-04-13 12:12:38 【问题描述】:

在Electron Performance docs中是这样说的:

在传统的 Node.js 开发中,我们习惯于将所有 require() 语句放在顶部。如果您当前正在使用相同的策略编写您的 Electron 应用程序并且正在使用您并不立即需要的相当大的模块,请应用相同的策略并将加载推迟到更合适的时间。

因此,它建议在需要时“及时”调用require() 分配资源。问题是我正在尝试使用 electron-react-boilerplate 而 TypeScript 似乎不能很好地支持这种代码。这是一个例子:

src/main.dev.ts:

if (
  process.env.NODE_ENV === 'development' ||
  process.env.DEBUG_PROD === 'true'
) 
  require('electron-debug')( showDevTools: false );

它在require('electron-debug') 中有一个 ESLint 错误“Unsafe call of an any typed value.eslint(@typescript-eslint/no-unsafe-call)”,即使this library has types defined。

但如果将其替换为import,则不会出现该错误:

import electronDebug from 'electron-debug'; // at the top of the file

if (
  process.env.NODE_ENV === 'development' ||
  process.env.DEBUG_PROD === 'true'
) 
  electronDebug( showDevTools: false );

那么在这种情况下,我该如何使用 require 并支持类型?

我读到this answer 说要使用import module = require('module'),但是如果我使用它,就会出现错误说“导入声明只能在命名空间或模块中使用。ts(1232)”在 if 或函数中。

【问题讨论】:

【参考方案1】:

我们可以使用异步import() 来解决这个问题:

if (
  process.env.NODE_ENV === 'development' ||
  process.env.DEBUG_PROD === 'true'
) 
  import('electron-debug').then(electronDebug =>
    electronDebug.default( showDevTools: false ),
  );

请注意,对于 CommonJS,它将被转译为 require(阅读有关它的更多信息 here),因此我们可以假设它仍然使用 Electron 文档中提到的 require cache。


electron-react-boilerplate 上使用这种方法可能会在yarn package 上创建额外的文件,例如252.main.prod.js,这将导致尝试执行程序时出错(错误:找不到模块'../ ../src/252.main.prod.js')。为了避免它,你需要告诉 Webpack 忽略它,如下例所示:

之前:

const sourceMapSupport = require('source-map-support');
sourceMapSupport.install();

之后:

import(/* webpackIgnore: true */ 'source-map-support')
  .then((sourceMapSupport) => sourceMapSupport.install())
  .catch(console.error);

【讨论】:

以上是关于如何在 Electron 上使用带有 TypeScript 类型支持的 require 内部函数或条件?的主要内容,如果未能解决你的问题,请参考以下文章

如何在带有 npm 的 PowerShell 中使用“@”

Angular / Electron 使用带有角度组件的 renderer.js

如何将 Prisma 与 Electron 一起使用

如何在 Electron-Angular 项目中使用永远的监视器?

如何在 Electron 上请求 MIDI 设备权限?

在 Electron 中打开带有扩展名的文件