Proxy DataFast with Astro

Learn how to proxy DataFast analytics through your Astro application using middleware to bypass adblockers and improve accuracy.

1. Create Middleware File

Create a middleware file at src/middleware.js (or src/middleware.ts for TypeScript):

// src/middleware.js
export async function onRequest(context, next) {
  const { request } = context;
  const url = new URL(request.url);

  // Proxy the DataFast script
  if (url.pathname === '/js/script.js') {
    const response = await fetch('https://datafa.st/js/script.js');
    const script = await response.text();
    
    return new Response(script, {
      headers: {
        'Content-Type': 'application/javascript',
        'Cache-Control': 'public, max-age=31536000',
      },
    });
  }

  // Proxy the events endpoint
  if (url.pathname === '/api/events' && request.method === 'POST') {
    const body = await request.text();
    
    const response = await fetch('https://datafa.st/api/events', {
      method: 'POST',
      headers: {
        'Content-Type': 'application/json',
        'User-Agent': request.headers.get('User-Agent') || '',
      },
      body: body,
    });
    
    const responseText = await response.text();
    
    return new Response(responseText, {
      status: response.status,
      headers: {
        'Content-Type': 'application/json',
      },
    });
  }

  return next();
}

2. Configure Astro for Server Output

Update your astro.config.mjs to enable server-side rendering (required for middleware):

// astro.config.mjs
import { defineConfig } from 'astro/config';
import node from '@astrojs/node';

export default defineConfig({
  output: 'server', // or 'hybrid'
  adapter: node({
    mode: 'standalone'
  }),
});

You'll need to install the Node.js adapter: npm install @astrojs/node

3. Alternative: Static Site with API Routes

If you prefer to keep your site static, you can create API routes instead:

Create Script Proxy Route

Create src/pages/js/script.js.js:

// src/pages/js/script.js.js
export async function GET() {
  const response = await fetch('https://datafa.st/js/script.js');
  const script = await response.text();
  
  return new Response(script, {
    headers: {
      'Content-Type': 'application/javascript',
      'Cache-Control': 'public, max-age=31536000',
    },
  });
}

Create Events Proxy Route

Create src/pages/api/events.js:

// src/pages/api/events.js
export async function POST({ request }) {
  const body = await request.text();
  
  const response = await fetch('https://datafa.st/api/events', {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
      'User-Agent': request.headers.get('User-Agent') || '',
    },
    body: body,
  });
  
  const responseText = await response.text();
  
  return new Response(responseText, {
    status: response.status,
    headers: {
      'Content-Type': 'application/json',
    },
  });
}

4. Update Your Script Tag

Replace your existing DataFast script with the proxied version in your layout:

---
// src/layouts/Layout.astro
const { title } = Astro.props;
---

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width" />
    <title>{title}</title>
    <script
      defer
      data-website-id="yourwebsiteid"
      data-domain="yourdomain.com"
      src="/js/script.js"
    ></script>
  </head>
  <body>
    <slot />
  </body>
</html>

5. Deploy Your Site

The proxy configuration will take effect automatically after deployment. Make sure your hosting provider supports:

  • Server-side rendering (for middleware approach)
  • API routes (for static site approach)

Popular Astro-compatible hosts include Vercel, Netlify, and Cloudflare Pages.

Verification

To verify the proxy is working:

  1. Visit your website
  2. Open the network tab in your browser's developer tools
  3. Check that analytics requests are going through your domain instead of datafa.st

Note: The middleware approach requires server-side rendering, while API routes work with both static and server-rendered sites.

Something missing? Suggest features ✍️