Deno LandDeno

Deno 1.14 Release Notes

September 14th, 2021
Bartek IwaƄczuk, Luca Casonato

Deno 1.14 has been tagged and released with the following features and changes:

If you already have Deno installed, you can upgrade to 1.14 by running

deno upgrade

If you are installing Deno for the first time, you can use one of the methods listed below:

# Using Shell (macOS and Linux):
curl -fsSL https://deno.land/x/install/install.sh | sh

# Using PowerShell (Windows):
iwr https://deno.land/x/install/install.ps1 -useb | iex

# Using Homebrew (macOS):
brew install deno

# Using Scoop (Windows):
scoop install deno

# Using Chocolatey (Windows):
choco install deno

New features

Web Crypto API additions

This release introduces many new Web Crypto APIs:

We are continually working on improving the Web Crypto API. We are hoping to be API complete by the end of the year. You can subscribe to this tracking issue to be notified of progress.

Thanks to Divy Srivastava for the significant work on the Web Crypto implementation in Deno.

Customization options for deno lint and deno fmt

Deno in the past has pushed back on configurability of deno lint and deno fmt. We believe the ecosystem benefits from canonical code styles and linting rules. Over the past year, we have gotten many requests from users to be able to tweak the options used by deno lint and deno fmt to cater to specific, legitimate needs. This release allows deno lint and deno fmt to be configured.

We still recommend that most users use the default options. These options work well for most teams and projects. By default deno lint will run with all recommended lint rules enabled.

Now --rules-exclude, --rules-include, and --rules-tags can now be used to exclude rules, or include specific rules not in the recommended set (like ban-untagged-todo).

The style rules of deno fmt are based on prettier. There are just five options that can be used to tweak the style rules:

These options can now also be configured in the file specified by --config. We have designed this flag so that the same file can be used with deno run --config, deno fmt --config, and deno lint --config. That is, we're extending the tsconfig.json file.

Before:

{
  "compilerOptions": {
    "allowJs": true,
    "lib": ["deno.window"],
    "strict": true
  }
}

After:

{
  "compilerOptions": {
    "allowJs": true,
    "lib": ["deno.window"],
    "strict": true
  },
  "lint": {
    "files": {
      "include": ["src/"],
      "exclude": ["src/testdata/"]
    },
    "rules": {
      "tags": ["recommended"],
      "include": ["ban-untagged-todo"],
      "exclude": ["no-unused-vars"]
    }
  },
  "fmt": {
    "files": {
      "include": ["src/"],
      "exclude": ["src/testdata/"]
    },
    "options": {
      "useTabs": true,
      "lineWidth": 80,
      "indentWidth": 4,
      "singleQuote": true,
      "proseWrap": "preserve"
    }
  }
}

We intend to further improve the experience of using Deno, by allowing more existing flags to be specified in the configuration file, as well as providing automatic discovery of the configuration file in future releases. In 1.14 you must manually specify the configuration file, there is no auto-detection.

Note that using a configuration file is not required now and will not be required in the future. Deno still works best with the default options and no configuration file. All options specified in the configuration file can also be set using command line flags (for example --options-use-tabs for deno fmt). Using the configuration file should be considered an "as needed" feature, not something every user should be reaching to as the first thing when setting up a project.

For in-depth description of allowed options in configuration file, see manual page or JSON schema file.

The VSCode extension has built-in support for this file via the deno.config setting.

URLPattern

This release introduces a new unstable web platform API for matching URLs against patterns. URLPattern is a builtin alternative to the popular path-to-regexp library.

The pattern syntax is very similar to path-to-regexp. What sets URLPattern apart is that it is capable of matching more than just paths - it can match each part of a URL (protocol, hostname, pathname, query string, hash, etc.) individually.

const pattern = new URLPattern({ pathname: "/books/:id" });

console.log(pattern.test("https://example.com/books/123")); // true
console.log(pattern.test("https://example.com/books/123/456")); // false
console.log(pattern.test("https://example.com/books")); // false

console.log(pattern.exec("https://example.com/books/123").pathname); // { input: "/books/123", groups: { id: "123" } }

This API is unstable (--unstable is required for use), but is not likely to change significantly before stabilization. Unless new blockers arise, we will be stabilizing the API in Deno 1.15, in sync with the stabilization in Chrome 95.

Detailed documentation will be available on MDN in a couple of days. You can view a preview of the MDN docs here.

Thanks to Jake Archibald for the initial API proposal, Ben Kelly for the specification effort, and @crowlKats for the implementation in Deno.

