在Namespaced Typescript项目中使用NPM模块



我有一个项目(现有项目),它的前端是用名称空间的typescript编写的。我无法从名称空间方法重写所有typescript文件以导出/导入es6语法。

但是,下面的代码运行良好。如果我添加我的新ts模块或react组件,只要我将其封装在命名空间中,并通过Class调用它,或者如果它在其他命名空间中,则使用命名空间前缀调用它,这是没有问题的。

问题是我不能将外部模块与import语句一起使用。我如何使用。。?由于import语句引发错误。

更具体地说,对于下面的代码,我想使用react redux,

当我检查node_moduels文件夹时,我看到了引用React namesapce的@types文件夹我假设由于tsconfig 中的这一行

"typeRoots": [
"./node_modules/@types/"
]

但当我安装npm install --save @types/react-redux时,它还在节点模块的@types文件夹下创建了带有index.ts的react redux文件夹。但它没有Namespace导出行React类型文件有如下内容。

export as namespace React;
declare namespace React {
....
}

最终。。我该如何使用第三方节点moudles,尤其是在这个项目中使用react redux。或者任何简单节点模块,并在任何ts文件中访问它;react bootstrap";以下是包装在namesapse中的react组件的简单ts文件,该文件运行良好(导入staement除外)

import { createStore } from 'redux'; //if i add this line this is throwing error.
namespace Profile.Sample {
import { createStore } from 'redux'; //this too throwing error, without these lines my code is working fine.
export class Profiles extends React.Component<any> {
constructor(props) {
super(props);           
this.state = { brand: "Ford" };
}     
render(): React.ReactNode {
return (
<sect
<div className="container-fluid">
<div className="row">
<div className="col-lg-12">
<div className="main-title">
<h2>Profiles</h2>
<p>Lorem ipsum dolor sit amet, consectetur adi</p>
</div>
</div>
</div>

</div>
</section>
);
}
}
}

下面是我的tsconfig

{
"compileOnSave": true,
"compilerOptions": {
"preserveConstEnums": true,
"experimentalDecorators": true,
"declaration": true,
"emitBOM": true,
"jsx": "react",
"noEmitHelpers": true,
"inlineSourceMap": true,
"inlineSources": true,
"outFile": "wwwroot/Scripts/site/Profiles.js",
"skipLibCheck": true,
"skipDefaultLibCheck": true,
"target": "es5",
"typeRoots": [
"./node_modules/@types/"
]
}
}

我知道命名空间不是未来推荐的方法。。但这是一个现有的项目,无法将所有文件从命名空间重写为导入/导出语句。

好的,让我们一步一步地让它运行:

  1. 虽然您没有明确声明,但我认为您收到了错误消息Cannot compile modules using option 'outFile' unless the '--module' flag is 'amd' or 'system'.。选项outFile生成一个包含所有代码的主文件。由于您在tsconfig.json中使用"target": "es5",因此module的默认值为commonjscommonjs是node.js广泛使用的模块语法(var x = require('x')/exports.x = x),该语法不支持将代码合并到一个文件中,因此被禁止。但是你想在浏览器中使用你的代码,所以commonjs无论如何都不受支持。所以首先要做的是

    "module": "AMD"插入到tsconfig.json文件中

    AMD是一种可在浏览器中使用的模块语法。您还可以使用"UMD",它只是一个扩展,因此该模块支持AMDcommonjs模块。

  2. 为了避免以后进行更多配置,您还应该使用

    tsconfig.json文件中将"outFile": "wwwroot/Scripts/site/Profiles.js"更改为"outDir": "wwwroot/Scripts/site"

  3. module设置为AMD会将moduleResolution的默认值从node更改为classic,但这并不好,因为import {createStore} from 'redux'将失败,并显示错误消息Cannot find module 'redux'. Did you mean to set the 'moduleResolution' option to 'node', or to add aliases to the 'paths' option?。因此

    "moduleResolution": "node"包含到tsconfig.json文件中

  4. 在代码中,您定义了一个扩展另一个基类的类。如果您转换此继承,则需要一个特殊的函数__extends。在当前设置中,此函数不是由typescript生成的,并且您会得到错误Uncaught ReferenceError: __extends is not defined。因此

    删除"noEmitHelpers": true

  5. 现在,您的所有文件都可以传输到AMD模块。但是要使用这些模块,您需要一个模块加载器。最流行的是require.js。要使用它,

    在HTML文件中插入<script data-main="setup" src="https://cdnjs.cloudflare.com/ajax/libs/require.js/2.3.6/require.min.js" integrity="sha512-c3Nl8+7g4LMSTdrm621y7kf9v3SDPnhxLNhcjFJbKECVnmZHTdo+IRO05sNLTH/D3vA6u1X32ehoLC7WFVdheg==" crossorigin="anonymous"></script>

    您也可以下载并自己提供。data-main="setup"表示在加载require.js之后,执行脚本setup.js。此脚本将在下一步中创建。

  6. require.js需要一些配置才能找到所有模块。所以

    创建wwwrootScriptssitesetup.js:

    requirejs.config({
    appDir: ".",
    paths: { 
    'react': ['./node_modules/react/umd/react.production.min.js', 'https://unpkg.com/react@16/umd/react.production.min'],
    'react-dom': ['./node_modules/react-dom/umd/react-dom.production.min.js', 'https://unpkg.com/react-dom@16/umd/react-dom.production.min'],
    'redux': ['./node_modules/redux/dist/redux.min.js', 'https://cdnjs.cloudflare.com/ajax/libs/redux/4.0.5/redux.min'],
    },
    });
    requirejs(['entryPoint'], function() {
    console.log("Entry point 'index' has been loaded!");
    return {};
    });
    

    在第一部分中,配置了require.js。特别是,定义了外部模块(通过npm安装的模块)的位置。这里,reactreact-domredux的位置被设置为node_modules文件夹中的位置,其中来自内容交付网络(CDN)的外部文件作为备份。您也可以删除其中一个位置。它们是从左到右请求的,如果一个请求失败,则继续前进。如果您使用node_modules文件夹中的位置,您也必须从Web服务器提供这些位置!

    在第二部分中,执行模块entryPoint。这是你的应用程序的入口点。将名称更改为您想要作为入口点的任何名称。如果要将文件someOtherFile.js中定义的模块作为入口点,请编写requirejs(['someOtherFile'], ...

  7. 要传输所有文件,请运行

    tsc --project tsconfig.json

  8. 提供目录wwwroot/Scripts/site中的所有文件,包括您的HTML文件。出于测试目的,您可以使用

    npx serve

您可以在此处看到稍微修改过的代码:https://codesandbox.io/s/elated-fermat-ie2ms?file=/src/index.tsx.

相关内容

  • 没有找到相关文章

最新更新