This post turns the repo's actual structure into a deployment checklist you can follow directly: your company site, the homepage contact form, and inbound forwarding for your branded email addresses.

This project is not a traditional multi-page website, and it does not have a separate contact.html. The contact feature lives in the #contact section at the bottom of the homepage, so the deployed result is a single-page company site with a contact form in the footer area. If your goal is to get the site and contact entry point online quickly, this structure is actually simpler.

Project Structure and Request Flow

These are the only files in the repo that really matter for launch:

  • index.html: the homepage itself, including the contact form.
  • assets/styles/main.css: page styles.
  • assets/scripts/main.js: frontend interactions, language switching, and form submission.
  • assets/runtime-config.json: the frontend form endpoint, which defaults to /api/inquiry-email.
  • workers/inquiry-email.js: the Cloudflare Worker that receives the form submission and calls Resend.
  • wrangler.toml: the Worker name, domain routes, and environment variables.

The request flow looks like this:

Visitor opens the website
-> fills out the contact form at the bottom of the homepage
-> browser sends a request to /api/inquiry-email
-> Cloudflare Worker receives the payload
-> Worker calls Resend to send the email
-> your inbox receives the inquiry notification

Inbound company email is a separate path: when someone emails [email protected] or [email protected], that does not go through Resend. Cloudflare Email Routing forwards those messages to your personal inbox.

What You Need Before Deployment

  • A Cloudflare account.
  • A Resend account.
  • A domain you control, for example example.com.
  • A local environment where you can run npx wrangler.

If you plan to serve the site directly from the apex domain, such as https://example.com, the domain should already be fully managed in Cloudflare. You will need that for custom domains, Worker routes, and Email Routing.

If the domain is not on Cloudflare yet, do these three things first:

  1. Add the domain in the Cloudflare dashboard.
  2. Go to your domain registrar and switch the nameservers to the ones Cloudflare gives you.
  3. Wait until the domain status becomes Active.

This sounds basic, but the custom domain setup, Worker routing, and Email Routing all depend on it.

Replace the Default Project Settings with Yours

This repo is currently configured for ennota.cn. Before going live, you should replace the domain, recipient address, sender address, and site copy with your own values. Otherwise the form and routes will point to the wrong place.

Update wrangler.toml

This file decides which domain the Worker runs on, which origins may call the form API, and where the notification emails go.

name = "your-inquiry-worker"
main = "workers/inquiry-email.js"
compatibility_date = "2026-06-07"

routes = [
  { pattern = "example.com/api/*", zone_name = "example.com" },
  { pattern = "www.example.com/api/*", zone_name = "example.com" },
]

[vars]
ALLOWED_ORIGIN = "https://www.example.com,https://example.com"
RESEND_API_BASE = "https://api.resend.com"
MAIL_TO = "[email protected]"
MAIL_CC = ""
MAIL_FROM = "[email protected]"
MAIL_FROM_NAME = "Your Website"
MAIL_SUBJECT_PREFIX = "[Website Inquiry]"

