Files
air-watcher/test/skyscannerSampleServer.test.js
2026-02-19 17:28:58 +09:00

138 lines
3.4 KiB
JavaScript

"use strict";
const test = require("node:test");
const assert = require("node:assert/strict");
const { Readable, Writable } = require("node:stream");
const {
createSkyscannerSampleHandler,
buildSampleOffers,
} = require("../src/skyscannerSampleServer");
function createMockRequest({ method = "POST", url = "/skyscanner", body = "" } = {}) {
const req = new Readable({
read() {
this.push(body);
this.push(null);
},
});
req.method = method;
req.url = url;
return req;
}
function createMockResponse() {
const chunks = [];
let statusCode = 0;
let headers = {};
let resolveDone;
const done = new Promise((resolve) => {
resolveDone = resolve;
});
const res = new Writable({
write(chunk, _encoding, callback) {
chunks.push(Buffer.from(chunk));
callback();
},
});
res.writeHead = (status, responseHeaders) => {
statusCode = status;
headers = responseHeaders || {};
};
res.end = (chunk) => {
if (chunk) chunks.push(Buffer.from(chunk));
resolveDone();
};
return {
res,
done,
getStatusCode() {
return statusCode;
},
getHeaders() {
return headers;
},
getJsonBody() {
return JSON.parse(Buffer.concat(chunks).toString("utf8"));
},
};
}
test("buildSampleOffers is deterministic for the same search params", () => {
const searchParams = {
segments: [{ from: "ICN", to: "MAD" }],
passengers: { total: 2 },
};
const first = buildSampleOffers(searchParams);
const second = buildSampleOffers(searchParams);
assert.deepEqual(first, second);
assert.equal(first[0].provider, "skyscanner");
assert.equal(first[0].currency, "KRW");
});
test("sample handler returns skyscanner offers on POST /skyscanner", async () => {
const handler = createSkyscannerSampleHandler();
const req = createMockRequest({
body: JSON.stringify({
watchId: "watch-1",
searchParams: {
segments: [{ from: "ICN", to: "MAD" }],
},
}),
});
const response = createMockResponse();
await handler(req, response.res);
await response.done;
assert.equal(response.getStatusCode(), 200);
assert.equal(response.getHeaders()["content-type"], "application/json; charset=utf-8");
const payload = response.getJsonBody();
assert.equal(payload.currency, "KRW");
assert.ok(Array.isArray(payload.offers));
assert.equal(payload.offers.length, 3);
assert.equal(payload.offers[0].provider, "skyscanner");
});
test("sample handler accepts wrapped request payload shape", async () => {
const handler = createSkyscannerSampleHandler();
const req = createMockRequest({
body: JSON.stringify({
request: {
watchId: "watch-2",
searchParams: {
segments: [{ from: "ICN", to: "BCN" }],
},
},
}),
});
const response = createMockResponse();
await handler(req, response.res);
await response.done;
assert.equal(response.getStatusCode(), 200);
const payload = response.getJsonBody();
assert.equal(payload.offers[0].provider, "skyscanner");
});
test("sample handler returns 404 for unsupported route", async () => {
const handler = createSkyscannerSampleHandler();
const req = createMockRequest({
url: "/not-skyscanner",
body: JSON.stringify({}),
});
const response = createMockResponse();
await handler(req, response.res);
await response.done;
assert.equal(response.getStatusCode(), 404);
assert.match(response.getJsonBody().expected, /POST \/skyscanner/);
});