Deno 入门教程 / 第 16 章:npm 兼容性
第 16 章:npm 兼容性
16.1 Deno 2.0 的 npm 兼容性
Deno 2.0 实现了对 npm 生态系统的高度兼容,可以无缝使用绝大多数 npm 包。
npm: 协议
// 直接使用 npm 包
import express from "npm:express@4.18";
import lodash from "npm:lodash-es@4.17";
import chalk from "npm:chalk@5";
// 使用子路径
import { map } from "npm:lodash-es@4.17/map";
package.json 支持
// package.json
{
"name": "my-deno-app",
"version": "1.0.0",
"dependencies": {
"express": "^4.18",
"lodash-es": "^4.17"
},
"devDependencies": {
"@types/express": "^4.17"
}
}
Deno 会自动读取 package.json 并解析依赖。
node_modules 目录
# 使用 npm 安装(如果需要 node_modules)
deno install
# 不创建 node_modules(推荐方式)
# 直接使用 npm: 协议导入
16.2 Node.js API 兼容
Deno 2.0 提供了对 Node.js 核心 API 的广泛兼容:
兼容的 Node.js 模块
| 模块 | 支持状态 | 说明 |
|---|---|---|
node:fs | ✅ 完整 | 文件系统操作 |
node:fs/promises | ✅ 完整 | 异步文件操作 |
node:path | ✅ 完整 | 路径处理 |
node:http | ✅ 完整 | HTTP 模块 |
node:https | ✅ 完整 | HTTPS 模块 |
node:crypto | ✅ 完整 | 加密模块 |
node:os | ✅ 完整 | 操作系统信息 |
node:url | ✅ 完整 | URL 处理 |
node:stream | ✅ 完整 | 流操作 |
node:events | ✅ 完整 | 事件系统 |
node:child_process | ✅ 完整 | 子进程 |
node:worker_threads | ✅ 完整 | Worker 线程 |
node:buffer | ✅ 完整 | Buffer 操作 |
node:dns | ✅ 完整 | DNS 查询 |
node:net | ✅ 完整 | TCP 网络 |
node:tls | ✅ 完整 | TLS 加密 |
node:zlib | ✅ 完整 | 压缩解压 |
使用 Node.js API
// 使用 node:fs
import fs from "node:fs";
import fsPromises from "node:fs/promises";
// 同步读取
const content = fs.readFileSync("./file.txt", "utf-8");
// 异步读取
const data = await fsPromises.readFile("./file.txt", "utf-8");
// 使用 node:path
import path from "node:path";
console.log(path.join("/home", "user", "file.txt"));
console.log(path.extname("file.txt"));
// 使用 node:os
import os from "node:os";
console.log("CPU 核心数:", os.cpus().length);
console.log("总内存:", os.totalmem());
console.log("可用内存:", os.freemem());
// 使用 node:crypto
import crypto from "node:crypto";
const hash = crypto.createHash("sha256").update("hello").digest("hex");
console.log(hash);
16.3 从 Node.js 迁移
迁移策略
| 策略 | 说明 | 适用场景 |
|---|---|---|
| 全新项目 | 从零开始用 Deno | 新项目 |
| 渐进迁移 | 逐步替换模块 | 中型项目 |
| 混合运行 | Deno + Node.js 共存 | 大型项目 |
| 编译迁移 | 一次性转换 | 小型项目 |
迁移清单
1. [ ] 检查依赖兼容性(npm 包在 Deno 中是否工作)
2. [ ] 替换 require() 为 import
3. [ ] 替换 __dirname 和 __filename
4. [ ] 替换 node: 开头的模块导入
5. [ ] 更新 package.json 或创建 deno.json
6. [ ] 运行 deno check 检查类型
7. [ ] 运行 deno test 确保测试通过
8. [ ] 更新构建和部署脚本
替换 __dirname
// Node.js 方式
const __dirname = path.dirname(new URL(import.meta.url).pathname);
// Deno 更简洁的方式
import { dirname } from "jsr:@std/path";
const __dirname = dirname(import.meta.url);
// 或者直接使用 URL
const currentDir = new URL(".", import.meta.url).pathname;
16.4 混合使用
deno.json 中配置 npm
{
"nodeModulesDir": "auto",
"tasks": {
"dev": "deno run --watch --allow-all src/main.ts",
"test": "deno test --allow-all"
},
"imports": {
"express": "npm:express@^4.18",
"lodash": "npm:lodash-es@^4.17"
}
}
使用 npm workspaces
{
"workspaces": [
"packages/*"
]
}
16.5 常见迁移问题
| 问题 | Node.js | Deno 解决方案 |
|---|---|---|
require() | require("module") | import x from "module" |
__dirname | 全局变量 | import.meta.url |
process.env | 全局对象 | Deno.env.get() |
Buffer | 全局对象 | import { Buffer } from "node:buffer" |
console | 全局对象 | 相同,直接使用 |
setTimeout | 全局函数 | 相同,直接使用 |
global | 全局对象 | globalThis |
16.6 本章小结
| 要点 | 说明 |
|---|---|
| npm: 协议 | 直接导入 npm 包 |
| Node.js API | 高度兼容 node:* 模块 |
| package.json | 可选使用 |
| 迁移策略 | 渐进迁移最稳妥 |
| 兼容性 | Deno 2.0 兼容绝大多数 npm 包 |
📖 扩展阅读
下一章:第 17 章:Docker 容器化 → 学习 Docker 部署 Deno 应用。