Files
guilan-ace-frontend/tests/event-catalog.test.mjs

152 lines
4.7 KiB
JavaScript

import assert from "node:assert/strict";
import test from "node:test";
import {
EVENT_PAGE_SIZE,
getEventLocationLabel,
getPriceCeiling,
parseEventCatalogParams,
serializeEventCatalogParams,
} from "../src/lib/event-catalog.ts";
import {
getEventBrowseLabel,
getEventRegistrationMessage,
} from "../src/lib/event-ui.ts";
const now = Date.parse("2026-09-30T12:00:00.000Z");
function event(overrides = {}) {
return {
status: "published",
event_type: "on_site",
address: "",
location: null,
start_time: "2026-10-01T12:00:00.000Z",
end_time: "2026-10-01T14:00:00.000Z",
registration_start_date: "2026-09-29T12:00:00.000Z",
registration_end_date: "2026-10-01T12:00:00.000Z",
capacity: 20,
registration_count: 8,
...overrides,
};
}
test("uses the agreed Persian status labels for completed, open, and upcoming events", () => {
assert.equal(getEventBrowseLabel(event({ status: "completed" }), now), "برگزار شده");
assert.equal(getEventBrowseLabel(event(), now), "درحال برگزاری");
assert.equal(
getEventBrowseLabel(event({ registration_start_date: "2026-10-01T12:00:00.000Z" }), now),
"به‌زودی",
);
assert.equal(
getEventBrowseLabel(event({ capacity: 8 }), now),
"به‌زودی",
);
});
test("uses a distinct registration message for not started, closed, full, and completed events", () => {
assert.equal(
getEventRegistrationMessage(event({ registration_start_date: "2026-10-01T12:00:00.000Z" }), now),
"ثبت‌نام هنوز آغاز نشده است",
);
assert.equal(
getEventRegistrationMessage(event({ registration_end_date: "2026-09-29T11:59:00.000Z" }), now),
"زمان ثبت‌نام به پایان رسیده است",
);
assert.equal(
getEventRegistrationMessage(event({ capacity: 8 }), now),
"ظرفیت ثبت‌نام تکمیل شده است",
);
assert.equal(
getEventRegistrationMessage(event({ status: "completed" }), now),
"این رویداد برگزار شده است",
);
});
test("rounds the global price maximum up to the next complete million", () => {
assert.equal(getPriceCeiling(650000), 1000000);
assert.equal(getPriceCeiling(4300000), 5000000);
assert.equal(getPriceCeiling(5000000), 5000000);
assert.equal(getPriceCeiling(0), 0);
});
test("always provides a location label and applies the requested fallbacks", () => {
assert.equal(getEventLocationLabel(event({ event_type: "online" })), "برگزاری آنلاین");
assert.equal(getEventLocationLabel(event({ event_type: "online", address: "گوگلمیت" })), "برگزاری آنلاین");
assert.equal(getEventLocationLabel(event()), "محل برگزاری اعلام نشده");
assert.equal(getEventLocationLabel(event({ address: "ساختمان دانشکده" })), "ساختمان دانشکده");
});
test("round-trips shareable catalog filters and defaults to 12 items per page", () => {
const filters = parseEventCatalogParams(new URLSearchParams(
"search=برنامه%20نویسی&state=upcoming&event_type=hybrid&date_from=2026-09-20&date_to=2026-09-30&price_min=100000&price_max=500000&page=3",
), 1000000);
assert.deepEqual(filters, {
search: "برنامه نویسی",
state: "upcoming",
eventType: "hybrid",
dateFrom: "2026-09-20",
dateTo: "2026-09-30",
priceMin: 100000,
priceMax: 500000,
freeOnly: false,
page: 3,
});
assert.deepEqual(
parseEventCatalogParams(serializeEventCatalogParams(filters, 1000000), 1000000),
filters,
);
assert.equal(
serializeEventCatalogParams({
search: "",
state: "all",
eventType: "all",
dateFrom: "",
dateTo: "",
priceMin: 0,
priceMax: 1000000,
freeOnly: false,
page: 1,
}, 1000000).toString(),
"",
);
assert.equal(EVENT_PAGE_SIZE, 12);
});
test("omits price bounds from the URL when free-only is enabled", () => {
const params = serializeEventCatalogParams({
search: "",
state: "upcoming",
eventType: "all",
dateFrom: "",
dateTo: "",
priceMin: 350000,
priceMax: 1000000,
freeOnly: true,
page: 1,
}, 1000000);
assert.equal(params.get("free_only"), "true");
assert.equal(params.has("price_min"), false);
assert.equal(params.has("price_max"), false);
});
test("ignores invalid or reversed query values and uses safe catalog defaults", () => {
assert.deepEqual(
parseEventCatalogParams(new URLSearchParams(
"state=unknown&event_type=other&date_from=2026-10-02&date_to=2026-10-01&price_min=-1&price_max=nope&page=0",
), 500000),
{
search: "",
state: "all",
eventType: "all",
dateFrom: "",
dateTo: "",
priceMin: 0,
priceMax: 500000,
freeOnly: false,
page: 1,
},
);
});