Arseniy Klempner e901f24c9d
feat: consolidate browser testing code into a single package
feat: simplify browser sim image to light push flow
2025-09-05 10:08:16 -07:00

117 lines
3.8 KiB
TypeScript

import { test, expect } from "@playwright/test";
import axios from "axios";
import { spawn } from "child_process";
import { fileURLToPath } from "url";
import { dirname, join } from "path";
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);
// Run this entire file in serial mode to avoid port collisions
test.describe.configure({ mode: "serial" });
test.describe("Server Tests", () => {
let serverProcess: any;
let baseUrl = "http://localhost:3000";
test.beforeAll(async () => {
// Start the server
const serverPath = join(__dirname, "..", "dist", "src", "server.js");
console.log("Starting server from:", serverPath);
serverProcess = spawn("node", [serverPath], {
stdio: "pipe",
env: { ...process.env, PORT: "3000" }
});
// Log server output
serverProcess.stdout?.on("data", (data: Buffer) => {
console.log("[Server]", data.toString().trim());
});
serverProcess.stderr?.on("data", (data: Buffer) => {
console.error("[Server Error]", data.toString().trim());
});
// Wait for server to start
console.log("Waiting for server to start...");
await new Promise((resolve) => setTimeout(resolve, 3000));
// Wait for server to be ready
let serverReady = false;
for (let i = 0; i < 30; i++) {
try {
const res = await axios.get(`${baseUrl}/`, { timeout: 2000 });
if (res.status === 200) {
console.log(`Server is ready after ${i + 1} attempts`);
serverReady = true;
break;
}
} catch (error: any) {
if (i % 5 === 0) {
console.log(`Attempt ${i + 1}/30 failed:`, error.code || error.message);
}
}
await new Promise((r) => setTimeout(r, 1000));
}
expect(serverReady).toBe(true);
});
test.afterAll(async () => {
if (serverProcess) {
console.log("Stopping server...");
serverProcess.kill("SIGTERM");
await new Promise((resolve) => setTimeout(resolve, 1000));
}
});
test("server health endpoint", async () => {
const res = await axios.get(`${baseUrl}/`);
expect(res.status).toBe(200);
expect(res.data.status).toBe("Waku simulation server is running");
});
test("static files are served", async () => {
// Check if the main HTML file is accessible
const htmlRes = await axios.get(`${baseUrl}/app/index.html`);
expect(htmlRes.status).toBe(200);
expect(htmlRes.data).toContain("Waku Test Environment");
// Check if the JavaScript file is accessible
const jsRes = await axios.get(`${baseUrl}/app/index.js`);
expect(jsRes.status).toBe(200);
expect(jsRes.data).toContain("WakuHeadless");
});
test("create and start Waku node", async () => {
try {
// Create a Waku node
const createRes = await axios.post(`${baseUrl}/admin/v1/create-node`, {
defaultBootstrap: true,
networkConfig: {
clusterId: 1
}
});
expect(createRes.status).toBe(200);
expect(createRes.data.success).toBe(true);
// Start the node
const startRes = await axios.post(`${baseUrl}/admin/v1/start-node`);
expect(startRes.status).toBe(200);
expect(startRes.data.success).toBe(true);
// Now the peer info endpoint should work
const infoRes = await axios.get(`${baseUrl}/waku/v1/peer-info`);
expect(infoRes.status).toBe(200);
expect(infoRes.data.peerId).toBeDefined();
expect(infoRes.data.multiaddrs).toBeDefined();
} catch (error: any) {
// If browser initialization failed, this test will fail - that's expected
console.log("Waku node test failed (expected if browser not initialized):", error.response?.data?.error || error.message);
// Validation error due to missing required networkConfig field results in 400
expect(error.response?.status).toBe(400);
}
});
});