跳到主要内容
Deno 2.4 发布,带来 deno bundle、bytes/text 导入、稳定的 OTel 等功能
了解更多

Deno KV 发布公告

我们很高兴推出 Deno KV,一个强一致性的键值数据库,在全球范围内复制以实现在 全球35个地区 的低延迟读取。

Deno Deploy 旨在提供在边缘部署和运行 JavaScript、TypeScript 和 Wasm 的最简单、最快速的方式。然而,之前在 Deno Deploy 上创建有状态应用程序需要连接到外部云数据库,这涉及到额外的配置步骤、本地测试挑战,并且如果数据存储未进行地理复制,可能会削弱使用边缘计算的优势。

随着今天的发布,我们将一个全球集成的数据库引入 Deno,让您能够轻松开发功能齐全的应用程序,同时克服这些障碍。

在这篇文章中,我们将讨论 Deno KV 的关键方面

如果您对使用 Deno KV 感兴趣,请加入等候名单

注意:Deno KV 目前处于测试阶段,不保证长期数据持久性。在生产应用程序中使用 Deno KV 时请牢记这一点。

注意:Deno KV 目前处于公开测试阶段

本地运行或托管

Deno KV 无缝集成到开源 Deno 运行时中,允许您在本地运行它,或将其作为托管服务部署,无需任何配置。

在本地运行时,Deno KV 由 SQLite 提供支持,为本地开发、测试或单区域生产系统提供了轻量级且易于使用的解决方案。

当您将应用程序部署到 Deno Deploy 时,Deno KV 数据库会自动由 FoundationDB 提供支持。此托管解决方案由 Deno 公司运营,确保了高性能和可靠性,无需您进行手动配置或维护。

简单而强大

Deno KV 是一个一流的原始类型,仅暴露少数几个方法,您可以使用它们来存储、检索、删除和枚举数据。Deno KV 专为 JavaScript 设计,可以存储任何 JavaScript 结构化可序列化值,例如对象、数组、BigInt、日期等。

const kv = await Deno.openKv();

const key = ["users", crypto.randomUUID()];
const value = { name: "Alice", created: new Date() };
await kv.set(key, value);

const result = await kv.get(key);
console.log(result.value);
// { name: "Alice", created: 2023-05-01T09:24:07.620Z }

使用 kv.list() 操作列出所有匹配特定选择器的键。在下面的示例中,所有以特定前缀开头的键都将被选中。

await kv.set(["users", "alice"], { birthday: "January 1, 1990" });
await kv.set(["users", "sam"], { birthday: "February 14, 1985" });
await kv.set(["users", "taylor"], { birthday: "December 25, 1970" });

// List out all entries with keys starting with `["users"]`
const iter = kv.list({ prefix: ["users"] });
for await (const entry of iter) {
  console.log(entry.key);
  console.log(entry.value);
}

列表操作以批处理方式从存储中检索数据,默认每次检索500个键。要实现分页,请将 iter.cursor 属性传递回 kv.list() 的后续调用中。

在文档中了解更多可用方法.

原子事务

对于许多应用程序,可靠的数据库事务是必需的。Deno KV 允许使用 kv.atomic() 创建具有强一致性的多键事务,这些事务默认立即持久化。

const kv = await Deno.openKv();
const change = 10;

const bob = await kv.get(["balance", "bob"]);
const liz = await kv.get(["balance", "liz"]);
if (bob.value < change) {
  throw "not enough balance";
}

const success = await kv.atomic()
  .check(bob, liz) // balances did not change
  .set(["balance", "bob"], bob.value - change)
  .set(["balance", "liz"], liz.value + change)
  .commit();

了解更多关于我们如何处理事务的信息。

一致性和性能

Deno KV 是一个强一致性数据库,提供外部一致性,包括

  • 可序列化性:事务的最高隔离级别,确保并发事务执行的结果与这些事务的顺序执行结果相同。
  • 线性一致性:保证读写等操作看起来是瞬时发生的,并且是实时发生的。一旦写操作完成,所有后续读操作都会返回更新后的值,确保强实时排序。

您可以为单个读取操作使用 consistency: "eventual" 选项来放宽一致性约束

// Read with eventual consistency from the nearest region
await db.get(["my-key"], { consistency: "eventual" });

// Read with strong consistency from the primary region
await db.get(["my-key"], { consistency: "strong" });

此选项允许系统从全球副本和缓存提供读取服务,以实现最小延迟。

以下是我们最受欢迎区域的测试版平均延迟数据。预计在公开测试版和 GA 版本中会有所改进。

区域 延迟(最终一致性) 延迟(强一致性)
北弗吉尼亚 (us-east4) 7毫秒 7毫秒
法兰克福 (europe-west3) 7毫秒 94毫秒
荷兰 (europe-west4) 13毫秒 95毫秒
加利福尼亚 (us-west2) 72毫秒 72毫秒
香港 (asia-east2) 42毫秒 194毫秒

用例和示例

Deno KV 是一种多功能解决方案,用于管理应用程序状态,使其成为各种用例的理想选择。以下是一些展示 Deno KV 潜力的应用程序示例

  • 实时协作:Deno KV 可以在多个客户端之间存储和同步数据,从而实现文档编辑或多人游戏等任务的无缝协作。实时应用程序通常使用 Deno 的 BroadcastChannel 来帮助同步状态。
  • 用户数据管理:使用 Deno KV 存储和管理用户生成的内容,例如博客文章和评论。通过使用全球复制的数据库,无论用户身在何处,您都可以确保快速访问。
  • 身份验证:Deno KV 可以存储用户凭据、角色和权限,为您的应用程序提供安全高效的身份验证。

作为一个基本示例,请访问 此 Playground,了解使用 Deno KV 创建全球一致、持久计数器是多么简单。

import { serve } from "/std@0.155.0/http/server.ts";

const db = await Deno.openKv();

serve(async (req: Request) => {
  await db.atomic().sum(["views"], 1n).commit();
  const res = await db.get(["views"]);
  const views = res.value.value;
  return new Response(`Views: ${views}`);
});

以下是我们构建的一些更高级的演示应用程序,以展示 Deno KV 的功能

  • 多人井字游戏(源代码演示):一个简单的在线多人游戏。
  • 像素页面(源代码演示):一个协作绘图应用程序,展示了实时同步和用户数据管理。
  • 共享待办事项列表(源代码演示):一个任务管理应用程序,展示了 Deno KV 存储和管理用户生成数据的能力。
  • KV 素描本(源代码演示):一个基于网络的素描本,突出了 Deno KV 存储和检索用户创建素描的能力,展示了用户数据管理。

这些示例让您大致了解 Deno KV 可以实现的功能。凭借其简单性、可扩展性和全球复制功能,Deno KV 是寻求轻松构建有状态应用程序的开发人员的强大工具。

下一步

我们的使命是使 Deno Deploy 成为部署和运行 API 服务器、Web 应用程序和边缘功能的首选平台。提供全球复制的持久数据存储是实现这一目标的重要一步。在未来几个月,我们将推出更多功能,进一步简化仅用几行代码构建和部署应用程序的过程。

在测试期间,用户可以免费享受最高一千兆字节的存储空间。我们很快将公布定价详情。

其他资源

如果您对使用 Deno KV 感兴趣,请加入等候名单

不要错过任何更新 — 在 Twitter 上关注我们