Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions web/e2e/smoke.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,15 @@ test.describe("Compiler Explorer smoke", () => {
await expect(page.getByRole("textbox", { name: "source" })).toContainText("H = relu(X @ W1 + b1)");
});

test("the landing page plays the hero clip and links to the explorer", async ({ page }) => {
await page.goto("/");
const video = page.locator("video");
await expect(video).toHaveAttribute("src", "/hero.webm");
const ready = await video.evaluate((v: HTMLVideoElement) => v.readyState >= 1 || new Promise((r) => (v.onloadedmetadata = () => r(true))));
expect(ready).toBeTruthy();
await expect(page.getByRole("link", { name: "Open the Compiler Explorer" })).toHaveAttribute("href", "/app");
});

test("a rejected program is shown as an error, not a crash", async ({ page }) => {
await page.goto("/app");
await page.getByLabel("source").fill("input A : i8[2, 2]\nC = A @ A +\noutput C\n");
Expand Down
5 changes: 5 additions & 0 deletions web/eslint.config.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
import js from "@eslint/js";
import tseslint from "typescript-eslint";
import globals from "globals";

export default tseslint.config(
{ ignores: [".vercel/", "dist/", ".astro/", "node_modules/", "src/lib/examples.generated.ts", "src/pages/docs/*.md", "public/"] },
js.configs.recommended,
...tseslint.configs.recommended,
{
files: ["scripts/**/*.mjs"],
languageOptions: { globals: globals.node },
},
{
files: ["**/*.ts", "**/*.tsx"],
rules: { "@typescript-eslint/no-explicit-any": "error" },
Expand Down
4 changes: 4 additions & 0 deletions web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,13 +30,17 @@
"@types/react": "^18.3.12",
"@types/react-dom": "^18.3.1",
"eslint": "^9.39.5",
"globals": "^15.15.0",
"typescript": "^5.6.3",
"typescript-eslint": "^8.72.0",
"vitest": "^2.1.9"
},
"pnpm": {
"onlyBuiltDependencies": [
"esbuild"
],
"ignoredBuiltDependencies": [
"sharp"
]
}
}
9 changes: 9 additions & 0 deletions web/pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Binary file added web/public/hero-poster.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added web/public/hero.webm
Binary file not shown.
34 changes: 34 additions & 0 deletions web/scripts/record-hero.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
// Records the hero clip: one program compiled and run on both chips, then the tiny-tpu array
// played cycle by cycle. Run against a built site (`pnpm build && pnpm preview --port 4322`):
// node scripts/record-hero.mjs http://127.0.0.1:4322 <out-dir>
// Output: hero-raw.webm in <out-dir>. The shipped clip is trimmed from 5.5 s (past the loading
// screen) and re-encoded: ffmpeg -ss 5.5 -i hero-raw.webm -an -c:v libvpx-vp9 -crf 40 -vf scale=960:-2 public/hero.webm
import { chromium } from "@playwright/test";
import { mkdirSync, renameSync } from "node:fs";
import { join } from "node:path";

const [base = "http://127.0.0.1:4322", outDir = "hero-out"] = process.argv.slice(2);
mkdirSync(outDir, { recursive: true });

const browser = await chromium.launch();
const context = await browser.newContext({
viewport: { width: 1280, height: 960 },
recordVideo: { dir: outDir, size: { width: 1280, height: 960 } },
});
const page = await context.newPage();
await page.goto(`${base}/app`);
await page.getByRole("button", { name: "Compile & run" }).click();
await page.getByText("bit-exact").first().waitFor({ timeout: 150_000 });
await page.getByRole("tab", { name: "tiny-tpu" }).click();
await page.getByRole("img", { name: /^PE\[0\]\[0\] / }).first().scrollIntoViewIfNeeded();
await page.getByRole("button", { name: "Play" }).click();
await page.waitForTimeout(6000);
await page.getByRole("tab", { name: "Run & compare" }).click();
await page.waitForTimeout(3000);
const video = page.video();
await context.close();
await browser.close();
const path = await video.path();
const target = join(outDir, "hero-raw.webm");
renameSync(path, target);
console.log(target);
16 changes: 16 additions & 0 deletions web/src/pages/index.astro
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,22 @@ import Base from "../layouts/Base.astro";
<p><a href="/app"><button class="primary">Open the Compiler Explorer</button></a> <a href="/docs/" style="margin-left: 12px">Read the docs</a></p>
</header>

<figure style="margin: 20px 0">
<video
src="/hero.webm"
poster="/hero-poster.jpg"
autoplay
muted
loop
playsinline
aria-label="One program, compiled to tiny-gpu and tiny-tpu: the tiny-tpu array playing cycle by cycle on the real RTL"
style="width: 100%; border: 1px solid var(--line); border-radius: 8px; background: var(--panel)"
></video>
<figcaption class="muted" style="font-size: 13px; margin-top: 6px">
<code>C = relu(A @ B)</code> compiled to both chips. The array is tiny-tpu's real RTL, cycle by cycle, from the Compiler Explorer.
</figcaption>
</figure>

<section class="panel" style="margin: 20px 0">
<h2 style="font-size: 17px; margin-top: 0">What is checked, on every commit</h2>
<ul style="margin: 0; padding-left: 18px">
Expand Down
Loading