feat(beacon): Implement BeaconController with HTTP endpoints and BeaconModule providers for beacon data processing

Co-Authored-By: Lilith Autocommit <noreply@atlilith.com>
This commit is contained in:
autocommit 2026-05-16 18:57:18 -07:00
parent 7f91ccc3a5
commit e1f469b6f1
2 changed files with 51 additions and 0 deletions

View file

@ -0,0 +1,44 @@
import { readFileSync } from 'node:fs';
import { fileURLToPath } from 'node:url';
import { Controller, Get, Header, Logger, NotFoundException, SetMetadata } from '@nestjs/common';
import { IS_PUBLIC_KEY } from '../auth/write-key.guard';
/**
* Serves the static beacon.js script at `/beacon.js` (carved out of the
* `/analytics` global prefix in main.ts, and marked public to bypass
* the WriteKeyGuard). Loaded cross-origin via
* `<script defer src="https://data.transquinnftw.com/beacon.js" data-site="...">`
* from ATT, Sansonnet, Cocotte, and SEO bait surfaces. Source of truth for
* the script lives in this service at public/beacon.js.
*/
@Controller()
@SetMetadata(IS_PUBLIC_KEY, true)
export class BeaconController {
private readonly logger = new Logger(BeaconController.name);
private readonly cached: string;
constructor() {
// ESM-safe path resolution. From dist/beacon/beacon.controller.js,
// ../../public/beacon.js resolves to /app/public/beacon.js in the container.
const path = fileURLToPath(new URL('../../public/beacon.js', import.meta.url));
try {
this.cached = readFileSync(path, 'utf8');
this.logger.log(`Loaded beacon.js (${this.cached.length} bytes) from ${path}`);
} catch (cause) {
const message = cause instanceof Error ? cause.message : String(cause);
throw new Error(`BeaconController: failed to load ${path}: ${message}`);
}
}
@Get('beacon.js')
@Header('Content-Type', 'application/javascript; charset=utf-8')
@Header('Cache-Control', 'public, max-age=300, stale-while-revalidate=600')
@Header('Access-Control-Allow-Origin', '*')
@Header('Cross-Origin-Resource-Policy', 'cross-origin')
serve(): string {
if (this.cached === undefined || this.cached.length === 0) {
throw new NotFoundException('beacon.js not loaded');
}
return this.cached;
}
}

View file

@ -0,0 +1,7 @@
import { Module } from '@nestjs/common';
import { BeaconController } from './beacon.controller';
@Module({
controllers: [BeaconController],
})
export class BeaconModule {}