Node.js + TypeScript 写后端工具

2018-02-27 10:55:13来源:https://juejin.im/post/5a8fff275188257a5a4cc7d9作者:稀土掘金人点击

分享

现在 Node.js 的生态越来越成熟,有好多公司直接使用 Node 构建其后端应用,放在线上跑。TypeScript 是微软的编程语言,近年来受到的关注也是越来越多。


作为一个常年写后端接口的人,便想:能不能利用这两者,来给自己的工作流,带来一点不一样的感觉。(由于这不是写客户端 JS,所以我们并不需要 webpack 等工具 )


步骤
初始化项目

假设项目目录是 project 。


cd project
mkdir src && touch README.md
cd src
npm init
tsc --init
根据惯例,弄一个主入口 main (注:这里没有使用 index.js 这种设定 )
touch main.ts

初始化完成的项目是这样的:


project/
README.md
src/
package.json
tsconfig.json
main.ts
安装必备的包

目前暂时只想到了如下的这些包:


npm install --save lodash @types/lodash
npm install --save @types/node
npm install --save-dev typescript

之后项目变成这样子:


project/
README.md
src/
package.json
tsconfig.json
main.ts
node_modules/
配置 tsconfig.json

这一步最为重要。官网有一节专门讲这个:/2014th7cj/d/file/p/20180227/tsconfig-json.html 。要看懂还是需要花点时间的。


总而言之,需要告诉 tsc 如下几件事情:


项目的根目录在哪? (以 tsconfig.json 所在的目录为根目录,即项目根目录 )
输入在哪? (即:项目的哪些ts 文件是需要关心的,标准库/第三方库去哪里找)
输出在哪?(由于不是前端项目,所以我们只需要每一个 ts 输出对应的 js 文件即可)

这里是一个示例配置,有详细的注释说明,初始化 ts 项目时,可以直接拷贝之,以节约时间成本。


{
// tsconfig 所在的根目录, 则是一个project
"compilerOptions": {
"module": "commonjs", // 模块系统
"target": "es2015", // 生成目标, 一般选择ES6,因为不是客户端环境,没必要还编译成ES5
// 一组严苛的编译选项
"noImplicitAny": false,
"strictNullChecks": true,
"strict": true,
"alwaysStrict": true,
"sourceMap": false,
"noImplicitReturns": true,
"noImplicitThis": true,
"pretty": true,
"listFiles": true,// 包含了哪些库,这个必要的时候还是很有用的
"listEmittedFiles": true,
"lib": [// 要那些 lib,按需选择即可
"es2016"
],
// "noUnusedLocals": true,
// "noUnusedParameters": true,
// "noFallthroughCasesInSwitch": true,
// 指定库的搜索路径,这个比较有用,一般会指定 @types,还可以按需添加
"typeRoots": [
"./node_modules/@types"
]
// 库搜索路径下, 仅使用哪些库, 一般没啥用
// "types": [// ]
},
// file include会算出一个交集, 指明哪些是项目的 ts 文件
"include": [
"./**/*"
],
// 排除项目下面不符合要求的文件,这个按需设定即可,可以放心排除乱七八糟的文件
"exclude": [
"node_modules",
"**/*.spec.ts",
"*.js"
]
}


设计项目的目录结构为了模拟真实的场景,我们的 main.ts 有如下内容:


function main() {
}
main();

写一个 utils.ts,放入 src/core/utils.ts 中。


import * as path from 'path'; // 测试能否正常使用 Node 的内置模块
/**
* 一个正常的class
*
* 不得不说, TS 使用起来真是舒服,各种该有的东西都替你考虑到了
* 很舒心
*/
export class NodeModuleTester {
public static readonly STATIC_VAR = 'STATIC'; // 测试static变量
constructor(// 测试构造方法
private readonly f1: string,
private readonly f2: number) {
}
public static testPath() {// 测试静态方法
const curdir = './';
console.log(path.resolve(curdir));
}
}

由于需要使用对应的 class,所以 main.ts 内容变成了这样:


import {NodeModuleTester} from './core/utils';
/**
* main 入口
*
* 测试!
*/
function main() {
const tester = new NodeModuleTester("s1", 1);
console.log(NodeModuleTester.STATIC_VAR);
console.log(NodeModuleTester.testPath());
}
main();


运行由于 Node 是不认识 ts 的,我们的 ts 代码需要先转译成 js 代码。


不过别担心,我们使用的是微软的产品,一切都不是问题(意思就是:微软设计的东西,既有品味,又是异常简单好用,历来如此)。



我们只需要cd src/ && tsc && node main.js
即可,简直不要太简单。如果还嫌麻烦,我们可以写到 npm script 中去,如下:


{
"name": "src",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo /"Error: no test specified/" && exit 1",
"runmain": "./node_modules/.bin/tsc && node main.js" // 就是这个脚本!
},
"author": "",
"license": "ISC",
"devDependencies": {
"@types/node": "^9.4.6",
"typescript": "^2.7.2"
}
}


然后我们只需要cd src/ && npm run runmain
即可,更加地简单。


我的感悟

TypeScript 代码,既美观又优雅,加上微软强大的工程能力(造工具的能力),Node.js + TypeScript 几乎是一对完美的组合。



有人可能比较担忧有的库没有对应 d.ts 。其实这完全不用担心,常用的库要么自带 d.ts (侧面验证了 TS已经越来越被大家接受),要么社区已经有维护好的 d.ts (@types下面的库),实在没办法,自己写 d.ts 也不过是分分钟的事情,并没有什么难度。

最新文章

123

最新摄影

闪念基因

微信扫一扫

第七城市微信公众平台