第一步
这篇文章包含几个简单的例子来教你一些 Deno 的基础知识。
这个文档假设你已经具备JavaScript知识,尤其是 async
/ await
知识。 如果你不知道,你需要在尝试Deno 之前到 JavaScript基础 这里去学习先。
Hello World
Deno 是JavaScript 和 TypeScript 的运行时环境,它致力于使用 web 新特性的时候做到 web 兼容。
由于它的浏览器兼容性,一个简单的 Hello World
程序和你在浏览器中运行的没有区别。
console.log("Welcome to Deno 🦕");
试一下这个程序:
deno run https://deno.land/std/examples/welcome.ts
发起 HTTP 请求
很多程序通过 HTTP 请求获取 web server 上的数据。我们也来写一个获取文件内容并打印到终端的小程序。
你可以如同在浏览器中一样使用 web 标准 API fetch
来发起 HTTP 请求:
const url = Deno.args[0];
const res = await fetch(url);
const body = new Uint8Array(await res.arrayBuffer());
await Deno.stdout.write(body);
让我们一步步看一下这个程序:
- 获取传给程序的第一个参数并存储在变量
url
中。 - 针对这个 url 发起请求,等待响应,并将响应结果存到变量
res
中。 - 用
ArrayBuffer
解析响应体,等待响应结果,并将其转化成Uint8Array
,然后存储为变量body
。 - 将
body
内容写到标准输出
中。
试试下面的脚本:
deno run https://deno.land/std/examples/curl.ts https://example.com
你会看到这个程序将报出网络连接错误,难道我们写错了?你可能想起了介绍中提到的 Deno 是默认安全的。 所以你需要显示地设置类似网络连接的权限“特权”。
设置正确的权限标识,然后再试一次:
deno run --allow-net=example.com https://deno.land/std/examples/curl.ts https://example.com
读文件
Deno 也提供一些非 web 的 API 。它们挂在 Deno
全局上。你可以在 doc.deno.land 找到这些 API 的文档说明。
例如文件系统 API 没有 web 标准格式,所以 Deno 提供了它自己的 API。
本程序中,每一个命令行参数被认为是一个文件名,文件会被打开,然后打印到标准输出。
for (let i = 0; i < Deno.args.length; i++) {
let filename = Deno.args[i];
let file = await Deno.open(filename);
await Deno.copy(file, Deno.stdout);
file.close();
}
这里的 copy()
函数只是一个 内核-> 用户空间 -> 内核的拷贝。
从文件中读取的数据被放到同一块内存中,然后写到标准输出,展示了 Deno IO 流的基本设计方向。
试试这个程序:
deno run --allow-read https://deno.land/std/examples/cat.ts /etc/passwd
简易 TCP 服务器
这是一个建立在8080端口上简单的服务器程序,返回它发送给客户端的内容。
const listener = Deno.listen({ port: 8080 });
console.log("listening on 0.0.0.0:8080");
for await (const conn of listener) {
Deno.copy(conn, conn);
}
为了安全,Deno 不能在未经允许的情况下访问网络,为了访问网络,要使用命令行标识:
deno run --allow-net https://deno.land/std/examples/echo_server.ts
试试用 netcat 发送数据来测试它:
$ nc localhost 8080
hello world
hello world
如同例子 cat.ts
,这里的 copy()
函数没有额外的内存拷贝。它从内核中获取包数据,然后直接返回。
更多示例
你可以在 示例
一章找到更多示例,比如一个 HTTP 文件服务器。