---
title: "Cloudflare"
description: "Instrument Cloudflare Workers with the Middleware APM package to collect traces, metrics and custom logs from your edge applications."
section: "APM"
breadcrumb: "APM > Cloudflare"
canonical: "https://docs.middleware.io/get-started/apm/cloudflare"
---
# Cloudflare

Use the Middleware APM package for Cloudflare Workers to send traces, metrics and application logs from your Workers to Middleware. The table shows which data types the integration collects.

| Traces | Metrics | App Logs | Custom Logs | Profiling |
| --- | --- | --- | --- | --- |
| ✅ | ✖ | ✖ | ✅ | ✖ |

## 1. Prerequisites

Wrangler installed v2.2 or newer. Check your version:

```bash
   wrangler version
```

## 2. Install

#### 1 Install the Worker APM package

```bash
   npm i @middleware.io/agent-apm-worker
```

#### 2 Import the tracker

```bash
   import { init, track } from '@middleware.io/agent-apm-worker';
```

#### 3 Initialize the tracker (once per isolate)

Add this near the top of your Worker module (or inside fetch as shown on the docs page):

```javascript
   init({
  serviceName: "{APM-SERVICE-NAME}",
  accountKey: "your-initial-token",
  target: "https://{ACCOUNT-UID}.middleware.io",
  consoleLogEnabled: false, // set true to see instrumented logs locally
});
```

## 3. Capture application data

- Trace the incoming request
  Use track(request, ctx) and return via sdk.sendResponse(response):

  ```js
     export default {
     async fetch(request: Request, env: Env, ctx: ExecutionContext): Promise<Response> {
        const sdk = track(request, ctx);

        // your app logic
        const response = new Response("ok", { status: 200 });

        return sdk.sendResponse(response);
     },
  };
  ```
- Trace upstream calls (HTTP client propagation)
  If your Worker calls an external API, use `sdk.fetch(...)` to propagate context automatically:

  ```js
        const sdk = track(request, ctx);
  const url = new URL(request.url);
  const upstream = await sdk.fetch(`https://httpbin.org${url.pathname}`);
  return sdk.sendResponse(upstream);
  ```

## 4. Custom logs (optional)

Emit structured logs correlated with the current trace:

```bash
   // sdk.logger.SEVERITY(message, attributes?)
sdk.logger.error("error test");
sdk.logger.error("error with attributes", { "log.file.name": "error.log" });
sdk.logger.info("info test");
sdk.logger.debug("debug test");
sdk.logger.warn("warn test");
```

## 5. Configure secrets & env (Wrangler)

Use Wrangler vars/secrets to avoid hardcoding keys:

- wrangler.toml

  ```js
     name = "my-worker"
     main = "src/index.ts"
     compatibility_date = "2024-12-01"

     [vars]
     SERVICE_NAME = "orders-worker"
     MW_TARGET = "https://<ACCOUNT-UID>.middleware.io"

     # Per-environment overrides
     [env.staging.vars]
     SERVICE_NAME = "orders-worker-staging"

     [env.production.vars]
     SERVICE_NAME = "orders-worker"
  ```
- Set your API key as a secret:

  ```js
     wrangler secret put MW_API_KEY
     # optionally per-env:
     wrangler secret put MW_API_KEY --env production
  ```
- Then read from `env` in your Worker:

  ```js
     init({
     serviceName: env.SERVICE_NAME,
     accountKey: env.MW_API_KEY, // bound secret
     target: env.MW_TARGET,
     consoleLogEnabled: false,
  });
  ```

## 6. View your data

After deployment, give it 3–5 minutes, then open Middleware to see:

- Traces (incoming Worker requests, plus any upstream calls done via `sdk.fetch`)
- Logs (from `sdk.logger.*`)
- Profiling is not yet available for Cloudflare Workers in Middleware.

## 7. Environment variables

| Key | Where | Purpose | Example |
| --- | --- | --- | --- |
| `SERVICE_NAME` | Wrangler `vars` | Logical service name for APM | `orders-worker` |
| `MW_API_KEY` | Wrangler `secret` | Auth token for Middleware | (secret) |
| `MW_TARGET` | Wrangler `vars` | Ingest endpoint (serverless) | `https://{ACCOUNT-UID}.middleware.io` |
| `consoleLogEnabled` | `init` option | Print instrumented logs to console | `false / true` |

(Names/usage align with the Middleware Worker agent options.) ([docs.middleware.io](https://docs.middleware.io/get-started/apm/cloudflare), [npm](https://www.npmjs.com/package/%40middleware.io/agent-apm-worker?activeTab=readme))

## 8. Troubleshooting

- No traces/logs:

  - Confirm `init(...)` is called and `track(request, ctx)` wraps every request.
  - Check that `accountKey/target` are set (or bound via env).
- Upstream service not showing as a child span:

  - Use `sdk.fetch(...)` instead of `fetch(...)` to propagate context.
- Local dev secrets:

  - Use `wrangler secret put` for real secrets and `.dev.vars` for local-only values.
- Multiple environments:

  - Define `vars` per environment in `wrangler.toml` (`[env.staging]`, `[env.production]`).

Need assistance or want to learn more about Middleware? Get in touch with us via our Contact Us page or join our Slack channel.
