---
title: Workers Binding API
description: Query D1 databases from a Cloudflare Worker using the D1 Binding API for prepared statements, batching, and type-safe results.
image: https://developers.cloudflare.com/dev-products-preview.png
---

> Documentation Index  
> Fetch the complete documentation index at: https://developers.cloudflare.com/d1/llms.txt  
> Use this file to discover all available pages before exploring further.

[Skip to content](#%5Ftop) 

# Workers Binding API

You can execute SQL queries on your D1 database from a Worker using the Worker Binding API. To do this, you can perform the following steps:

1. [Bind the D1 Database](https://developers.cloudflare.com/d1/get-started/#3-bind-your-worker-to-your-d1-database).
2. [Prepare a statement](https://developers.cloudflare.com/d1/worker-api/d1-database/#prepare).
3. [Run the prepared statement](https://developers.cloudflare.com/d1/worker-api/prepared-statements).
4. Analyze the [return object](https://developers.cloudflare.com/d1/worker-api/return-object) (if necessary).

Refer to the relevant sections for the API documentation.

## TypeScript support

D1 Worker Bindings API is fully-typed via the runtime types generated by running [wrangler types](https://developers.cloudflare.com/workers/languages/typescript/) package, and also supports [generic types ↗](https://www.typescriptlang.org/docs/handbook/2/generics.html#generic-types) as part of its TypeScript API. A generic type allows you to provide an optional `type parameter` so that a function understands the type of the data it is handling.

When using the query statement methods [D1PreparedStatement::run](https://developers.cloudflare.com/d1/worker-api/prepared-statements/#run), [D1PreparedStatement::raw](https://developers.cloudflare.com/d1/worker-api/prepared-statements/#raw) and [D1PreparedStatement::first](https://developers.cloudflare.com/d1/worker-api/prepared-statements/#first), you can provide a type representing each database row. D1's API will [return the result object](https://developers.cloudflare.com/d1/worker-api/return-object/#d1result) with the correct type.

For example, providing an `OrderRow` type as a type parameter to [D1PreparedStatement::run](https://developers.cloudflare.com/d1/worker-api/prepared-statements/#run) will return a typed `Array<OrderRow>` object instead of the default `Record<string, unknown>` type:

TypeScript

```

// Row definition

type OrderRow = {

  Id: string;

  CustomerName: string;

  OrderDate: number;

};


// Elsewhere in your application

// env.MY_DB is the D1 database binding from your Wrangler configuration file

const result = await env.MY_DB.prepare(

  "SELECT Id, CustomerName, OrderDate FROM [Order] ORDER BY ShippedDate DESC LIMIT 100",

).run<OrderRow>();


```

## Type conversion

D1 automatically converts supported JavaScript (including TypeScript) types passed as parameters via the Workers Binding API to their associated D1 types 1. This conversion is permanent and one-way only. This means that when reading the written values back in your code, you will get the converted values rather than the originally inserted values.

Note

We recommend using [STRICT tables ↗](https://www.sqlite.org/stricttables.html) in your SQL schema to avoid issues with mismatched types between values that are actually stored in your database compared to values defined by your schema.

The type conversion during writes is as follows:

| JavaScript (write) | D1               | JavaScript (read) |
| ------------------ | ---------------- | ----------------- |
| null               | NULL             | null              |
| Number             | REAL             | Number            |
| Number 2           | INTEGER          | Number            |
| String             | TEXT             | String            |
| Boolean 3          | INTEGER          | Number (0,1)      |
| ArrayBuffer        | BLOB             | Array 4           |
| ArrayBuffer View   | BLOB             | Array 4           |
| undefined          | Not supported. 5 | \-                |

1 D1 types correspond to the underlying [SQLite types ↗](https://www.sqlite.org/datatype3.html).

2 D1 supports 64-bit signed `INTEGER` values internally, however[BigInts ↗](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global%5FObjects/BigInt)are not currently supported in the API yet. JavaScript integers are safe up to[Number.MAX\_SAFE\_INTEGER ↗](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global%5FObjects/Number/MAX%5FSAFE%5FINTEGER).

3 Booleans will be cast to an `INTEGER` type where `1` is `TRUE` and`0` is `FALSE`.

4 `ArrayBuffer` and [ArrayBufferviews ↗](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global%5FObjects/ArrayBuffer/isView)are converted using[Array.from ↗](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global%5FObjects/Array/from).

5 Queries with `undefined` values will return a `D1_TYPE_ERROR`.

## API playground

The D1 Worker Binding API playground is an `index.js` file where you can test each of the documented Worker Binding APIs for D1\. The file builds from the end-state of the [Get started](https://developers.cloudflare.com/d1/get-started/#write-queries-within-your-worker) code.

You can use this alongside the API documentation to better understand how each API works.

Follow the steps to setup your API playground.

### 1\. Complete the Get started tutorial

Complete the [Get started](https://developers.cloudflare.com/d1/get-started/#write-queries-within-your-worker) tutorial. Ensure you use JavaScript instead of TypeScript.

### 2\. Modify the content of `index.js`

Replace the contents of your `index.js` file with the code below to view the effect of each API.

index.js

JavaScript

```

// D1 API Playground - Test each D1 Worker Binding API method

// Change the URL pathname to test different methods (e.g., /RUN, /RAW, /FIRST)

export default {

  async fetch(request, env) {

    const { pathname } = new URL(request.url);


    // Sample data for testing

    const companyName1 = `Bs Beverages`;

    const companyName2 = `Around the Horn`;


    // Prepare reusable statements

    const stmt = env.DB.prepare(`SELECT * FROM Customers WHERE CompanyName = ?`);

    const stmtMulti = env.DB.prepare(`SELECT * FROM Customers; SELECT * FROM Customers WHERE CompanyName = ?`);

    const session = env.DB.withSession("first-primary")

    const sessionStmt = session.prepare(`SELECT * FROM Customers WHERE CompanyName = ?`);


      // Test D1PreparedStatement::run - returns full D1Result object

      if (pathname === `/RUN`){

      const returnValue = await stmt.bind(companyName1).run();

      return Response.json(returnValue);


      // Test D1PreparedStatement::raw - returns array of arrays

    } else if (pathname === `/RAW`){

      const returnValue = await stmt.bind(companyName1).raw();

      return Response.json(returnValue);


      // Test D1PreparedStatement::first - returns first row only

    } else if (pathname === `/FIRST`){

      const returnValue = await stmt.bind(companyName1).first();

      return Response.json(returnValue);


      // Test D1Database::batch - execute multiple statements

    } else if (pathname === `/BATCH`) {

      const batchResult = await env.DB.batch([

        stmt.bind(companyName1),

        stmt.bind(companyName2)

      ]);

      return Response.json(batchResult);


      // Test D1Database::exec - execute raw SQL without parameters

    } else if (pathname === `/EXEC`){

      const returnValue = await env.DB.exec(`SELECT * FROM Customers WHERE CompanyName = "Bs Beverages"`);

      return Response.json(returnValue);


      // Test D1 Sessions API with read replication

    } else if (pathname === `/WITHSESSION`){

      const returnValue = await sessionStmt.bind(companyName1).run();

      console.log("You're now using D1 Sessions!")

      return Response.json(returnValue);

    }


      // Default response with instructions

      return new Response(

      `Welcome to the D1 API Playground!

      \nChange the URL to test the various methods inside your index.js file.`,

      );

    },


};


```

### 3\. Deploy the Worker

1. Navigate to your tutorial directory you created by following step 1.
2. Run `npx wrangler deploy`.  
Terminal window  
```  
npx wrangler deploy  
```  
```  
⛅️ wrangler 3.112.0  
--------------------  
Total Upload: 1.90 KiB / gzip: 0.59 KiB  
Your worker has access to the following bindings:  
- D1 Databases:  
  - DB: DATABASE_NAME (<DATABASE_ID>)  
Uploaded WORKER_NAME (7.01 sec)  
Deployed WORKER_NAME triggers (1.25 sec)  
  https://jun-d1-rr.d1-sandbox.workers.dev  
Current Version ID: VERSION_ID  
```
3. Open a browser at the specified address.

### 4\. Test the APIs

Change the URL to test the various D1 Worker Binding APIs.

```

```

```json
{"@context":"https://schema.org","@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"item":{"@id":"/directory/","name":"Directory"}},{"@type":"ListItem","position":2,"item":{"@id":"/d1/","name":"D1"}},{"@type":"ListItem","position":3,"item":{"@id":"/d1/worker-api/","name":"Workers Binding API"}}]}
```
