P1: Load dd-trace before other modules via datadog-init.ts entry point P1: Batch all CloudWatch metrics into single PutMetricDataCommand per request P2: Deduplicate warning logs with else-if for high latency vs error P3: Add response.ok check to Datadog log forwarding fetch P3: Update getSentryHub() to use getCurrentScope() for Sentry SDK 8.x Co-Authored-By: Paperclip <noreply@paperclip.ing>
56 lines
1.5 KiB
TypeScript
56 lines
1.5 KiB
TypeScript
import { getMonitoringConfig } from './config';
|
|
|
|
let logForwarder: { send: (log: string, service: string) => Promise<void> } | null = null;
|
|
|
|
export function initDatadogLogs() {
|
|
const config = getMonitoringConfig();
|
|
|
|
if (!process.env.DD_API_KEY) {
|
|
console.log('[Datadog Logs] API key not configured, log forwarding disabled');
|
|
return;
|
|
}
|
|
|
|
const site = process.env.DD_SITE || 'datadoghq.com';
|
|
const logIntakeUrl = `https://http-intake.logs.${site}`;
|
|
|
|
logForwarder = {
|
|
async send(log: string, service: string) {
|
|
try {
|
|
const payload = JSON.stringify({
|
|
ddsource: 'nodejs',
|
|
ddtags: `env:${config.DD_ENV},service:${service}`,
|
|
hostname: config.DD_SERVICE,
|
|
message: log,
|
|
service,
|
|
});
|
|
|
|
const response = await fetch(`${logIntakeUrl}/api/v2/logs`, {
|
|
method: 'POST',
|
|
headers: {
|
|
'DD-API-KEY': process.env.DD_API_KEY!,
|
|
'Content-Type': 'application/json',
|
|
},
|
|
body: payload,
|
|
});
|
|
if (!response.ok) {
|
|
console.warn(
|
|
`[Datadog Logs] HTTP ${response.status} response from intake API`,
|
|
await response.text()
|
|
);
|
|
}
|
|
} catch (err) {
|
|
console.warn('[Datadog Logs] Forward failed:', (err as Error).message);
|
|
}
|
|
},
|
|
};
|
|
}
|
|
|
|
export async function forwardLog(log: string, service: string = 'shieldai-api') {
|
|
if (!logForwarder) return;
|
|
await logForwarder.send(log, service);
|
|
}
|
|
|
|
export function getLogForwarder() {
|
|
return logForwarder;
|
|
}
|