Skip to content

Commit 0751371

Browse files
authored
feat: add ORIGIN_URL support to template and publish (#870)
1 parent 3ba6c93 commit 0751371

File tree

11 files changed

+925
-32
lines changed

11 files changed

+925
-32
lines changed

templates.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@
7979
"package_json_hash": "9dc78284a3d5aaa5fdf89bcddda7ec0b753cf54d"
8080
},
8181
"x402-proxy-template": {
82-
"package_json_hash": "0a02b5a875619caafe0b3c84272e4285b5e167fb"
82+
"package_json_hash": "436f521fc7854bc068dc1bc151317042a3e152fb"
8383
}
8484
}
8585
}

x402-proxy-template/README.md

Lines changed: 70 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,73 @@ The proxy is configured via environment variables in `wrangler.jsonc`:
129129
| `PAYMENT_CONFIG.price` | Cost per access | `"$0.01"` |
130130
| `PAYMENT_CONFIG.network` | Blockchain network | `"base-sepolia"` (testnet) or `"base"` (mainnet) |
131131
| `PAYMENT_CONFIG.description` | What the payment grants | `"Access for 1 hour"` |
132+
| `ORIGIN_URL` | (Optional) External origin URL for proxying | `"https://origin.example.com"` |
133+
134+
#### Proxy Modes
135+
136+
The proxy supports two modes for routing requests to your backend. Choose based on your architecture:
137+
138+
##### DNS-Based Mode (Default)
139+
140+
**Best for:** Traditional backend servers (VMs, containers, other hosting providers)
141+
142+
When `ORIGIN_URL` is **not set**, requests are forwarded to the origin server defined in your Cloudflare DNS records.
143+
144+
**Setup:**
145+
146+
1. Add a DNS record in Cloudflare pointing to your origin server:
147+
- Type: `A` (for IP address) or `CNAME` (for hostname)
148+
- Name: `api` (or your subdomain)
149+
- Content: Your origin server IP or hostname
150+
- Proxy status: **Proxied** (orange cloud)
151+
152+
2. Configure a route in `wrangler.jsonc`:
153+
154+
```jsonc
155+
"routes": [
156+
{ "pattern": "api.example.com/*", "zone_name": "example.com" }
157+
]
158+
```
159+
160+
3. Deploy. The proxy will forward requests to your origin server automatically.
161+
162+
```
163+
User → api.example.com → x402 Proxy → Origin Server (via DNS)
164+
```
165+
166+
##### External Origin Mode
167+
168+
**Best for:** Another Cloudflare Worker, or any external service with a public URL
169+
170+
When `ORIGIN_URL` **is set**, requests are rewritten to that URL. This lets you proxy to another Worker on a Custom Domain or any external API.
171+
172+
**Setup:**
173+
174+
1. Set `ORIGIN_URL` in `wrangler.jsonc`:
175+
176+
```jsonc
177+
"vars": {
178+
"ORIGIN_URL": "https://my-origin-worker.example.com",
179+
// ... other vars
180+
}
181+
```
182+
183+
2. If your origin is a Worker, deploy it with a [Custom Domain](https://developers.cloudflare.com/workers/configuration/routing/custom-domains/).
184+
185+
3. Deploy the proxy. Requests are rewritten to the origin URL while preserving the original `Host` header.
186+
187+
```
188+
User → api.example.com → x402 Proxy → my-origin-worker.example.com (URL rewrite)
189+
```
190+
191+
**Why External Origin mode?** Cloudflare routes a hostname to one Worker only. You can't chain Workers on the same hostname via routing. External Origin mode solves this by rewriting the URL to a different hostname where your origin Worker lives.
192+
193+
##### Quick Comparison
194+
195+
| Mode | `ORIGIN_URL` | Origin Type | Use Case |
196+
| --------------- | ------------ | ------------------ | ------------------------------------------------- |
197+
| DNS-Based | Not set | Traditional server | Your backend is a VM, container, or external host |
198+
| External Origin | Set to URL | Worker or any URL | Your backend is another Worker or external API |
132199

133200
#### Local Development Setup
134201

@@ -322,13 +389,15 @@ curl -v http://localhost:8787/__x402/protected
322389
The worker uses a single catch-all middleware that:
323390

324391
1. **Checks path** against `PROTECTED_PATTERNS`
325-
2. **For unprotected paths**: Proxies request immediately via `fetch(c.req.raw)`
392+
2. **For unprotected paths**: Proxies request immediately to origin
326393
3. **For protected paths**:
327394
- Checks for valid JWT cookie
328395
- If no valid cookie, requires x402 payment
329396
- Issues JWT cookie on successful payment
330397
- Proxies authenticated request to origin
331398

399+
The proxy mode (DNS-based or External Origin) determines how requests reach your backend. See [Proxy Modes](#proxy-modes) for details.
400+
332401
### Configuration Examples
333402

334403
**Protect a single route:**

x402-proxy-template/TESTING.md

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -61,15 +61,11 @@ Network: Base Sepolia (testnet)
6161
6262
📤 Step 3: Sending request with payment...
6363
✅ Payment successful! Premium content received:
64-
Message: Welcome to premium content!
65-
Auth method: via payment
6664
Cookie received: Yes
6765
6866
🍪 Step 4: Testing cookie authentication...
6967
Waiting 2 seconds...
7068
✅ Cookie authentication successful!
71-
Message: Welcome to premium content!
72-
Auth method: via cookie
7369
No payment required!
7470
7571
🎉 All tests passed!
@@ -86,11 +82,11 @@ Summary:
8682

8783
## Manual Testing with curl
8884

89-
### 1. Test the public endpoint
85+
### 1. Test the health endpoint
9086

9187
```bash
92-
curl http://localhost:8787/message
93-
# Should return: "Hello Hono!"
88+
curl http://localhost:8787/__x402/health
89+
# Should return: {"status":"ok","proxy":"x402-proxy","message":"This endpoint is always public",...}
9490
```
9591

9692
### 2. Request protected endpoint without payment
@@ -141,7 +137,7 @@ curl http://localhost:8787/premium \
141137
-H "Cookie: auth_token=<your-jwt-token>"
142138
```
143139

144-
You should receive premium content without being asked for payment!
140+
You should receive the authenticated response without being asked for payment!
145141

146142
## Troubleshooting
147143

x402-proxy-template/package-lock.json

Lines changed: 3 additions & 3 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

x402-proxy-template/package.json

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,9 @@
99
"categories": [
1010
"starter"
1111
],
12+
"publish": true,
13+
"preview_image_url": "https://imagedelivery.net/wSMYJvS3Xw-n339CbDyDIA/26abc75c-56c4-4c74-ba7e-e16c10f96a00/preview",
14+
"preview_icon_url": "https://imagedelivery.net/wSMYJvS3Xw-n339CbDyDIA/9b1345c4-7bfe-4be2-89fd-80cd59985e00/public",
1215
"healthCheckPath": "/__x402/health",
1316
"bindings": {
1417
"JWT_SECRET": {

0 commit comments

Comments
 (0)