爪爪 · Paw Work
SELECT + DESCRIBE OUTCOME → DELIVER
爪爪 · Paw Work は Chrome MV3 のサイドパネル拡張。すでに開いているページで「伸爪(Paw Mode)」を有効にし、画像・表・本文・ブロック・リンクを点選してから、サイドパネルに欲しい結果を書く。返ってくるのはページについての要約文ではなく、編集可能なオフィスファイルとライブキャンバス(表計算・スライド・ポスター・HTML サイト・長文ドキュメント)。
無人でウェブを巡回する Operator でも、ターミナルのコーディングエージェントでもない。ログイン済みのブラウザの隣に座り、利用者が範囲を指定し、拡張が確認可能な成果物を返す、という分担になっている。
実装の正は「Session Workspace Runtime」と呼ばれる設計文書群。セッションがそのままワークスペースであり、利用者のメッセージはすべて同じエージェントループに入る。ツールは能力であって義務ではなく、モデルが「テキストで答えるか、永続ファイルを作るか」を判断する。
| 向いている | 第一候補にはならない |
|---|---|
| ブラウザ上で比較・抽出・書き出しを繰り返す人。ページをシート/デッキ/ポスター/サイト/長文へ変換したい人 | サイトを横断して購入・送信・決済まで無人で回す RPA |
| すでにログイン済みの SaaS・ストア・ドキュメントページから作業を始める人 | Docker・ローカルシェル・巨大リポジトリを主戦場にする開発(コーディングエージェントの領域) |
Alt+Shift+S。
@ で個別のキャプチャを参照できる。
| ページ上の対象 | 依頼の例 | 持ち帰るもの |
|---|---|---|
| 製品写真・表・本文・ブロック・リンク | 比較シートにして | 編集を続けられる Univer のライブ表計算 |
| 同じ選択、または空のワークスペース | 8 ページのデッキ/ポスター 1 枚 | tldraw キャンバス上の Design / Slides。デッキは PPTX へ書き出せる |
| いま開いているページ | 入場モーション付きの編集可能なサイトにして | 実体としての HTML。以後の修正は同じファイルに当たる。Site QA が品質を判定する |
| 長いメモや書き起こし | ドキュメントにして | 文書キャンバス |
| 画像や調べものが必要なとき | この作風で生成して/検索してシートに入れて | ワークスペース内の画像。検索は利用者自身の web-acquire キーを使う |
/plan はスラッシュコマンドで、そのターンのカード表示を強制する。
利用者がエディタを選ぶ操作はない。ファイルの型がそのまま表示面を決める、という対応になっている。
| 成果物 | ファイルの型 | 開く画面 |
|---|---|---|
| クリックで直す視覚物(ポスター・スライド) | pawCanvas JSON(themeId + layoutId + スロット) | tldraw の design.html |
| 実サイト・ランディング | data-paw-kind=site を持つ HTML | site.html。レイアウトエンジンではなくページとして開く |
| 表計算 | ワークブック | sheet.html(Univer) |
| 長文ドキュメント | Univer Docs、または data-paw-kind=document の HTML | docs.html か汎用プレビュー |
| PDF・素の HTML・Markdown | 分類できたが編集面を持たないもの | artifactPreview.html(閲覧専用) |
取り込み時の分類
ファイルを開くときの振り分けは classifyOpenArtifact() 一箇所に集約されている。マジックバイトが優先され、ファイル名と MIME はヒント扱い。ZIP(PK)と PDF(%PDF)を UTF-8 として文字列化することはしない、と明記されている。
| 入力 | 行き先 |
|---|---|
| xlsx / csv / tsv / json ワークブック | sheet |
| docx / json ドキュメント / html ドキュメント | docs |
json キャンバス(pawCanvas) | design(tldraw) |
html サイト(data-paw-kind=site) | web(site.html) |
| png / jpeg / gif / webp | ギャラリー |
| 正体不明の zip・不透明なバイナリ | ファイルカード。テキストとして開かない |
IWorkbookData への変換は Excel と等価ではなく、ポスター PDF は CID テキストより埋め込み JPEG を優先する。
利用者のメッセージはすべて sendMessage を通る。ユーザーに見える「チャットモード / 実行モード」の切り替えは存在しない。
toolChoice=auto で、モデルがツールを呼ばなくなるか Abort まで回る。
プロダクトの入口
エージェント作業のランタイム入口は 1 本に固定されている。
src/agent/vnext/runSession.product.js
エージェントが開いた作業タブは active: false で静かに開き、セッションごとに 1 つの Chrome タブグループへ入る。利用者が「打开」で開いたときはフォーカスする。書き込み中はそのセッションの作業タブがロックされる(ライブページ側はロックしない)。
設計文書は「モデルは判断(judge)し、ランタイムは拘束(bind)する」を役割分担として繰り返し書いている。ホスト法(隔離やページネーション)をプロンプトへ流し込まないこと、隔離の強制をプロンプトへ委ねないことが、そのまま禁止事項になっている。
| 層 | 担当 | やらないこと |
|---|---|---|
| Skill | 成果物の型、構成、アートディレクション、themeId / layoutId、スロットの文言、いつ確認するか |
座標(x/y/w/h)を書く。カタログをシステムプロンプトへ流す。QA を避けるために別ファイルを作る |
| Prompt | 短い不変条件(開いているキャンバスが対象。1 タスク 1 成果物。QA 失敗はそのファイルで直す) | レイアウトカタログ、長いレシピ、ホスト側の隔離規則、3 つ目のプランゲート |
| Runtime | ライブ artifactId の固定、ゲストパスの読み込み、JSON 検証、公式コマンド経由の適用、幾何のコンパイル、fail-closed |
プロンプトに隔離や「100 行を打ち直すな」を強制させる |
ツールは段階的開示ではなく、常に tools[] に載っている。9 つ目は作らない、というのが明文の制約。
| ツール | 役割 |
|---|---|
inspect | 選択グループやスキルの中身を必要になった時点で見る。無関係な質問で全件展開はしない |
acquire | ベンダー名を出さない取得系。search / fetch / map / crawl / image / note |
run | 生成コードのコンパイルと実行、キャンバスの作成(createScene / fromPage / fromRaster / fromSelection) |
clarify | 制御面の UI。質問、またはプランカードを出す |
sheet | ワークブックへの適用(Univer の Facade / Command 経由) |
deck | Design / Slides への適用。意味的なペイロード(themeId + frames)を受ける |
doc | ドキュメントへの適用 |
web | サイト HTML への適用。サイトが存在した後はそのファイルにパッチする |
計算と適用を分ける
大量の行やスロットを扱うときは、run が計算して /scratch に JSON を置き、公式ツール側は path / from でそれを読む。モデルが結果を打ち直す経路を作らない、という分担になっている。ファイルが無ければ ENOENT、中身が空や不正なら BAD_INPUT で止まる。
run # /scratch に計算結果の JSON を書く
sheet|deck|doc|web
# path / from でその JSON を読み、公式コマンドで適用
# 欠落 → ENOENT / 空・不正 → BAD_INPUT
fail-closed になっている境界
- 目印のない見栄えだけの HTML は Design ファイルとして着地できない(
USE_CANVAS)。 - 対象のキャンバスが無い場合は
NO_CANVAS。同種が 2 つあって対象指定が無ければAMBIGUOUS_CANVAS/AMBIGUOUS_WORKBOOK。 - ピン留めしたノードなしのフィールド書き込みは
NEED_SELECTION。ライブな Design タブなしの PNG / SVG / PDF 書き出しはNEED_TAB。 - QA が落ちたときは
CANVAS_QA_FAILEDと課題一覧が返り、同じ成果物を直す。新しいファイルへ逃げない。 - 空の公式書き込みは「成功 + 適用 0 件」ではなく
BAD_INPUTとして明言する。 - モデルは選択グループを書き換えられない(グループ書き込み API をツールに出していない)。
/context 読み取り専用。周辺のコンテキスト
/artifacts セッションの永続成果物
/scratch 実行スコープ。終了時に片付けられる
セッションを跨いだパスはプロンプトではなくホストの FS jail が拒否する。永続化は IndexedDB のメタデータと OPFS のブロブ(DurableSessionWorkspaceStore)で、同じ DB 名の新しいサービスやストアからセッションの成果物を復元できる。
| 領域 | 寿命 | 削除の条件 |
|---|---|---|
| /artifacts | ターン・エージェント再起動・ブラウザ再起動をまたいで残る | 明示的な成果物削除、またはセッション削除のみ。古さ・容量・「未使用」・モデルの都合では自動削除しない |
| /scratch | 実行中のみ | 実行が終了・中断・失敗した時点で消える。モデル側の後片付けツールは要らない |
モデルが書いた TypeScript / JavaScript は、拡張のソースコードではなくタスクのデータとして扱われる。同梱の esbuild-wasm がローカルでコンパイルし、同梱の QuickJS-WASM が隔離 VM で実行する。
ToolLoopAgent
→ run({ code / files })
→ manifest の sandbox ページ
→ 同梱 esbuild-wasm がローカルでコンパイル
→ 同梱 QuickJS-WASM が隔離 VM で実行
→ ファイルシステム RPC のみ明示的に開く
ゲストプログラムは chrome、window、document、fetch、IndexedDB、OPFS、拡張ホストのグローバルを受け取らない。見えるのは現在のセッションのファイルシステムとコンソール出力だけで、ホストがすべてのパスを検証・jail する。ランタイムの JS と WASM はすべて拡張に同梱され、実行可能コードを CDN から読み込む経路は無い。ライブページへコードを注入する旧 userScripts 経路は、プロダクトとマニフェストから外されている。
script-src 'self' 'wasm-unsafe-eval'、サンドボックスページのみ 'unsafe-eval' を持つ。最低要件は Chrome 115。
設計文書は S-A から S-R までの不変条件を並べ、tests/session-workspace/ の pendingCount=0 をゲートにしている。主なものを抜き出すと以下。
- 直接の質問にはテキストだけで答える。無関係な選択があっても
inspectしない。 - 成果物の依頼は
runと永続ファイルになり、後のターンで前の成果物を修正できる。 - 新しいセッションは隔離されたワークスペースを持ち、セッションを跨いだ FS 読み取りは拒否される。
- 成果物は実行終了とランタイム再起動をまたいで残り、セッション削除時は成果物も連鎖削除される(選択グループは残る)。
- 容量が逼迫しても成果物を自動削除しない。成果物が多くても初期コンテキストへ流し込まない。
- 通常のメッセージごとに Task オブジェクトを作らない。
Chrome ウェブストアには未掲載。README は「使うだけならソースツリー全体をクローンしない」と強く注意しており、unpacked ブランチ(約 44 MB)だけを取得する手順を案内している。そのフォルダがそのまま拡張本体で、ルートに manifest.json がある。
git clone --depth 1 --single-branch --branch unpacked \
https://github.com/Player-YN/PawWork_ZhuaZhua.git paw-work
realpath paw-work
- 上のブロックを実行する。最後の行が取得先の絶対パスを出力する(Windows は PowerShell 版が README にある)。
- Chrome で
chrome://extensionsを開く。 - デベロッパーモードを有効にする。
- パッケージ化されていない拡張機能を読み込むで、出力されたパスのフォルダを選ぶ。
git を使わない場合は GitHub 上でブランチを unpacked に切り替えて ZIP をダウンロードするか、リリースページの paw-work-unpacked.zip(同一バイト)を使う。Node も npm install も不要。
ソースからビルドする場合
前提は Node.js 20+、npm、Chrome 120+。
git clone https://github.com/Player-YN/PawWork_ZhuaZhua.git
cd PawWork_ZhuaZhua
npm install
npm run build:agent
npm run pack:extension
読み込むのは artifacts/unpacked/。npm install 後のリポジトリルートは node_modules を含んで数百 MB になるため、ルートを読み込んではいけないと明記されている。src を編集した日常の作業では npm run pack:dev(Univer / tldraw の再ビルドなし)のあとに拡張を再読み込みする。
| コマンド | 内容 |
|---|---|
npm run build:agent | アイコン、QuickJS、AI SDK、esbuild.wasm、sheet / docs / design をまとめてビルド |
npm run build:sheet / build:design | Univer + SheetJS / tldraw のベンダーバンドル生成(成果物は追跡外) |
npm run test:session-workspace | セッションワークスペースの受け入れ条件のゲート |
npm run pack:dev / pack:watch | src のみコピー。watch は変更ごとにコピーし続ける |
npm run check:icons | 生成された Lucide モジュールが決定的かを検査(アイコンは追跡対象の生成物) |
npm run playwright:install | ブラウザピクセル検証用の Chromium。既定ではインストールされない |
鍵がなければ何も動かない。設定はサイドパネル内。鍵は自分のマシンの拡張ストレージに置かれ、送られるのは自分で指定した HTTPS エンドポイントだけ、というのが記述されているモデル。
| 種別 | 必須 | 内容 |
|---|---|---|
| チャット | 必須 | OpenAI 互換の HTTPS エンドポイント(ベース URL + キー + モデル) |
| 画像 | 任意 | 専用のベース URL / キー / モデル。空欄はチャット側を継承する |
| ウェブ検索・取得 | 任意 | 検索やクロールのキー。無い場合でも fetch は匿名 GET を試せる |
| tldraw ライセンス | 任意 | Design / Slides の透かしを外す本番ライセンス |
fetch は Firecrawl のキーがあれば scrape、なければ匿名 GET。map と crawl は Firecrawl が必要。
- ウェブストア未掲載。
unpackedブランチかリリース zip からのサイドロードは暫定手段で、ストアが後の正面玄関という位置づけ。 - 拡張のみ。Chromium MV3。ホスティングされたサービスもアカウントも無い。
- BYOK 必須。チャット・画像・ウェブ取得それぞれに自分のキーが要る。
- tldraw の透かし。本番ライセンスが無ければ Design / Slides に公式の透かしが出る。CSS や DOM で隠すのはサポート外であり許容しない、と明記されている。
- キャプチャは真実の全部ではない。選択は意図であり、エージェントは必要に応じて調べ、成果物の型が本当に不明なときだけ一度だけ聞く。
- Excel / PowerPoint / ブラウザ RPA の完全な置き換えではない。ライブキャンバスが作業面であり、無人で巡回・決済・送信はしない。
- スイートの緑はそれ自体では成果ではない。テストが通ることを完成の証明としない、と設計文書側で明示されている。
- GitHub: Player-YN/PawWork_ZhuaZhua — 公開ソースツリー(MIT)
unpackedブランチ — 拡張本体のみ。使うだけならこちら- 最新リリース —
paw-work-unpacked.zip(同一バイト) - Univer — 表計算とドキュメントのライブキャンバス
- tldraw — Design / Slides のキャンバス
- Vercel AI SDK —
ToolLoopAgentのエージェントループ - QuickJS — 生成コードを走らせる WASM VM
リポジトリ内でランタイム契約を読むなら docs/SESSION_WORKSPACE_RUNTIME.md(プロダクト憲章)、docs/PROMPT_RUNTIME.md(判断と拘束の分担)、docs/RUNTIME_STACK.md(スタックと自前ビルドの境界)、docs/CWS_CODE_RUNTIME.md(生成コードとストアの境界)。