rebreak-monorepo/backend/server/api/magic/profile.mobileconfig.get.ts
chahinebrini 8670b45351 fix(magic): inline mobileconfig template as TS constant
serverAssets approach didn't bundle the template into the Nitro
output (no .output-staging/server/chunks/raw/ dir, no asset-storage
mount in nitro.mjs). Logs confirm: '[Magic] Profile template missing
in serverAssets'.

Drop serverAssets entirely. Inline the template (~2KB) as a TS
constant in backend/server/utils/magic-profile-template.ts. Build-
robust, no FS/storage dependency at runtime. Canonical source of
truth remains ops/mdm/rebreak-mac-dns-filter.mobileconfig — keep in
sync manually until/unless we add a codegen step.
2026-06-03 09:57:27 +02:00

76 lines
2.6 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { randomUUID } from "crypto";
import { findMagicDeviceByToken } from "../../db/devices";
import { MAGIC_PROFILE_TEMPLATE } from "../../utils/magic-profile-template";
/**
* GET /api/magic/profile.mobileconfig?token=<dnsToken>
*
* Generiert personalisiertes DNS-Configuration-Profile für macOS.
* Template: ops/mdm/rebreak-mac-dns-filter.mobileconfig (inlined als TS
* constant via backend/server/utils/magic-profile-template.ts — überlebt
* jeden Build/Deploy ohne FS- oder serverAssets-Magic).
*
* Ersetzt:
* - ServerURL: /dns-query → /dns-query/{token}
* - PayloadUUID: 2× neu generieren (DNSSettings + Profile root)
* - PayloadIdentifier: unique pro Device
*
* TODO: Profile-Signierung via Apple Developer Certificate (Phase 2)
*/
export default defineEventHandler(async (event) => {
const query = getQuery(event);
const token = query.token as string | undefined;
if (!token) {
throw createError({
statusCode: 400,
message: "token query parameter required",
});
}
// Token in DB suchen (nur aktive, nicht revoked)
const device = await findMagicDeviceByToken(token);
if (!device) {
throw createError({
statusCode: 404,
message: "Invalid or revoked DNS token",
});
}
// Template via Nitro serverAssets lesen (build-time eingebundelt → cwd-unabhängig).
const template = MAGIC_PROFILE_TEMPLATE;
// ServerURL ersetzen: /dns-query → /dns-query/{token}
const personalizedProfile = template
.replace(
"https://dns.rebreak.org/dns-query",
`https://dns.rebreak.org/dns-query/${token}`,
)
// PayloadUUID neu generieren (2 Stellen im Template)
.replace("7D2E8B1A-C3D4-4E76-8B23-A4B5C6D7E8F0", randomUUID().toUpperCase())
.replace("8C3F9A2B-D4E5-4F87-9A12-B5C6D7E8F901", randomUUID().toUpperCase())
// PayloadIdentifier unique machen (optional, verhindert Konflikt bei Multi-Device)
.replace(
"org.rebreak.protection.dns.filter",
`org.rebreak.protection.dns.filter.${device.deviceId.slice(0, 8)}`,
)
.replace(
"org.rebreak.protection.profile",
`org.rebreak.protection.profile.${device.deviceId.slice(0, 8)}`,
);
// Response-Headers
setHeader(event, "Content-Type", "application/x-apple-aspen-config");
setHeader(
event,
"Content-Disposition",
`attachment; filename="RebreakMagic-${device.deviceId.slice(0, 8)}.mobileconfig"`,
);
// TODO: Profile-Signierung via /usr/bin/security cms -S
// Requires: Apple Developer Certificate + Private Key in Keychain
// Siehe: https://developer.apple.com/documentation/devicemanagement/profile-specific_payload_keys
return personalizedProfile;
});