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
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,10 @@ for more or fewer slices. Each frame is 640px wide and named for its timestamp;
records the video, the segment and every frame time, so a claim about the mechanic can name the
clip it came from. Cards still cite source code at the pinned SHA; they never cite a video.

Every release also ships `watch.mjs`, so an installed game project fetches the watcher from the
same base URL the reference tools already read
(`releases/latest/download/watch.mjs`) and runs it with no checkout of this repository.

The default window opens 10% into the video, past the title card and menu. A vertical slice of an
open-ended session is still a guess: the first sheet is for deciding where to look next.

Expand Down
5 changes: 4 additions & 1 deletion scripts/validate.mjs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import Ajv from 'ajv/dist/2020.js';
import { readFileSync, readdirSync, mkdirSync, existsSync, writeFileSync } from 'node:fs';
import { readFileSync, readdirSync, mkdirSync, existsSync, writeFileSync, copyFileSync } from 'node:fs';
import path from 'node:path';
import { execFileSync } from 'node:child_process';
import { gzipSync } from 'node:zlib';
Expand Down Expand Up @@ -180,6 +180,9 @@ export function run(args = process.argv.slice(2)) {
mkdirSync(path.join(root, '.release'), { recursive: true });
writeFileSync(path.join(root, '.release', 'index.json.gz'), gzipSync(JSON.stringify({ version: 1, games: catalog, stubs })));
for (const game of games) writeFileSync(path.join(root, '.release', `game-${game.id}.json`), JSON.stringify(game));
// The gameplay watcher rides along so an installed game project can fetch it from the same
// release the reference tools already read, with no checkout of this repository.
copyFileSync(new URL('../scripts/watch.mjs', import.meta.url), path.join(root, '.release', 'watch.mjs'));
}
}
if (process.argv[1] && path.resolve(process.argv[1]) === fileURLToPath(import.meta.url)) {
Expand Down
3 changes: 2 additions & 1 deletion tests/library.spec.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,8 @@ test('release assets keep the version-1 contract and exact asset set', t => {
t.after(() => cleanup(dir));
const result = runNpm(dir, ['release:assets', '--', '--source', source.dir]);
assert.equal(result.status, 0, result.stderr);
assert.deepEqual(readdirSync(path.join(dir, '.release')).sort(), ['game-demo.json', 'game-second.json', 'index.json.gz']);
assert.deepEqual(readdirSync(path.join(dir, '.release')).sort(), ['game-demo.json', 'game-second.json', 'index.json.gz', 'watch.mjs']);
assert.equal(readFileSync(path.join(dir, '.release', 'watch.mjs'), 'utf8'), readFileSync(path.join(dir, 'scripts', 'watch.mjs'), 'utf8'));
const index = JSON.parse(gunzipSync(readFileSync(path.join(dir, '.release', 'index.json.gz'))).toString());
assert.equal(index.version, 1);
assert.deepEqual(index.games, config);
Expand Down
Loading