1.2 History of Deno

To understand the creation of Deno, a new server-side runtime, we must first examine the circumstances that led to its development. Node.js, a well-established runtime for server-side applications, has been in use for over 13 years and has gained widespread recognition for its reliability and performance. Its popularity has grown significantly over time, earning the trust of prominent corporations such as PayPal, Netflix, Trello, NASA, Twitter, Walmart, and many others, which rely on Node.js to power fast and efficient web applications.

Despite Node.js's success, the need for a new runtime emerged. We will explore the reasons behind this decision and examine the motivations that led to the creation of Deno. By understanding the context and rationale behind Deno's development, we can better appreciate its design and features.

Who's behind Deno?

The Deno project is led by Ryan Dahl, the original creator of Node.js. Ryan was at the helm of Node.js for its first 3-4 years before it was transitioned to the Node Package Manager (NPM). After his involvement with Node.js, Ryan pursued other ventures, including a stint at Google.

In 2018, Ryan returned to the spotlight with a notable presentation where he openly discussed his concerns and regrets regarding Node.js. He reflected on various aspects of the project that he wished he had handled differently. This presentation marked the introduction of Deno, a new runtime born out of Ryan's determination to address these regrets.

The primary goal behind Deno's creation was to develop a modern, secure runtime that would rectify the shortcomings Ryan perceived in Node.js. He sought to create a runtime that would incorporate contemporary practices and offer enhanced security features, thereby mitigating the mistakes of the past.

We will now examine the specific areas of regret that motivated Ryan to create Deno.

The regrets

Ryan Dahl's Reflections on Node.js In 2018, at the JSConf event, Ryan Dahl delivered a presentation discussing his retrospective thoughts on Node.js. This talk, available on YouTube at https://www.youtube.com/watch?v=M3BM9TB-8yA, offers valuable insights into the motivations behind creating a new runtime.

Examining the key aspects of Ryan's regrets will provide us with a deeper understanding of the initial motivations that led to the development of Deno. By analyzing these factors, we can gain a better understanding of the foundational principles that Deno was built upon.

Promises

After the initial release of Node.js, Ryan Dahl introduced promises to the platform in June 2009. Although promises were initially integrated into the core of Node.js, they were later removed in February 2010. At that time, the use of promises for async/await operations was still relatively new, and the core Node.js framework relied heavily on callbacks, a pattern that still persists today.

In modern programming, promises have become essential for supporting contemporary async/await code. However, a significant portion of the Node.js codebase still relies on callback-based structures. While asynchronous programming techniques have evolved, the original callback-oriented code remains functional and effective.

Given the robust and dependable nature of the existing callback-centric foundation, it is unlikely that the established code will be completely replaced with promises or async/await constructs. The stability and reliability of Node.js applications are ensured by this foundation.

Open access

Both Node.js and Deno leverage Google's V8 JavaScript engine to execute JavaScript programs. However, they differ in their approaches to security and isolation.

V8 operates within a secure sandboxed environment, confining JavaScript code execution and preventing direct access to sensitive system resources. In contrast, Node.js has traditionally taken a more open approach, allowing programs to access a wide range of resources available to user-level processes. This was the case for all Node.js versions prior to v20.

Starting from version v20, Node.js has begun to adopt sandboxing for applications, a shift towards enhanced security and isolation. Although this feature is still experimental, it marks a significant change in Node.js' approach. The maturation of this sandboxing feature will likely require considerable time, as it undergoes refinement and enhancement.

NPM or package.json

The idea behind package.json was influenced by NPM (Node Package Manager), a widely used package manager for Node.js. Initially, Ryan Dahl, the creator of Node.js, supported the use of package.json by enabling the require() function to reference the file for module resolution. As NPM evolved, it became the primary repository for various Node.js modules and expanded its scope to become one of the largest package managers across multiple programming languages.

However, a significant drawback of NPM is its private ownership. Originally an independent entity, NPM was acquired by GitHub and later by Microsoft, closely tying Node.js and NPM together. Ryan Dahl regretted the limitation of only being able to source Node.js packages from a single repository, rather than diverse sources. This led to a desire for a more decentralized approach to package management.

Note: Deno now fully supports NPM (this is required to compete in the market).

Node_modules

The module resolution algorithm in Node.js became increasingly complex over time. Initially, the concept of vendor modules showed promise, but the use of $NODE_PATH introduced challenges. Furthermore, this approach deviated significantly from the conventions used in web browsers. Ryan Dahl, the creator of Node.js, aimed to align module resolution with established standards, but this goal was not realized within the Node.js framework. As a result, the module resolution logic in Node.js remains uniquely tailored to its specific environment, diverging from broader web standards.

Implicit require

Node.js's require("module") function, used without the ".js" extension, was a unique feature designed specifically for the Node.js environment. However, this approach differs from how JavaScript works in web browsers. In browser-based JavaScript, omitting the ".js" extension in a script tag's src attribute is not valid. Instead, the module loader must search various file system locations to infer the user's intended module reference, a process that can lead to ambiguity and errors.

Index.js

Ryan Dahl was drawn to the name "index.js" because of its similarity to "index.html". However, this naming convention introduced unnecessary complexity into the module loading system. This complexity was further exacerbated when the 'require' function began to support package.json files, leading to unforeseen challenges in the module loading process.

Conception of Deno

As mentioned earlier, Ryan Dahl expressed his regrets regarding Node.js development. In his JSConf 2018 presentation https://www.youtube.com/watch?v=M3BM9TB-8yA, he shared additional concerns. Notably, he regretted granting a private company, NPM, control over third-party modules and the Node.js ecosystem. This decision ultimately led to NPM gaining control over Node.js, which was not the intended outcome.

Although some of these regrets, like NPM integration, have been addressed in Deno over time, the experience served as a valuable lesson. Deno's need to access NPM's extensive library of packages (1.4 million) drove the integration. The details of this evolution will be discussed in the next section.

These moments of regret inspired Ryan to create a new runtime, designed to make better choices from the start. This runtime, built with modern technologies, prioritizes openness and avoids external control, aiming to correct the mistakes of the past.

Last updated