metis-desk/apps/server/src/printers.integration.ts

174 lines
6.7 KiB
TypeScript

import assert from "node:assert/strict";
import { randomUUID } from "node:crypto";
import { CatalogResponseSchema, InventoryResponseSchema } from "@metis/assets/common";
import type { PrinterConfigurationInput } from "@metis/companies/common";
import {
CompanyResponseSchema,
PrinterConfigurationResponseSchema,
PrinterConfigurationsResponseSchema,
WorkProfileResponseSchema,
} from "@metis/companies/common";
import type { Sequelize } from "sequelize";
import { z } from "zod/v4";
type Request = (path: string, body?: unknown, origin?: string, token?: string) => Promise<Response>;
export async function verifyPrinters(
request: Request,
companyId: string,
otherId: string,
database: Sequelize
) {
const personResponse = await request(`/companies/${companyId}/people`, {
name: "Persona prueba impresoras",
position: null,
email: null,
phone: null,
active: true,
isContact: false,
});
assert.equal(personResponse.status, 201);
const person = CompanyResponseSchema.parse(await personResponse.json()).company.people.at(-1);
assert.ok(person);
const inventory = InventoryResponseSchema.parse(
await (await request(`/assets/${companyId}`)).json()
);
const host = inventory.assets.find((item) => item.values.status !== "retired");
assert.ok(host);
const catalog = CatalogResponseSchema.parse(
await (await request(`/asset-catalog/${companyId}`)).json()
);
const template = catalog.items.find(
(item) =>
item.values.kind === "template" && item.values.name === "Impresora" && item.effectiveActive
);
assert.ok(template);
const addPrinter = async (name: string) => {
const response = await request(`/assets/${companyId}`, {
values: {
name,
templateId: template.id,
status: "available",
siteId: null,
personId: null,
notes: "",
characteristics: {},
},
});
assert.equal(response.status, 201);
const current = InventoryResponseSchema.parse(
await (await request(`/assets/${companyId}`)).json()
).assets.find((item) => item.values.name === name);
assert.ok(current);
return current;
};
const first = await addPrinter("Impresora prueba USB");
const second = await addPrinter("Impresora prueba red");
const profileValues = {
name: "Perfil impresoras",
personId: person.id,
assetId: host.id,
accountId: null,
active: true,
notes: null,
};
const profileResponse = await request(`/work-profiles/${companyId}`, { values: profileValues });
assert.equal(profileResponse.status, 201);
const profile = WorkProfileResponseSchema.parse(await profileResponse.json()).profile;
const path = `/printer-configurations/${companyId}`;
const input: PrinterConfigurationInput = {
profileId: profile.id,
printerId: first.id,
connection: "usb",
isDefault: true,
state: "configured",
notes: null,
};
const save = async (values: PrinterConfigurationInput, id?: string) => {
const response = await request(path + (id ? `/${id}/update` : ""), { values });
assert.equal(response.status, id ? 200 : 201);
return PrinterConfigurationResponseSchema.parse(await response.json()).configuration;
};
const error = async (values: unknown, code: string, id?: string, status = 409) => {
const response = await request(path + (id ? `/${id}/update` : ""), { values });
assert.equal(response.status, status);
assert.equal(z.object({ code: z.string() }).parse(await response.json()).code, code);
};
await error({ ...input, actorId: person.id }, "INVALID_REQUEST", undefined, 400);
await error({ ...input, printerId: randomUUID() }, "PRINTER_REFERENCE_NOT_FOUND", undefined, 404);
await error({ ...input, printerId: host.id }, "PRINTER_REFERENCE_NOT_FOUND", undefined, 404);
assert.equal((await request(path, { values: input }, "https://other.example")).status, 403);
assert.equal((await request(path, { values: input }, undefined, "a".repeat(64))).status, 403);
const attempts = await Promise.all([
request(path, { values: input }),
request(path, { values: input }),
]);
assert.deepEqual(attempts.map((response) => response.status).sort(), [201, 409]);
const successful = attempts.find((response) => response.status === 201);
assert.ok(successful);
const created = PrinterConfigurationResponseSchema.parse(await successful.json()).configuration;
assert.equal(created.id[14], "7");
assert.equal(created.history[0]?.id[14], "7");
assert.ok(created.history[0]?.actorName);
assert.deepEqual(await save(input, created.id), created);
await error({ ...input, printerId: second.id }, "DEFAULT_PRINTER_EXISTS");
const network = await save({
...input,
printerId: second.id,
connection: "network",
isDefault: false,
state: "pending",
});
await error({ ...input, printerId: second.id }, "PRINTER_TARGET_IMMUTABLE", created.id);
await error(
{ ...input, state: "removed", isDefault: false },
"INVALID_PRINTER_TRANSITION",
created.id
);
await database.query("UPDATE printer_configurations SET defaultKey=NULL WHERE id=:id", {
replacements: { id: created.id },
});
try {
assert.equal((await request(path)).status, 500);
} finally {
await database.query("UPDATE printer_configurations SET defaultKey=:key WHERE id=:id", {
replacements: { id: created.id, key: profile.id },
});
}
const archive = await request(`/work-profiles/${companyId}/${profile.id}/update`, {
values: { ...profileValues, active: false },
});
assert.equal(archive.status, 200);
const reviewed = PrinterConfigurationsResponseSchema.parse(
await (await request(path)).json()
).configurations;
assert.equal(reviewed.find((item) => item.id === created.id)?.needsReview, true);
await error(
{ ...network.values, state: "configured" },
"PRINTER_REFERENCE_UNAVAILABLE",
network.id
);
const noted = await save({ ...created.values, notes: "Retirar tras salida" }, created.id);
assert.equal(noted.history.length, 2);
assert.equal(noted.history[0]?.values.notes, null);
const removal = await save(
{ ...noted.values, state: "removal_pending", isDefault: false },
created.id
);
assert.equal(removal.needsReview, true);
const removed = await save({ ...removal.values, state: "removed" }, created.id);
assert.equal(removed.needsReview, false);
await error({ ...removed.values, notes: "Otro" }, "INVALID_PRINTER_TRANSITION", created.id);
assert.equal(
(await request(`/printer-configurations/${otherId}/${created.id}/update`, { values: input }))
.status,
404
);
assert.equal(
PrinterConfigurationsResponseSchema.parse(
await (await request(`/printer-configurations/${otherId}`)).json()
).configurations.length,
0
);
}