These are the fields people most often get wrong:

  • routes: sends /api/* on your domain to the Worker.
  • ALLOWED_ORIGIN: the list of origins allowed to call the endpoint. If your production site uses both www and the bare domain, include both.
  • MAIL_TO: where the inquiry email should finally land.
  • MAIL_FROM: the sender address Resend uses. It must belong to a domain that has already been verified in Resend.

Both MAIL_TO and MAIL_CC support multiple email addresses separated by commas.

Check assets/runtime-config.json

The repo defaults to a same-domain setup, so the frontend submits to this path:

{
  "formEndpoint": "/api/inquiry-email"
}

That only works if both of these are true:

  • The site runs on https://example.com
  • The Worker runs on https://example.com/api/*

If that is exactly how you are deploying it, leave the file unchanged.

Only change it when the website and Worker are deployed separately. In that case, use the full URL instead:

{
  "formEndpoint": "https://your-worker.workers.dev/api/inquiry-email"
}

Where to Edit Copy and Logo

  • index.html: company name, phone number, address, and footer.
  • assets/i18n/*.json: multilingual copy.
  • assets/logo/: logo and favicon.

If your goal is to launch quickly, the bare minimum is to replace the company name, phone number, and email-related information. Otherwise the site still looks like a demo.

The Contact Form Sends Email Through Resend

The form in this repo does not send email directly from the browser. The frontend only posts JSON. The actual email is sent by workers/inquiry-email.js, which calls the Resend API.

Start by adding a sending domain in Resend. In most cases, it is better to use a subdomain dedicated to outbound mail:

This keeps your website domain and email reputation separated, which makes later troubleshooting easier.

Resend will ask you to add several DNS records. Since the domain is already on Cloudflare, add those records in Cloudflare DNS. Once the domain status becomes verified, move to the next step.

Store the Resend API key as a Worker secret:

npx wrangler secret put RESEND_API_KEY

Do not commit that key into the repo. A secret is enough.

Deploy the Form Worker First

It is worth deploying the Worker on its own first, just to confirm that the form endpoint works. Once the API is confirmed, shipping the static site is much safer.

Run this from the project root:

npx wrangler deploy

If you already replaced the routes in wrangler.toml with your own domain, you can test the endpoint like this after deployment:

curl https://example.com/api/inquiry-email

The normal response is:

{ "ok": true, "service": "inquiry-email" }

If it does not work, check these items first:

  • Is routes pointing at the domain you are actually using?
  • Is the domain managed under the current Cloudflare account?
  • Was the Worker deployed to the correct account?
  • Does ALLOWED_ORIGIN include all production origins?

Deploy the Static Site from a Clean Release Directory

The only public assets you actually need to publish from this repo are:

  • index.html
  • assets/

It is better not to point Cloudflare Pages at the repo root directly. The root also contains workers/ and wrangler.toml, and those files do not need to be public.

The safer approach is to build a dedicated release/ directory first:

mkdir -p release
cp index.html release/
cp -R assets release/

Then deploy that directory to Cloudflare Pages:

npx wrangler pages deploy release --project-name your-landing-site

After deployment, Cloudflare gives you a temporary *.pages.dev URL. Use that to verify the page and static assets before you attach the real domain.

Attach the Production Domain to Pages

In the Cloudflare dashboard, go in this order:

  1. Open Workers & Pages.
  2. Enter your Pages project.
  3. Open Custom domains.
  4. Add example.com.
  5. Add www.example.com.

If you bind the apex domain example.com, that domain must already be in the current Cloudflare account and the nameservers must already point to Cloudflare.

Cloudflare Email Routing Handles Inbound Company Mail

When people say "company email" here, what they really mean is inbound forwarding for your company domain. It is not a full office email suite, but it is usually more than enough in the early stage:

For an early-stage site, this setup is light and cheap. You do not need to run your own mail server or buy a full business email suite on day one.

Enable Email Routing

The prerequisite is still the same: the domain must already be managed in Cloudflare.

In the Cloudflare dashboard:

  1. Open your domain.
  2. Open Email Routing.
  3. Choose Add records and enable.

Cloudflare will automatically add the MX and TXT records required for Email Routing.

One common issue here is that the domain may already have MX records from another mail provider. If you want to use Cloudflare Email Routing, you cannot keep a second inbound mail system active at the same time. That is a common source of setup conflicts.

Create Public Addresses and Forward Them to Your Inbox

Then create the routing rules:

  1. Open Routing rules.
  2. Choose Create address.
  3. Create an address such as [email protected].
  4. Set the Destination address to your personal inbox, such as [email protected].
  5. Open the verification email in that inbox.
  6. Finish the verification.

Once verification is complete, any mail sent to [email protected] will be forwarded automatically to your personal mailbox.

If you are just getting the site online, these addresses are usually enough:

If the team is still small, forwarding all of them to the same inbox is perfectly fine.

There is one limitation worth knowing early: by default, Cloudflare Email Routing forwards one custom address to one destination inbox. If you want [email protected] to fan out to several people, the default rule is not enough. You would need extra Worker logic, and each destination address must be verified first.

Sending and Receiving Are Two Different Systems

When people first set this up, they often think Resend and Email Routing are the same thing. They are not. Their responsibilities are completely separate.

The contact form notification email is sent by Resend:

  • The homepage form submits to the Worker.
  • The Worker calls Resend.
  • Resend sends the inquiry notification to your inbox.

Inbound company email forwarding is handled by Cloudflare Email Routing:

  • A customer sends mail to [email protected].
  • Cloudflare receives the message.
  • Cloudflare forwards it to your personal inbox.

The short version is: Resend handles sending, Email Routing handles receiving.

Recommended Deployment Order

If you follow this order, you usually avoid unnecessary detours:

  1. Move the domain to Cloudflare and complete the nameserver switch.
  2. Verify the sending domain in Resend.
  3. Replace the domain, allowlist, recipient mailbox, and sender mailbox in wrangler.toml.
  4. Configure RESEND_API_KEY.
  5. Deploy the Worker and confirm that /api/inquiry-email responds normally.
  6. Prepare the release/ directory.
  7. Deploy the static site to Cloudflare Pages.
  8. Attach the real domain to Pages.
  9. Open the website and submit a manual test form.
  10. Enable Cloudflare Email Routing.
  11. Create addresses such as hello@ and sales@, and forward them to your personal inbox.

The advantage of this order is simple: get the API working first, ship the page second, and add inbound email last. That makes troubleshooting much clearer.

The Most Common Problems

If the page opens but the form cannot send, check these first: does ALLOWED_ORIGIN include every production domain, is RESEND_API_KEY configured, and is formEndpoint pointing to the correct URL?

If the Worker is deployed but no email ever arrives, first verify that MAIL_FROM belongs to a domain already verified in Resend, then confirm that MAIL_TO is correct. Most of the time, the code is fine and the sender domain simply has not been fully verified.

If the site works but /api/inquiry-email returns 403, the most likely cause is an origin allowlist mismatch. This happens all the time when www and the bare domain get mixed.

If Email Routing cannot be enabled at all, the usual causes are just three things: the domain is not fully managed by Cloudflare yet, the nameserver switch has not propagated, or the DNS records still contain MX entries from another provider.

If the page deploys correctly but the form is calling the wrong endpoint, go back to assets/runtime-config.json. Keep /api/inquiry-email for same-domain deployments, and only switch to a full URL when the site and Worker are deployed separately.

This Command Is Enough for a Local Preview

If you only want to preview the homepage locally, run this from the project root:

python3 -m http.server 4173

Then open:

http://127.0.0.1:4173

This is enough to review the page and copy. If you want to test the form locally as well, you still need to run the Worker and point formEndpoint to a local or test endpoint.

Short Command Checklist

# Configure the Resend API key
npx wrangler secret put RESEND_API_KEY

# Deploy the form Worker
npx wrangler deploy

# Build the static site release directory
mkdir -p release
cp index.html release/
cp -R assets release/

# Deploy the site to Cloudflare Pages
npx wrangler pages deploy release --project-name your-landing-site

Everything else happens in the Cloudflare dashboard:

  • Attach the production domain to Pages.
  • Create inbound forwarding rules in Email Routing.

This repo already has the main path for the company site and contact form in place. What remains is mostly replacing the domain, DNS, and mailbox settings with your own values, then attaching them to Cloudflare and Resend in the right order.