KI-AGENT: Ergänze Mandantenexport und Import
All checks were successful
Build and Push Docker Images / build-backend (push) Successful in 18s
Build and Push Docker Images / build-frontend (push) Successful in 51s
Build and Push Docker Images / build-docs (push) Successful in 11s

This commit is contained in:
2026-05-18 21:23:18 +02:00
parent 9c6a6a841a
commit bb3b842be1
5 changed files with 571 additions and 0 deletions

View File

@@ -15,6 +15,8 @@ import {
import { generateRandomPassword, hashPassword } from "../utils/password";
import { sendMail } from "../utils/mailer";
import { ensureTenantBaseData } from "../modules/bootstrap.service";
import { buildTenantFullExport, importTenantFullExport } from "../utils/tenantFullExport";
import type { TenantFullExport } from "../utils/tenantFullExport";
export default async function adminRoutes(server: FastifyInstance) {
const deriveNameFromEmail = (email: string) => {
@@ -929,6 +931,57 @@ export default async function adminRoutes(server: FastifyInstance) {
}
});
// -------------------------------------------------------------
// GET /admin/tenants/:tenant_id/export
// -------------------------------------------------------------
server.get("/admin/tenants/:tenant_id/export", async (req, reply) => {
try {
const currentUser = await requireAdmin(req, reply);
if (!currentUser) return;
const { tenant_id } = req.params as { tenant_id: string };
const tenantId = Number(tenant_id);
if (!tenantId) {
return reply.code(400).send({ error: "tenant_id required" });
}
const exportData = await buildTenantFullExport(server, tenantId);
const safeTenantName = String(exportData.tables.tenants?.[0]?.short || exportData.tables.tenants?.[0]?.name || tenantId)
.replace(/[^a-z0-9_-]+/gi, "-")
.replace(/^-+|-+$/g, "")
.toLowerCase();
const filename = `fedeo-tenant-${safeTenantName || tenantId}-${new Date().toISOString().slice(0, 10)}.json`;
reply.header("Content-Type", "application/json");
reply.header("Content-Disposition", `attachment; filename="${filename}"`);
return reply.send(exportData);
} catch (err) {
console.error("ERROR /admin/tenants/:tenant_id/export:", err);
return reply.code(500).send({ error: "Internal Server Error" });
}
});
// -------------------------------------------------------------
// POST /admin/tenant-imports
// -------------------------------------------------------------
server.post("/admin/tenant-imports", { bodyLimit: 1024 * 1024 * 1024 }, async (req, reply) => {
try {
const currentUser = await requireAdmin(req, reply);
if (!currentUser) return;
const exportData = req.body as TenantFullExport;
const result = await importTenantFullExport(server, exportData);
return {
success: true,
...result,
};
} catch (err: any) {
console.error("ERROR /admin/tenant-imports:", err);
return reply.code(500).send({ error: err?.message || "Internal Server Error" });
}
});
// -------------------------------------------------------------
// PUT /admin/users/:user_id/access
// -------------------------------------------------------------