← Back to API Hub DEPLOY-GUIDE-2026-01

1 Project Structure

All files are static HTML/CSS/JS. There is no build step — the root folder is deployed directly.

Kids Vaccination/ # → project root (deployed as-is) ├── index.html # Landing hub — lists all published APIs ├── wrangler.toml # Cloudflare Pages project config ├── .cfignore # Files excluded from CF deployment ├── .env # Local credentials (never committed) ├── package.json # npm scripts: serve, test, deploy │ ├── apis/ │ └── kids-vaccination/ # One folder per API │ ├── index.html # API reference document │ └── assets/ │ ├── api-samples.md # Editable request/response samples │ └── sanar-logo.png │ ├── deploy/ │ ├── deploy.sh # Deployment shell script │ └── guide.html # This document │ └── tests/ └── smoke.spec.js # Playwright smoke tests

2 Local Development

Serve the project locally before making any deployment. This also enables full rendering of API samples (fetch requires HTTP, not file://).

Start the local server

cd "Kids Vaccination"
npm run serve
# → Serving at http://127.0.0.1:4173

Or serve directly

serve . -l 4173
Always use the local server URL (http://127.0.0.1:4173), not file:// paths. The file:// protocol blocks fetch() calls needed to render API samples.

3 Environment Setup

Create a .env file at the project root with the following variables. This file is listed in .cfignore and must never be committed.

Variable Description Where to get it
CLOUDFLARE_ACCOUNT_ID Your Cloudflare account identifier Cloudflare Dashboard → right sidebar on home page
CLOUDFLARE_API_TOKEN API token with Cloudflare Pages: Edit permission My Profile → API Tokens → Create Token

Example .env

CLOUDFLARE_ACCOUNT_ID=your_account_id_here
CLOUDFLARE_API_TOKEN=your_token_here
The API token must have the Cloudflare Pages: Edit permission. Without it, wrangler will return a code 10000 authentication error.

4 Deploy to Production

Deploys the entire project root to the main branch of the Cloudflare Pages project, making changes live at the production URL.

Using npm script (recommended)

npm run deploy

Using the deploy script directly

bash deploy/deploy.sh

Manual wrangler command

source .env
npx wrangler pages deploy . \
  --project-name sanar-api-docs \
  --branch main
Production URL: https://sanar-api-docs.pages.dev
Wrangler also outputs a unique hash deployment URL (e.g. b5448ecb.sanar-api-docs.pages.dev). Use the stable URL for sharing.

5 Deploy Preview

Creates a preview deployment on a separate branch. Does not affect the production URL.

npm run deploy:preview
# or
bash deploy/deploy.sh --preview

6 Adding a New API

Follow this structure every time a new API is published. Consistency ensures the hub search and card layout work without any JS changes.

  1. 01
    Create a new folder under apis/ using a lowercase, hyphenated slug — e.g. apis/lab-results/
  2. 02
    Copy apis/kids-vaccination/index.html as a starting template. Update the title, hero text, endpoint table, auth table, and flow steps.
  3. 03
    Create apis/{slug}/assets/api-samples.md with request and response examples. The page renders this file automatically.
  4. 04
    Add the logo and any source PDFs to apis/{slug}/assets/.
  5. 05
    Add a new <article class="card" data-keywords="..."> block to index.html pointing to href="apis/{slug}/" (trailing slash required).
  6. 06
    Update the stat box on index.html from "1 Published API" to the new count.
  7. 07
    Run locally to verify, then deploy.

Card template

<article class="card" data-keywords="[keywords here]">
  <div class="card-top">
    <span class="tag">[Category / Sub-category]</span>
    <span class="status">LIVE</span>
  </div>
  <h4>[API Name]</h4>
  <p>[One-sentence description of the integration flow.]</p>
  <ul class="meta-list">
    <li><strong>Version:</strong> v1</li>
    <li><strong>Endpoints:</strong> N</li>
    <li><strong>Auth:</strong> [auth type]</li>
    <li><strong>Protocol:</strong> REST / JSON</li>
  </ul>
  <div class="card-actions">
    <a class="btn primary" href="apis/[slug]/">Open API Document</a>
    <a class="btn" href="apis/[slug]/source/[name].pdf">Open Original PDF</a>
  </div>
</article>

7 Updating API Samples

Request and response examples are stored as plain text in each API's assets/api-samples.md. You do not need to touch the HTML file to update them.

Format rules

  1. ##
    Section heading — becomes a titled block. Example: ## Endpoint 01 — POST /services
  2. ###
    Sub-label within a block. Example: ### Request or ### Response
  3. ```
    Opening and closing triple backticks wrap a JSON code block. Syntax highlighting is applied automatically.

Example entry

## Endpoint 01 — POST /services

### Request

```
{
  "prd_id": "ST043"
}
```

### Response

```
{
  "status": 1000,
  "data": [ ... ]
}
```

8 Running Tests

Playwright smoke tests verify the hub and API doc render correctly end-to-end. The local server must be running before tests are executed.

Start server then run tests

# Terminal 1 — start server
npm run serve

# Terminal 2 — run tests (headed Chromium)
npm test

What the smoke test checks

  1. 1
    Landing page loads with "Sanar API Hub" heading visible
  2. 2
    "Published APIs" section is present
  3. 3
    Clicking "Open API Document" navigates to /apis/kids-vaccination/
  4. 4
    API doc heading "Kids Vaccination API Documentation" is visible
  5. 5
    Logo loads successfully (naturalWidth > 0)
  6. 6
    #samplesRoot is visible and .md-body is present (markdown rendered)
  7. 7
    No error text is shown on the page

9 Troubleshooting

API samples not rendering

Cause: page was opened via file:// instead of HTTP. Fix: run npm run serve and open http://127.0.0.1:4173.

Deploy fails with code 10000

Cause: API token is missing the Cloudflare Pages: Edit permission. Fix: go to Cloudflare Dashboard → My Profile → API Tokens → edit the token and add that permission.

Logo shows as broken image

Cause: navigated to apis/kids-vaccination/index.html with explicit filename, causing a redirect that breaks relative asset paths. Fix: always link to apis/kids-vaccination/ with a trailing slash.

Wrangler not found

npm install -g wrangler@latest

serve not found

npm install -g serve