denoflare CLI installation command
To deploy Deno to Cloudflare Workers, use the community-created CLI denoflare. Install it with: deno install --unstable-worker-options --allow-read --allow-net --global --allow-env --allow-run --name denoflare --force https://raw.githubusercontent.com/skymethod/denoflare/v0.6.0/cli/cli.ts
Module Worker minimum export structure
A Module Worker function must export default an object that exposes a fetch function, which returns a Response object. Example: export default { fetch(request: Request): Response { return new Response("Hello, world!"); }; }
Testing Deno Cloudflare Worker locally
To test a Deno Cloudflare Worker locally, run denoflare serve main.ts from the command line. The worker will be accessible at localhost:8080 in your browser.
.denoflare configuration file structure
The .denoflare config file is JSON and contains a $schema field, scripts object, and profiles object. Scripts require a path field (absolute path to the TypeScript file) and localPort field. Profiles require accountId and apiToken fields for Cloudflare authentication.
Finding Cloudflare accountId
Your Cloudflare accountId can be found by going to the Cloudflare dashboard, clicking Workers, and locating Account ID on the right side of the page.
Generating Cloudflare API token for denoflare
Generate an apiToken from your Cloudflare API Tokens settings at https://dash.cloudflare.com/profile/api-tokens. When creating an API token, use the template "Edit Cloudflare Workers" to ensure proper permissions.
Pushing Deno worker to Cloudflare
After configuring the .denoflare file with your accountId and apiToken, deploy your worker by running: denoflare push main
Deploying Fresh app to Cloudflare Workers
The Fresh framework has its own deployment guidance for Cloudflare Workers and other platforms. Refer to the Fresh documentation at https://fresh.deno.dev/docs/ for deployment instructions.
Deploying Deno to Cloudflare Workers overview
Cloudflare Workers allows you to run JavaScript on Cloudflare's edge network. You can deploy Deno functions to Cloudflare Workers as Module Workers. Web servers or full apps cannot be deployed; only Module Workers are supported.
Wrangler is Node.js CLI provided by Cloudflare
Wrangler is the official CLI for Node.js provided by Cloudflare for its developer platform. It can be invoked from Deno using npm:wrangler after adding it with `deno add npm:wrangler`.
Deploy Deno to Cloudflare Workers with Wrangler
To deploy a Deno application to Cloudflare Workers using Wrangler: (1) Add wrangler npm module with `deno add npm:wrangler`. (2) Create wrangler.json with schema from unpkg.com, specifying name, main entry point, and compatibility_date. (3) Add deno.json tasks for deploy, dev, start, and cf-typegen commands. (4) Run `deno task cf-typegen` to generate worker-configuration.d.ts. (5) Configure deno.json compilerOptions with lib, types, and skipLibCheck to use Cloudflare Workers types. (6) Create worker script in src/mod.ts exporting an object with a fetch handler satisfying ExportedHandler<Env>. (7) Set up build with esbuild and @deno/esbuild-plugin to bundle src/mod.ts to dist/server.js. (8) Configure wrangler.json build command to run the build task. (9) Execute `deno task deploy` to publish to Cloudflare Workers.
Wrangler setup for Deno: deno.json tasks
Add the following tasks to deno.json for Wrangler integration: deploy (deno --allow-env --allow-run npm:wrangler deploy), dev (deno npm:wrangler dev), start (deno npm:wrangler dev), cf-typegen (deno npm:wrangler types), and build (deno run -REW --allow-run build.ts).
wrangler.json configuration for Deno
A wrangler.json for Deno should include: $schema pointing to https://www.unpkg.com/wrangler/config-schema.json, name (project name), main (entry point: initially src/mod.ts, then dist/server.js after build setup), compatibility_date (e.g., 2026-04-18), observability.enabled (true), and build.command (deno task build).
deno.json compilerOptions for Cloudflare Workers
When deploying to Cloudflare Workers, configure deno.json compilerOptions as follows: lib should be ["esnext"] (or ["esnext", "deno.ns"] if using Deno.* APIs) to remove Deno's default Web/DOM globals and use workerd types instead, types should be ["./worker-configuration.d.ts"] to load generated Workers types project-wide, and skipLibCheck should be true to skip type checking inside declaration files.
Cloudflare Workers Deno worker script structure
A Cloudflare Workers script in src/mod.ts must export an object containing a fetch handler and satisfy the ExportedHandler<Env> type. Example: export default { async fetch(req) { return new Response("Hello World"); }, } satisfies ExportedHandler<Env>;
Build configuration for Deno with Wrangler esbuild
To set up a build script for Deno with Wrangler: (1) Install esbuild and @deno/esbuild-plugin with `deno add npm:esbuild jsr:@deno/esbuild-plugin`. (2) Create build.ts that imports both packages and calls esbuild.build() with entryPoints ["src/mod.ts"], outfile "dist/server.js", format "esm", bundle true, minify true, treeShaking true, and plugins [denoPlugin()]. (3) Call esbuild.stop() after build. (4) Add build task to deno.json as `deno run -REW --allow-run build.ts`. (5) Set wrangler.json main to dist/server.js and build.command to "deno task build".
cf-typegen generates worker-configuration.d.ts
Running `deno task cf-typegen` (which executes `deno npm:wrangler types`) automatically generates worker-configuration.d.ts, a type definition file that provides the Env interface and Cloudflare Workers runtime types (ExportedHandler, Request, Response, and other workerd global scope types).
Denoflare as alternative to Wrangler for Cloudflare Workers
Denoflare is a Deno-friendly third-party tool guaranteed to run on Deno for deploying to Cloudflare Workers. Unlike Wrangler, there is no guarantee that Denoflare can correctly utilize all Cloudflare features, so use Wrangler for full feature support.
Deno Deploy is a global edge network hosting service
Deno Deploy allows you to host your Deno applications on a global edge network with built-in telemetry and CI/CD tooling.
Deno Deploy app configuration for static site
When deploying a static Vite site to Deno Deploy, the app configuration includes: Framework preset set to 'No preset', Runtime configuration set to 'Static Site', Install command as 'deno install', Build command as 'deno task build', and Static Directory set to 'dist'.
Deno Deploy preview URL format
Once deployment to Deno Deploy completes, you receive a preview URL with the format 'https://your-app-name.your-org-name.deno.net'.
Deno Deploy automatic redeploy on git push
When you commit and push changes to the GitHub repository linked to your Deno Deploy application, a new build automatically starts on the Deno Deploy dashboard.
Deno Deploy Logs feature
Deno Deploy's Logs feature in the application dashboard displays console output from your application and includes a search bar to filter logs by context (for example, 'context:production').
Deno Deploy Traces feature
Deno Deploy's Traces feature allows you to view request traces with detailed timing information. You can select individual traces to examine spans and understand request processing.
Deno Deploy Metrics feature
Deno Deploy's Metrics feature displays application performance metrics including request counts, error rates, and response times.
JSR automatically generates documentation for published packages
If you publish your package to JSR (JavaScript Registry), you get beautiful documentation automatically generated for free. JSR uses the same 'deno doc' technology under the hood to create searchable, web-based documentation for all published packages. Publish with 'deno publish' and JSR handles the rest.
Use @std/http file-server as installed script
After installation, run the file server with: file-server . to serve the current directory. It listens on http://0.0.0.0:8000 by default. Run file-server --help to see available options.
Install @std/http file server with deno install
For Deno 2.x, install the standard library file server with: deno install --global --allow-net --allow-read jsr:@std/http/file-server. This installs the script to the Deno installation root. For Deno 1.x, omit the --global flag.
GitHub Actions cache-hash parameter
To key the GitHub Actions cache on something other than deno.lock files, set cache-hash parameter in setup-deno (which implies cache: true). For example: cache-hash: ${{ hashFiles('**/deno.json') }}
Example GitHub Actions workflow for Deno CI
name: CI
on: [push, pull_request]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: denoland/setup-deno@v2
with:
deno-version: v2.x # Latest stable Deno
cache: true # Cache dependencies between runs
- run: deno ci # Install dependencies from the lockfile
- run: deno fmt --check
- run: deno lint
- run: deno test --allow-all
This minimal workflow checks formatting, lints, and runs tests on every push and pull request.
Example GitHub Actions matrix for testing across Deno versions
jobs:
test:
runs-on: ubuntu-latest
continue-on-error: ${{ matrix.deno-version == 'canary' }}
strategy:
matrix:
deno-version: [v2.x, canary]
steps:
- uses: actions/checkout@v4
- uses: denoland/setup-deno@v2
with:
deno-version: ${{ matrix.deno-version }}
cache: true
- run: deno test --allow-all
This tests the same job against stable (v2.x) and canary versions, with continue-on-error keeping a canary failure from failing the whole workflow.
deno-version parameter accepts semver ranges
The deno-version parameter in setup-deno accepts a semver range (like v2.x), an exact version, or 'canary'.
denoland/setup-deno GitHub Action
The denoland/setup-deno action (v2) installs Deno on GitHub Actions runners. It accepts deno-version parameter (semver range like v2.x, exact version, or 'canary'), and has a cache parameter to cache dependencies between runs.
GitHub Actions cache behavior with deno
With cache: true in setup-deno, the action saves and restores DENO_DIR (the directory where Deno stores downloaded dependencies). The cache key includes the job id, the runner OS and architecture, and a hash of all deno.lock files. The cache is invalidated exactly when the lockfile changes.