From 99f16f2bca0ed5fd2f2a129a3af8113522e65c7c Mon Sep 17 00:00:00 2001 From: RECTOR Date: Sun, 6 Sep 2026 23:01:01 +0700 Subject: [PATCH 1/2] =?UTF-8?q?fix(render):=20adopt=20modern=20pi=20tool?= =?UTF-8?q?=20contract=20=E2=80=94=20execute=20signature,=20TypeBox=20para?= =?UTF-8?q?meters,=20AgentToolResult=20content=20blocks=20(#17)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- extensions/render.ts | 17 ++++++++++------- package.json | 3 ++- pnpm-lock.yaml | 8 ++++++++ 3 files changed, 20 insertions(+), 8 deletions(-) diff --git a/extensions/render.ts b/extensions/render.ts index 879179f..3f0c786 100644 --- a/extensions/render.ts +++ b/extensions/render.ts @@ -1,5 +1,7 @@ // extensions/render.ts import { chromium } from "playwright-core" +import { Type } from "typebox" + import { pathToFileURL } from "node:url" import { writeFileSync, mkdirSync } from "node:fs" import { join } from "node:path" @@ -186,14 +188,15 @@ export default function (pi: any) { pi.registerTool({ name: "keystone_render", description: "Render an HTML file with headless Chromium at given viewports. Returns screenshots + computed styles + DOM snapshot for the Keystone gate engine.", - parameters: { - htmlPath: { type: "string", description: "Absolute path to the HTML file to render" }, - url: { type: "string", description: "Optional live URL to render instead of htmlPath (audit URL mode). If set, htmlPath is ignored." }, - viewports: { type: "array", items: { type: "number" }, description: "CSS pixel widths to screenshot", default: [1280, 375, 320, 414, 768] }, - outDir: { type: "string", description: "Directory to write outputs", default: "./keystone-render" }, - }, + parameters: Type.Object({ + htmlPath: Type.String({ description: "Absolute path to the HTML file to render" }), + url: Type.Optional(Type.String({ description: "Optional live URL to render instead of htmlPath (audit URL mode). If set, htmlPath is ignored." })), + viewports: Type.Optional(Type.Array(Type.Number({ description: "CSS pixel widths to screenshot" }))), + outDir: Type.Optional(Type.String({ description: "Directory to write outputs" })), + }), async execute(_toolCallId: string, input: RenderInput) { - return render(input) + const result = await render(input) + return { content: [{ type: "text" as const, text: JSON.stringify(result, null, 2) }], details: result } }, }) } diff --git a/package.json b/package.json index 29c63ff..f670eca 100644 --- a/package.json +++ b/package.json @@ -52,7 +52,8 @@ }, "devDependencies": { "@types/node": "^24.13.3", - "playwright": "1.62.0" + "playwright": "1.62.0", + "typebox": "*" }, "packageManager": "pnpm@10.33.2" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 572260e..e23119f 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -27,6 +27,9 @@ importers: playwright: specifier: 1.62.0 version: 1.62.0 + typebox: + specifier: '*' + version: 1.3.28 packages: @@ -310,6 +313,9 @@ packages: engines: {node: '>=18.0.0'} hasBin: true + typebox@1.3.28: + resolution: {integrity: sha512-5hTNlwzKj7BPPqhT91TPa4fK9bh/ZOei7mzweMpNidwLTxtduXHgr/OAbwx4mRW8aKFYu1I8fT1+0+PQtst1/g==} + uhyphen@0.2.0: resolution: {integrity: sha512-qz3o9CHXmJJPGBdqzab7qAYuW8kQGKNEuoHFYrBwV6hWIMcpAmxDLXojcHfFr9US1Pe6zUswEIJIbLI610fuqA==} @@ -538,6 +544,8 @@ snapshots: optionalDependencies: fsevents: 2.3.3 + typebox@1.3.28: {} + uhyphen@0.2.0: {} undici-types@7.18.2: {} From 82d28c2b6de8883f173d763af96bd5286dfb0799 Mon Sep 17 00:00:00 2001 From: RECTOR Date: Sun, 6 Sep 2026 23:01:01 +0700 Subject: [PATCH 2/2] =?UTF-8?q?chore(release):=201.0.2=20=E2=80=94=20omp?= =?UTF-8?q?=20tool=20contract=20adoption=20(#17)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index f670eca..ee49040 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@getpipher/keystone", - "version": "1.0.1", + "version": "1.0.2", "description": "Anti-AI-slop design skill with an executable gate engine. Beats Hallmark by enforcing its gates instead of imagining them.", "keywords": [ "pi-package",