Initial local backup snapshot

This commit is contained in:
Selecta Keke 2026-06-24 00:02:55 -03:00
commit acd9e14ba5
367 changed files with 118038 additions and 0 deletions

161
server/logisticsSettings.ts Normal file
View file

@ -0,0 +1,161 @@
import * as db from "./db";
import {
materialEventInventory,
materialEventItems,
materialEventReplacementValues,
type MaterialEventItemKey,
} from "@shared/materialEvent";
export const LOGISTICS_SETTINGS_KEY = "system.logistics.settings";
export type LogisticsSettings = {
materialReturnLeadDays: number;
materialReturnGraceDays: number;
inventory: Record<MaterialEventItemKey, number | null>;
replacementValues: Record<MaterialEventItemKey, number | null>;
updatedAt: string | null;
};
export const defaultLogisticsSettings: Omit<LogisticsSettings, "updatedAt"> = {
materialReturnLeadDays: 4,
materialReturnGraceDays: 3,
inventory: {
...materialEventInventory,
},
replacementValues: {
...materialEventReplacementValues,
},
};
function clampWholeNumber(value: unknown, fallback: number, min: number, max: number) {
const parsed = Number.parseInt(String(value ?? ""), 10);
if (!Number.isFinite(parsed)) return fallback;
return Math.min(max, Math.max(min, parsed));
}
function sanitizeInventory(rawInventory: unknown) {
const nextInventory = { ...defaultLogisticsSettings.inventory } as Record<MaterialEventItemKey, number | null>;
if (!rawInventory || typeof rawInventory !== "object") {
return nextInventory;
}
for (const item of materialEventItems) {
const rawValue = (rawInventory as Record<string, unknown>)[item.key];
if (rawValue === null || rawValue === "") {
nextInventory[item.key] = null;
continue;
}
const parsed = Number.parseInt(String(rawValue ?? ""), 10);
if (Number.isFinite(parsed) && parsed >= 0) {
nextInventory[item.key] = parsed;
}
}
return nextInventory;
}
function sanitizeReplacementValues(rawReplacementValues: unknown) {
const nextReplacementValues = {
...defaultLogisticsSettings.replacementValues,
} as Record<MaterialEventItemKey, number | null>;
if (!rawReplacementValues || typeof rawReplacementValues !== "object") {
return nextReplacementValues;
}
for (const item of materialEventItems) {
const rawValue = (rawReplacementValues as Record<string, unknown>)[item.key];
if (rawValue === null || rawValue === "") {
nextReplacementValues[item.key] = null;
continue;
}
const parsed = Number.parseInt(String(rawValue ?? ""), 10);
if (Number.isFinite(parsed) && parsed >= 0) {
nextReplacementValues[item.key] = parsed;
}
}
return nextReplacementValues;
}
function sanitizeLogisticsSettings(rawValue: unknown, updatedAt: string | null): LogisticsSettings {
const source = rawValue && typeof rawValue === "object" ? rawValue as Record<string, unknown> : {};
return {
materialReturnLeadDays: clampWholeNumber(
source.materialReturnLeadDays,
defaultLogisticsSettings.materialReturnLeadDays,
1,
30
),
materialReturnGraceDays: clampWholeNumber(
source.materialReturnGraceDays,
defaultLogisticsSettings.materialReturnGraceDays,
0,
30
),
inventory: sanitizeInventory(source.inventory),
replacementValues: sanitizeReplacementValues(source.replacementValues),
updatedAt,
};
}
export async function getLogisticsSettings(): Promise<LogisticsSettings> {
const record = await db.getPortalSettingRecord(LOGISTICS_SETTINGS_KEY);
if (!record?.valeur) {
return {
...defaultLogisticsSettings,
updatedAt: null,
};
}
try {
const parsed = JSON.parse(record.valeur);
return sanitizeLogisticsSettings(parsed, record.updatedAt?.toISOString?.() || null);
} catch {
return {
...defaultLogisticsSettings,
updatedAt: record.updatedAt?.toISOString?.() || null,
};
}
}
export async function saveLogisticsSettings(input: {
materialReturnLeadDays?: number;
materialReturnGraceDays?: number;
inventory?: Partial<Record<MaterialEventItemKey, number | null>>;
replacementValues?: Partial<Record<MaterialEventItemKey, number | null>>;
}) {
const current = await getLogisticsSettings();
const next = sanitizeLogisticsSettings(
{
materialReturnLeadDays: input.materialReturnLeadDays ?? current.materialReturnLeadDays,
materialReturnGraceDays: input.materialReturnGraceDays ?? current.materialReturnGraceDays,
inventory: {
...current.inventory,
...(input.inventory || {}),
},
replacementValues: {
...current.replacementValues,
...(input.replacementValues || {}),
},
},
new Date().toISOString()
);
await db.setPortalSetting(
LOGISTICS_SETTINGS_KEY,
JSON.stringify({
materialReturnLeadDays: next.materialReturnLeadDays,
materialReturnGraceDays: next.materialReturnGraceDays,
inventory: next.inventory,
replacementValues: next.replacementValues,
}),
"Réglages logistiques globaux du portail"
);
return getLogisticsSettings();
}