{
  "schemaVersion": "1.0",
  "item": {
    "slug": "canvas-os-1-0-1",
    "name": "Canvas Os 1.0.1",
    "source": "tencent",
    "type": "skill",
    "category": "开发工具",
    "sourceUrl": "https://clawhub.ai/Knightluozichu/canvas-os-1-0-1",
    "canonicalUrl": "https://clawhub.ai/Knightluozichu/canvas-os-1-0-1",
    "targetPlatform": "OpenClaw"
  },
  "install": {
    "downloadMode": "redirect",
    "downloadUrl": "/downloads/canvas-os-1-0-1",
    "sourceDownloadUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=canvas-os-1-0-1",
    "sourcePlatform": "tencent",
    "targetPlatform": "OpenClaw",
    "installMethod": "Manual import",
    "extraction": "Extract archive",
    "prerequisites": [
      "OpenClaw"
    ],
    "packageFormat": "ZIP package",
    "includedAssets": [
      "CANVAS-LOADING.md",
      "README.md",
      "SKILL.md",
      "_meta.json",
      "canvas-inject.py",
      "close-app.sh"
    ],
    "primaryDoc": "SKILL.md",
    "quickSetup": [
      "Download the package from Yavira.",
      "Extract the archive and review SKILL.md first.",
      "Import or place the package into your OpenClaw setup."
    ],
    "agentAssist": {
      "summary": "Hand the extracted package to your coding agent with a concrete install brief instead of figuring it out manually.",
      "steps": [
        "Download the package from Yavira.",
        "Extract it into a folder your agent can access.",
        "Paste one of the prompts below and point your agent at the extracted folder."
      ],
      "prompts": [
        {
          "label": "New install",
          "body": "I downloaded a skill package from Yavira. Read SKILL.md from the extracted folder and install it by following the included instructions. Then review README.md for any prerequisites, environment setup, or post-install checks. Tell me what you changed and call out any manual steps you could not complete."
        },
        {
          "label": "Upgrade existing",
          "body": "I downloaded an updated skill package from Yavira. Read SKILL.md from the extracted folder, compare it with my current installation, and upgrade it while preserving any custom configuration unless the package docs explicitly say otherwise. Then review README.md for any prerequisites, environment setup, or post-install checks. Summarize what changed and any follow-up checks I should run."
        }
      ]
    },
    "sourceHealth": {
      "source": "tencent",
      "status": "healthy",
      "reason": "direct_download_ok",
      "recommendedAction": "download",
      "checkedAt": "2026-04-30T16:55:25.780Z",
      "expiresAt": "2026-05-07T16:55:25.780Z",
      "httpStatus": 200,
      "finalUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=network",
      "contentType": "application/zip",
      "probeMethod": "head",
      "details": {
        "probeUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=network",
        "contentDisposition": "attachment; filename=\"network-1.0.0.zip\"",
        "redirectLocation": null,
        "bodySnippet": null
      },
      "scope": "source",
      "summary": "Source download looks usable.",
      "detail": "Yavira can redirect you to the upstream package for this source.",
      "primaryActionLabel": "Download for OpenClaw",
      "primaryActionHref": "/downloads/canvas-os-1-0-1"
    },
    "validation": {
      "installChecklist": [
        "Use the Yavira download entry.",
        "Review SKILL.md after the package is downloaded.",
        "Confirm the extracted package contains the expected setup assets."
      ],
      "postInstallChecks": [
        "Confirm the extracted package includes the expected docs or setup files.",
        "Validate the skill or prompts are available in your target agent workspace.",
        "Capture any manual follow-up steps the agent could not complete."
      ]
    },
    "downloadPageUrl": "https://openagent3.xyz/downloads/canvas-os-1-0-1",
    "agentPageUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent",
    "manifestUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent.json",
    "briefUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent.md"
  },
  "agentAssist": {
    "summary": "Hand the extracted package to your coding agent with a concrete install brief instead of figuring it out manually.",
    "steps": [
      "Download the package from Yavira.",
      "Extract it into a folder your agent can access.",
      "Paste one of the prompts below and point your agent at the extracted folder."
    ],
    "prompts": [
      {
        "label": "New install",
        "body": "I downloaded a skill package from Yavira. Read SKILL.md from the extracted folder and install it by following the included instructions. Then review README.md for any prerequisites, environment setup, or post-install checks. Tell me what you changed and call out any manual steps you could not complete."
      },
      {
        "label": "Upgrade existing",
        "body": "I downloaded an updated skill package from Yavira. Read SKILL.md from the extracted folder, compare it with my current installation, and upgrade it while preserving any custom configuration unless the package docs explicitly say otherwise. Then review README.md for any prerequisites, environment setup, or post-install checks. Summarize what changed and any follow-up checks I should run."
      }
    ]
  },
  "documentation": {
    "source": "clawhub",
    "primaryDoc": "SKILL.md",
    "sections": [
      {
        "title": "Canvas OS",
        "body": "Canvas as an app platform. Build, store, and run rich visual apps on the OpenClaw Canvas."
      },
      {
        "title": "Philosophy",
        "body": "You are an OS. Canvas is the window. Apps are built locally and run on Canvas.\n\nRich HTML/CSS/JS UIs — not just text. Full interactivity, animations, live data."
      },
      {
        "title": "Quick Commands",
        "body": "CommandWhat Jarvis Does\"Open [app]\"Start server, navigate Canvas, inject data\"Build me a [type]\"Create app from template, open it\"Update [element]\"Inject JS to modify live\"Show [data] on canvas\"Quick A2UI display\"Close canvas\"Stop server, hide Canvas"
      },
      {
        "title": "How It Works",
        "body": "Key principle: Apps run on Canvas, not in a browser tab. Canvas is your UI window."
      },
      {
        "title": "Canvas Loading Methods",
        "body": "Canvas has security restrictions that block file path access. Three methods work:\n\nMethodWhen to UseProsConsLocalhost ServerComplex apps, external assetsFull browser featuresRequires port managementDirect HTML InjectionQuick displays, demosInstant, no server neededNo external assets, size limitData URLsSmall contentSelf-containedUnreliable on some systems\n\n❌ Does NOT work: file:///path/to/file.html (blocked by Canvas security)\n\n📖 See: CANVAS-LOADING.md for detailed guide + troubleshooting\n\nHelper script: canvas-inject.py — Formats HTML for direct injection"
      },
      {
        "title": "1. Apps are HTML/CSS/JS files",
        "body": "~/.openclaw/workspace/apps/[app-name]/\n├── index.html    # The UI (self-contained recommended)\n├── data.json     # Persistent state\n└── manifest.json # App metadata"
      },
      {
        "title": "2. Serve via localhost",
        "body": "cd ~/.openclaw/workspace/apps/[app-name]\npython3 -m http.server [PORT] > /dev/null 2>&1 &"
      },
      {
        "title": "3. Navigate Canvas to localhost",
        "body": "NODE=\"Your Node Name\"  # Get from: openclaw nodes status\nopenclaw nodes canvas navigate --node \"$NODE\" \"http://localhost:[PORT]/\"\n\nImportant: This opens the app on Canvas (the visual panel), NOT in a browser."
      },
      {
        "title": "4. Agent injects data via JS eval",
        "body": "openclaw nodes canvas eval --node \"$NODE\" --js \"app.setData({...})\"\n\nNote: The openclaw-canvas:// URL scheme has issues in current OpenClaw versions. Use http://localhost: instead."
      },
      {
        "title": "Opening an App",
        "body": "What this does: Displays the app on Canvas (the visual panel), not in a browser tab."
      },
      {
        "title": "Method 1: Localhost Server (Recommended for Complex Apps)",
        "body": "Full sequence:\n\nNODE=\"Your Node Name\"\nPORT=9876\nAPP=\"my-app\"\n\n# 1. Kill any existing server on the port\nlsof -ti:$PORT | xargs kill -9 2>/dev/null\n\n# 2. Start server\ncd ~/.openclaw/workspace/apps/$APP\npython3 -m http.server $PORT > /dev/null 2>&1 &\n\n# 3. Wait for server\nsleep 1\n\n# 4. Navigate Canvas\nopenclaw nodes canvas navigate --node \"$NODE\" \"http://localhost:$PORT/\"\n\n# 5. Inject data\nopenclaw nodes canvas eval --node \"$NODE\" --js \"app.loadData({...})\""
      },
      {
        "title": "Method 2: Direct HTML Injection (For Quick Displays)",
        "body": "When to use: File paths don't work in Canvas (security sandboxing). Data URLs can be unreliable. Use this for instant displays without localhost.\n\n# Example using canvas tool\ncanvas.present(url=\"about:blank\", target=node_name)\n\nhtml_content = \"\"\"<!DOCTYPE html>\n<html>\n<head>\n    <style>\n        body { background: #667eea; color: white; padding: 40px; }\n        .card { background: white; color: #333; padding: 30px; border-radius: 16px; }\n    </style>\n</head>\n<body>\n    <div class=\"card\">\n        <h1>Your Content Here</h1>\n    </div>\n</body>\n</html>\"\"\"\n\n# Escape backticks and inject\njs_code = f\"\"\"document.open();\ndocument.write(`{html_content}`);\ndocument.close();\"\"\"\n\ncanvas.eval(javaScript=js_code, target=node_name)\n\nKey limitation: File paths (file:///path/to/file.html) are blocked in Canvas for security. Always use localhost or direct injection."
      },
      {
        "title": "App API Convention",
        "body": "Every app should expose a window.app or window.[appname] object:\n\nwindow.app = {\n  // Update values\n  setValue: (key, val) => {\n    document.getElementById(key).textContent = val;\n  },\n  \n  // Bulk update\n  loadData: (data) => { /* render all */ },\n  \n  // Notifications\n  notify: (msg) => { /* show toast */ }\n};"
      },
      {
        "title": "Two-Way Communication",
        "body": "Apps send commands back via deep links:\n\nfunction sendToAgent(message) {\n  window.location.href = `openclaw://agent?message=${encodeURIComponent(message)}`;\n}\n\n// Button click → agent command\ndocument.getElementById('btn').onclick = () => {\n  sendToAgent('Refresh my dashboard');\n};"
      },
      {
        "title": "Dashboard",
        "body": "Stats cards, progress bars, lists. Self-contained HTML.\n\nDefault port: 9876\nAPI: dashboard.setRevenue(), dashboard.setProgress(), dashboard.notify()"
      },
      {
        "title": "Tracker",
        "body": "Habits/tasks with checkboxes and streaks. Self-contained HTML.\n\nDefault port: 9877\nAPI: tracker.setItems(), tracker.addItem(), tracker.toggleItem()"
      },
      {
        "title": "Quick Display (A2UI)",
        "body": "For temporary displays without a full app:\n\nopenclaw nodes canvas a2ui push --node \"$NODE\" --text \"\n📊 QUICK STATUS\n\nRevenue: \\$500\nUsers: 100\n\nDone!\n\""
      },
      {
        "title": "Port Assignments",
        "body": "App TypeDefault PortDashboard9876Tracker9877Timer9878Display9879Custom9880+"
      },
      {
        "title": "Design System",
        "body": ":root {\n  --bg-primary: #0a0a0a;\n  --bg-card: #1a1a2e;\n  --accent-green: #00d4aa;\n  --accent-blue: #4a9eff;\n  --accent-orange: #f59e0b;\n  --text-primary: #fff;\n  --text-muted: #888;\n  --border: #333;\n}"
      },
      {
        "title": "Best Practices",
        "body": "Self-contained HTML — Inline CSS/JS for portability\nDark theme — Match OpenClaw aesthetic\nExpose app API — Let agent update via window.app.*\nUse IDs — On elements the agent will update\nLive clock — Shows the app is alive\nDeep links — For two-way communication"
      },
      {
        "title": "Troubleshooting",
        "body": "App opens in browser instead of Canvas?\n\nMake sure you're using openclaw nodes canvas navigate, not just open\nCanvas navigate targets the Canvas panel specifically\n\n\"Not Found\" on Canvas?\n\nFile paths don't work: Canvas blocks file:/// URLs for security (sandboxing)\nData URLs may fail: Use direct HTML injection via canvas eval + document.write() instead\nFor localhost: Verify server is running: curl http://localhost:[PORT]/\nCheck port is correct\nUse http://localhost: not openclaw-canvas:// (URL scheme has issues)\n\nCanvas shows \"Not Found\" even with correct URL?\n\nThis is a security boundary: Canvas can't access local filesystem\nSolution: Use Method 2 (Direct HTML Injection) from \"Opening an App\" section\nOr serve via localhost (Method 1)\n\nApp not updating?\n\nCheck window.app API is defined: openclaw nodes canvas eval --js \"typeof window.app\"\nVerify JS eval syntax: single quotes inside double quotes\n\nServer port already in use?\n\nKill existing: lsof -ti:[PORT] | xargs kill -9"
      },
      {
        "title": "canvas-inject.py",
        "body": "Python helper for direct HTML injection (Method 2).\n\n# Example usage in Python\nfrom canvas_inject import inject_html_to_canvas\n\nhtml = open(\"my-dashboard.html\").read()\ncommands = inject_html_to_canvas(html, node_name=\"Your Node\")\n\n# Then use canvas tool with these commands\ncanvas.present(**commands[\"step1_present\"])\ncanvas.eval(**commands[\"step2_inject\"])\n\nOr just follow the pattern manually (see Method 2 in \"Opening an App\")."
      },
      {
        "title": "Requirements",
        "body": "OpenClaw with Canvas support (macOS app)\nPython 3 (for http.server)\nA paired node with canvas capability"
      }
    ],
    "body": "Canvas OS\n\nCanvas as an app platform. Build, store, and run rich visual apps on the OpenClaw Canvas.\n\nPhilosophy\n\nYou are an OS. Canvas is the window. Apps are built locally and run on Canvas.\n\nRich HTML/CSS/JS UIs — not just text. Full interactivity, animations, live data.\n\nQuick Commands\nCommand\tWhat Jarvis Does\n\"Open [app]\"\tStart server, navigate Canvas, inject data\n\"Build me a [type]\"\tCreate app from template, open it\n\"Update [element]\"\tInject JS to modify live\n\"Show [data] on canvas\"\tQuick A2UI display\n\"Close canvas\"\tStop server, hide Canvas\nHow It Works\n\nKey principle: Apps run on Canvas, not in a browser tab. Canvas is your UI window.\n\nCanvas Loading Methods\n\nCanvas has security restrictions that block file path access. Three methods work:\n\nMethod\tWhen to Use\tPros\tCons\nLocalhost Server\tComplex apps, external assets\tFull browser features\tRequires port management\nDirect HTML Injection\tQuick displays, demos\tInstant, no server needed\tNo external assets, size limit\nData URLs\tSmall content\tSelf-contained\tUnreliable on some systems\n\n❌ Does NOT work: file:///path/to/file.html (blocked by Canvas security)\n\n📖 See: CANVAS-LOADING.md for detailed guide + troubleshooting\n\nHelper script: canvas-inject.py — Formats HTML for direct injection\n\n1. Apps are HTML/CSS/JS files\n~/.openclaw/workspace/apps/[app-name]/\n├── index.html    # The UI (self-contained recommended)\n├── data.json     # Persistent state\n└── manifest.json # App metadata\n\n2. Serve via localhost\ncd ~/.openclaw/workspace/apps/[app-name]\npython3 -m http.server [PORT] > /dev/null 2>&1 &\n\n3. Navigate Canvas to localhost\nNODE=\"Your Node Name\"  # Get from: openclaw nodes status\nopenclaw nodes canvas navigate --node \"$NODE\" \"http://localhost:[PORT]/\"\n\n\nImportant: This opens the app on Canvas (the visual panel), NOT in a browser.\n\n4. Agent injects data via JS eval\nopenclaw nodes canvas eval --node \"$NODE\" --js \"app.setData({...})\"\n\n\nNote: The openclaw-canvas:// URL scheme has issues in current OpenClaw versions. Use http://localhost: instead.\n\nOpening an App\n\nWhat this does: Displays the app on Canvas (the visual panel), not in a browser tab.\n\nMethod 1: Localhost Server (Recommended for Complex Apps)\n\nFull sequence:\n\nNODE=\"Your Node Name\"\nPORT=9876\nAPP=\"my-app\"\n\n# 1. Kill any existing server on the port\nlsof -ti:$PORT | xargs kill -9 2>/dev/null\n\n# 2. Start server\ncd ~/.openclaw/workspace/apps/$APP\npython3 -m http.server $PORT > /dev/null 2>&1 &\n\n# 3. Wait for server\nsleep 1\n\n# 4. Navigate Canvas\nopenclaw nodes canvas navigate --node \"$NODE\" \"http://localhost:$PORT/\"\n\n# 5. Inject data\nopenclaw nodes canvas eval --node \"$NODE\" --js \"app.loadData({...})\"\n\nMethod 2: Direct HTML Injection (For Quick Displays)\n\nWhen to use: File paths don't work in Canvas (security sandboxing). Data URLs can be unreliable. Use this for instant displays without localhost.\n\n# Example using canvas tool\ncanvas.present(url=\"about:blank\", target=node_name)\n\nhtml_content = \"\"\"<!DOCTYPE html>\n<html>\n<head>\n    <style>\n        body { background: #667eea; color: white; padding: 40px; }\n        .card { background: white; color: #333; padding: 30px; border-radius: 16px; }\n    </style>\n</head>\n<body>\n    <div class=\"card\">\n        <h1>Your Content Here</h1>\n    </div>\n</body>\n</html>\"\"\"\n\n# Escape backticks and inject\njs_code = f\"\"\"document.open();\ndocument.write(`{html_content}`);\ndocument.close();\"\"\"\n\ncanvas.eval(javaScript=js_code, target=node_name)\n\n\nKey limitation: File paths (file:///path/to/file.html) are blocked in Canvas for security. Always use localhost or direct injection.\n\nBuilding Apps\nApp API Convention\n\nEvery app should expose a window.app or window.[appname] object:\n\nwindow.app = {\n  // Update values\n  setValue: (key, val) => {\n    document.getElementById(key).textContent = val;\n  },\n  \n  // Bulk update\n  loadData: (data) => { /* render all */ },\n  \n  // Notifications\n  notify: (msg) => { /* show toast */ }\n};\n\nTwo-Way Communication\n\nApps send commands back via deep links:\n\nfunction sendToAgent(message) {\n  window.location.href = `openclaw://agent?message=${encodeURIComponent(message)}`;\n}\n\n// Button click → agent command\ndocument.getElementById('btn').onclick = () => {\n  sendToAgent('Refresh my dashboard');\n};\n\nTemplates\nDashboard\n\nStats cards, progress bars, lists. Self-contained HTML.\n\nDefault port: 9876\nAPI: dashboard.setRevenue(), dashboard.setProgress(), dashboard.notify()\nTracker\n\nHabits/tasks with checkboxes and streaks. Self-contained HTML.\n\nDefault port: 9877\nAPI: tracker.setItems(), tracker.addItem(), tracker.toggleItem()\nQuick Display (A2UI)\n\nFor temporary displays without a full app:\n\nopenclaw nodes canvas a2ui push --node \"$NODE\" --text \"\n📊 QUICK STATUS\n\nRevenue: \\$500\nUsers: 100\n\nDone!\n\"\n\nPort Assignments\nApp Type\tDefault Port\nDashboard\t9876\nTracker\t9877\nTimer\t9878\nDisplay\t9879\nCustom\t9880+\nDesign System\n:root {\n  --bg-primary: #0a0a0a;\n  --bg-card: #1a1a2e;\n  --accent-green: #00d4aa;\n  --accent-blue: #4a9eff;\n  --accent-orange: #f59e0b;\n  --text-primary: #fff;\n  --text-muted: #888;\n  --border: #333;\n}\n\nBest Practices\nSelf-contained HTML — Inline CSS/JS for portability\nDark theme — Match OpenClaw aesthetic\nExpose app API — Let agent update via window.app.*\nUse IDs — On elements the agent will update\nLive clock — Shows the app is alive\nDeep links — For two-way communication\nTroubleshooting\n\nApp opens in browser instead of Canvas?\n\nMake sure you're using openclaw nodes canvas navigate, not just open\nCanvas navigate targets the Canvas panel specifically\n\n\"Not Found\" on Canvas?\n\nFile paths don't work: Canvas blocks file:/// URLs for security (sandboxing)\nData URLs may fail: Use direct HTML injection via canvas eval + document.write() instead\nFor localhost: Verify server is running: curl http://localhost:[PORT]/\nCheck port is correct\nUse http://localhost: not openclaw-canvas:// (URL scheme has issues)\n\nCanvas shows \"Not Found\" even with correct URL?\n\nThis is a security boundary: Canvas can't access local filesystem\nSolution: Use Method 2 (Direct HTML Injection) from \"Opening an App\" section\nOr serve via localhost (Method 1)\n\nApp not updating?\n\nCheck window.app API is defined: openclaw nodes canvas eval --js \"typeof window.app\"\nVerify JS eval syntax: single quotes inside double quotes\n\nServer port already in use?\n\nKill existing: lsof -ti:[PORT] | xargs kill -9\nHelper Scripts\ncanvas-inject.py\n\nPython helper for direct HTML injection (Method 2).\n\n# Example usage in Python\nfrom canvas_inject import inject_html_to_canvas\n\nhtml = open(\"my-dashboard.html\").read()\ncommands = inject_html_to_canvas(html, node_name=\"Your Node\")\n\n# Then use canvas tool with these commands\ncanvas.present(**commands[\"step1_present\"])\ncanvas.eval(**commands[\"step2_inject\"])\n\n\nOr just follow the pattern manually (see Method 2 in \"Opening an App\").\n\nRequirements\nOpenClaw with Canvas support (macOS app)\nPython 3 (for http.server)\nA paired node with canvas capability"
  },
  "trust": {
    "sourceLabel": "tencent",
    "provenanceUrl": "https://clawhub.ai/Knightluozichu/canvas-os-1-0-1",
    "publisherUrl": "https://clawhub.ai/Knightluozichu/canvas-os-1-0-1",
    "owner": "Knightluozichu",
    "version": "1.0.0",
    "license": null,
    "verificationStatus": "Indexed source record"
  },
  "links": {
    "detailUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1",
    "downloadUrl": "https://openagent3.xyz/downloads/canvas-os-1-0-1",
    "agentUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent",
    "manifestUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent.json",
    "briefUrl": "https://openagent3.xyz/skills/canvas-os-1-0-1/agent.md"
  }
}