Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017eEAG8HD3mm8gsKXgk8uU8
73 lines
2.4 KiB
TypeScript
73 lines
2.4 KiB
TypeScript
import { after } from "next/server";
|
|
|
|
/**
|
|
* After a chart is saved, ask the engine to cache today's full-data packet.
|
|
* The save response does not wait for that build (TASK fix F5).
|
|
*/
|
|
|
|
type WarmDeps = {
|
|
after: (task: () => Promise<void> | void) => void;
|
|
fetch: typeof fetch;
|
|
apiBase?: string;
|
|
};
|
|
|
|
function asNumber(value: unknown): number | null {
|
|
if (typeof value === "number" && Number.isFinite(value)) return value;
|
|
if (typeof value === "string" && value.trim() && Number.isFinite(Number(value))) return Number(value);
|
|
return null;
|
|
}
|
|
|
|
export function consultWarmBodyFromColumns(columns: Record<string, unknown> | null | undefined): Record<string, unknown> | null {
|
|
if (!columns) return null;
|
|
const date = typeof columns.birth_date === "string" ? columns.birth_date : "";
|
|
const time = typeof columns.reported_birth_time === "string" ? columns.reported_birth_time : "";
|
|
const lat = asNumber(columns.latitude);
|
|
const lon = asNumber(columns.longitude);
|
|
const tz = asNumber(columns.timezone_offset);
|
|
const match = /^(\d{4})-(\d{2})-(\d{2})$/.exec(date);
|
|
const clock = /^(\d{1,2}):(\d{2})/.exec(time);
|
|
if (!match || !clock || lat === null || lon === null || tz === null) return null;
|
|
return {
|
|
year: Number(match[1]),
|
|
month: Number(match[2]),
|
|
day: Number(match[3]),
|
|
hour: Number(clock[1]),
|
|
minute: Number(clock[2]),
|
|
second: 0,
|
|
lat,
|
|
lon,
|
|
tz,
|
|
ayanamsa: typeof columns.ayanamsa === "string" && columns.ayanamsa ? columns.ayanamsa : "lahiri",
|
|
node_mode: "mean",
|
|
consult_card_warm_only: true,
|
|
};
|
|
}
|
|
|
|
export function scheduleConsultPacketWarm(
|
|
columns: Record<string, unknown> | null | undefined,
|
|
deps: WarmDeps = {
|
|
after,
|
|
fetch,
|
|
apiBase: process.env.JYOTISH_API_BASE ?? "http://127.0.0.1:5200",
|
|
},
|
|
): boolean {
|
|
const body = consultWarmBodyFromColumns(columns);
|
|
if (!body) return false;
|
|
const apiBase = deps.apiBase ?? "http://127.0.0.1:5200";
|
|
// Warm is best effort. `after` throws outside a request scope; the save has
|
|
// already been written by then, so a scheduling failure must not turn it
|
|
// into a 500 (BUG-1305).
|
|
try {
|
|
deps.after(() => {
|
|
return deps.fetch(`${apiBase}/api/consultation_workflow`, {
|
|
method: "POST",
|
|
headers: { "content-type": "application/json" },
|
|
body: JSON.stringify(body),
|
|
}).then(() => undefined).catch(() => undefined);
|
|
});
|
|
} catch {
|
|
return false;
|
|
}
|
|
return true;
|
|
}
|