Stabilization of native server side WebSocket API

Native server side WebSocket support was added in Deno 1.12, however it was only available behind --unstable flag.

After testing the API in the wild and getting feedback from users, Deno.upgradeWebSocket() API has been stabilized in 1.14 and no longer requires --unstable flag.

Zero-copy ArrayBuffer transfers between workers

This releases introduces the capability of transferring ArrayBuffers between workers without requiring copying. This can significantly speed up transfers for large buffers.

To transfer a buffer instead of copying it, specify the buffer in the transfer option when calling postMessage().

File locking APIs

This releases introduces four new unstable APIs that can be used for file locking:

These APIs are essential for projects like sqlite to provide proper database synchronization.

Thanks to Tilman Roeder for implementing this feature.

Changes to OS signals APIs

1.14 overhauls the unstable OS signals API. Deno.Signal enum was changed to a union of string identifiers for signals, allowing signal APIs to use string identifiers as well, instead of requiring to pass Deno.Signal members.

Before:

for await (const _ of Deno.signal(Deno.Signal.SIGTERM)) {
  console.log("got SIGTERM!");
}

After:

for await (const _ of Deno.signal("SIGTERM")) {
  console.log("got SIGTERM!");
}

Additionally the Deno.signals namespace, containing helper methods for creating different signal streams was removed completely. These changes were made in an effort towards stabilization of signal API that we expect to happen soon.

Mutual TLS support in fetch

This release introduces support for mutual TLS in fetch(). Mutual TLS (sometimes called client authentication) is a way to authenticate a client to a server. A few common use cases include:

Client certificates and private keys can now be specified to fetch by means of a custom Deno.HttpClient.

const client = Deno.createHttpClient({
  certChain: Deno.readTextFileSync("./cert.pem"),
  privateKey: Deno.readTextFileSync("./key.pem"),
});
const resp = await fetch("https://example.com/", { client });

Thanks to Sean Michael Wykes and Eric Lindvall for implementing this feature.

Basic auth support in DENO_AUTH_TOKENS

Deno allows to fetch code from private repositories and servers that require authentication, by providing Bearer tokens in the DENO_AUTH_TOKENS environmental variable.

Starting with 1.14 DENO_AUTH_TOKENS also accepts Basic authentication making it possible to fetch code from more servers.

To specify Basic authentication data use username:[email protected] syntax, eg.

DENO_AUTH_TOKENS=testuser123:[email protected]:4554

Both Basic data and Bearer tokens can be mixed together in the environmental variable like so:

[email protected];testuser123:[email protected]:4554

Thanks to @BasiqueEvangelist for implementing this feature.

URL parsing is now 3x faster

A few weeks ago we got some reports that our URL parsing was significantly slower than other engines like Chrome. This is a relatively high impact performance issue, because URL parsing is a very common operation in web server applications.

We are happy to report that our URL parsing is now 3x faster than in 1.13. This is a significant improvement, but we are still investigating ways to further optimize this hotpath in the future.

gid and uid can now be specified for subprocesses

The subprocess API gets much requested feature that allows to specify user id and group id for the spawned processes.

Deno.run({
  cmd: [
    "echo",
    "Hello from root user",
  ],
  uid: 0,
});
Deno.run({
  cmd: [
    "echo",
    "Hello from root group",
  ],
  gid: 0,
});

This feature is unstable and thus requires --unstable flag. Currently it is only supported on Unix systems and ignored on Windows.

Thanks to @crowlKats for implementing this feature.

Much faster std/http module

Version 0.107.0 of standard library brings a major revamp of the http module.

After stabilization of native HTTP bindings in v1.13, the http/server.ts module was rewritten to use that newly stabilized API. As a result a significant performance boost was achieved, as well as a more user-friendly API that handles mundane parts of creating solid HTTP servers; like error handling and multiplexing of connections.

Thanks to Craig Morten for implementing these changes.

Updates to VSCode extension

The official Deno VSCode extension got a number of updates including:

TypeScript 4.4

Deno 1.14 ships with the latest stable version of TypeScript. For more information on new features in TypeScript see TypeScript's 4.4 blog post

V8 9.4

This release includes a new version of V8, which includes many bug fixes, and one important new feature: class static initialization blocks. Classes get the ability to group code that should run once per class evaluation via static initialization blocks.

class C {
  // This block will run when the class itself is evaluated
  static {
    console.log("Why is it always raining in Deno land?");
  }
}

An explainer for static initialization blocks can be found on the V8 blog. See also the V8 9.4 release notes.