Files
Mujoco_WASM/web_platform/e2e/lekiwi.meshes.spec.ts
T
chenlin f3a8a38acd
web-platform-ci / Standalone decision service (no cloud credentials) (push) Has been cancelled
web-platform-ci / TypeScript, lint, unit, build (push) Has been cancelled
web-platform-ci / Playwright E2E (push) Has been cancelled
lekiwi-compatibility / cpu-compatibility (push) Has been cancelled
web-platform-ci / Standalone decision service (no cloud credentials) (pull_request) Has been cancelled
web-platform-ci / TypeScript, lint, unit, build (pull_request) Has been cancelled
web-platform-ci / Playwright E2E (pull_request) Has been cancelled
lekiwi-compatibility / cpu-compatibility (pull_request) Has been cancelled
feat: release v1.0.1 CADWorld 网站与 LeKiwi 智能抓放
集成同源 BYOK 会话隔离、精简模型设置、官方订阅入口和 HTTPS 发布运维;保留本地训练/调参与控制能力。同步 npm 版本及 CHANGELOG,记录公网真实 API 验收仍待用户凭据。
2026-09-24 09:57:41 +08:00

59 lines
2.7 KiB
TypeScript

import { expect, test } from '@playwright/test';
import { resolve } from 'node:path';
import { writeFile } from 'node:fs/promises';
import type {} from '../physics/runner';
test('完整 314244 面三轮:真实 WASM、随轴运动、ZIP 重导与有界资源', async ({ page }, info) => {
const errors: string[] = [];
page.on('pageerror', (error) => errors.push(error.message));
await page.goto('/physics/runner.html');
await page.waitForFunction(() => Boolean(window.lekiwiPhysics));
await page.evaluate((path) => window.lekiwiPhysics.boot(path), `/@fs${resolve('build/lekiwi')}`);
try {
const before = await page.evaluate(() => window.lekiwiPhysics.visualStats());
// The three original filenames contain identical bytes; one content-addressed
// OBJ is shared by three independent visual instances.
expect(before.generatedMeshes).toHaveLength(1);
expect(before.wheels).toHaveLength(3);
for (const wheel of before.wheels) {
expect(wheel.faces).toBe(314244);
expect(wheel.vertices).toBeGreaterThan(150000);
expect(wheel.centerError).toBeLessThan(1e-6);
expect(wheel.scale).toEqual([0.001, 0.001, 0.001]);
expect(wheel.collision).toBe(false);
expect(wheel.mass).toBe(0);
}
await page.evaluate(() => window.lekiwiPhysics.drive(0, 0.1, 0, 0.25));
const after = await page.evaluate(() => window.lekiwiPhysics.visualStats());
for (let i = 0; i < 3; i++) {
expect(after.wheels[i].centerError).toBeLessThan(1e-6);
expect(
after.wheels[i].rotation.some((v, j) => Math.abs(v - before.wheels[i].rotation[j]) > 0.01),
).toBe(true);
}
const traces: Awaited<ReturnType<typeof window.lekiwiPhysics.packageRoundtrip>>[] = [];
for (let i = 0; i < 8; i++) {
const result = await page.evaluate(() => window.lekiwiPhysics.packageRoundtrip());
expect(result.oldModelDeleted).toBe(true);
expect(result.oldDataDeleted).toBe(true);
expect(result.workspaces).toHaveLength(1);
expect(result.generatedMeshes).toHaveLength(1);
expect(result.wheels.every((wheel) => wheel.faces === 314244 && !wheel.collision)).toBe(true);
traces.push(result);
}
console.log(
'mesh resources',
traces.map((t) => ({ heap: t.heap, bytes: t.projectBytes, xml: t.xmlFiles })),
);
await writeFile(
info.outputPath('full-mesh-roundtrip.json'),
JSON.stringify({ before, after, traces }, null, 2),
);
expect(traces.every((t) => t.projectBytes === traces[0].projectBytes)).toBe(true);
expect(traces[7].heap).toBeLessThanOrEqual(traces[5].heap + 32 * 1024 * 1024);
expect(errors).toEqual([]);
} finally {
await page.evaluate(() => window.lekiwiPhysics.dispose());
}
});