Skip to content
Gauge

ax-check.com

Anima

useanima.sh

ax-check.com

Checked 21 September 2026

B

84/100

Agents need your login

Anima's docs, SDKs and pricing are all readable without login.

21 of 23 checklist items passed: quickstarts, CLI/SDK install, OpenAPI/MCP docs, and all four pricing tiers are stated openly with clear units.

2 fixes to start with

Concrete changes, backed by what we found.

Onboarding

Give agents a clear login handoff and a way to resume setup.

Agents cannot progress through onboarding without human help. Provide an agent-accessible path through authentication and setup.

Docs

Return Markdown when clients request text/markdown.

Homepage returned text/html for a text/markdown request; no Markdown representation offered.

Recorded coding sessions

Same task, 3 models, no useanima.sh account. Recorded 21 September 2026 on Pi.

3 recorded · 10m 47s

10m 47s · recorded

Session findings

Select a finding to see it in context.

piv0.84.2
modelQwen 3.8 Maxcwd/sandbox/repo
Help me build a simple example using Anima. Tell me how pricing works, and briefly tell me whether this product will be easy for you to manage. Let me know if you get blocked. If this product has no developer workflow you can act on, say so plainly and stop. Stay light: use the hosted product through its SDK or API. Do not start local service stacks or wait for long-running commands; if the quickstart requires either, say so plainly and stop.
Thinking…

I'm not familiar with Anima as a product, so I need to explore the repository to understand what it does.

$ ls -la /sandbox/repo && cat /sandbox/repo/README* 2>/dev/null | head -100{"content":[{"text":"total 16\ndrwxr-xr-x 3 root root 4096 Sep 18 08:00 .\ndrwxr-xr-x 7 root root 4096 Sep 21 12:50 ..\ndrwxr-xr-x 8 root root 4096 Sep 18 08:00…ctrl+o
{"content":[{"text":"total 16\ndrwxr-xr-x 3 root root 4096 Sep 18 08:00 .\ndrwxr-xr-x 7 root root 4096 Sep 21 12:50 ..\ndrwxr-xr-x 8 root root 4096 Sep 18 08:00 .git\n-rw-r--r-- 1 root root  408 Sep 18 08:00 .gitignore\n","type":"text"}]}
Thinking…

Empty repo. "Anima" — ambiguous. Could be several products: Anima App (design-to-code, Figma to React), or Anima (a Rust-based ML?). Let me check git history and any clues.

$ cd /sandbox/repo && git log --oneline | head -20; cat .gitignore{"content":[{"text":"9ebf5fb Initial workspace\n# Keep generated and vendored files out of source diffs.\n\n# Logs / OS cruft\n*.log\n.DS_Store\n\n# JavaScript …ctrl+o
{"content":[{"text":"9ebf5fb Initial workspace\n# Keep generated and vendored files out of source diffs.\n\n# Logs / OS cruft\n*.log\n.DS_Store\n\n# JavaScript / TypeScript\nnode_modules/\n.next/\ndist/\nbuild/\ncoverage/\n\n# Python\n.venv/\nvenv/\n__pycache__/\n*.py[cod]\n.pytest_cache/\n*.egg-info/\n\n# Rust\ntarget/\n\n# Go / PHP / Ruby vendored deps\nvendor/\n.bundle/\n\n# Java / Kotlin / Scala\n.gradle/\n\n# .NET\nbin/\nobj/\n\n# Elixir\n_build/\ndeps/\n\n# Dart / Flutter\n.dart_tool/\n","type":"text"}]}
Thinking…

The repo is empty. There's no indication of which "Anima" product. I need to determine what "Anima" is. The most likely well-known product named Anima with an SDK/API and pricing: animaapp.com — design-to-code (Figma to HTML/React/Vue), has an API (Anima API / Code Export API) and pricing plans. There's also "Anima" by... hmm.

I should check whether I have network access to check docs, and whether there's an API key available.

But important: I should be honest about ambiguity. Let me check network access.

$ env | grep -iE "anima|api_key|token" | sed 's/=.*/=<redacted>/'; echo "---"; timeout 12 curl -sS -o /dev/null -w "%{http_code}\n" https://registry.npmjs.org/anima 2>&1; timeout 12 curl -sS -o /dev/nul…{"content":[{"text":"PI_GATEWAY_API_KEY=<redacted>\n---\n200\n404\n","type":"text"}]}ctrl+o
env | grep -iE "anima|api_key|token" | sed 's/=.*/=<redacted>/'; echo "---"; timeout 12 curl -sS -o /dev/null -w "%{http_code}\n" https://registry.npmjs.org/anima 2>&1; timeout 12 curl -sS -o /dev/null -w "%{http_code}\n" https://pypi.org/pypi/anima/json 2>&1

Thinking…

Network works. npm has a package "anima"? Let's check what it is. But careful — the name may be a squatter. Let me look at npm search for anima-related packages and PyPI for anima-app.

Let me be careful not to install random packages. Let me query npm registry metadata.

$ cd /tmp && timeout 20 curl -sS https://registry.npmjs.org/anima | python3 -c "{"content":[{"text":"anima CSS/JS Animations Library with Physics support\nlatest: {'latest': '0.4.0'}\nrepo: {'type': 'git', 'url': 'https://github.com/lvivski…ctrl+o
cd /tmp && timeout 20 curl -sS https://registry.npmjs.org/anima | python3 -c "
import json,sys
d=json.load(sys.stdin)
print(d.get('name'), d.get('description'))
print('latest:', d.get('dist-tags'))
print('repo:', d.get('repository'))
print('homepage:', d.get('homepage'))
vs=list(d.get('versions',{}).keys())
print('versions:', vs[-5:])
print('modified:', d.get('time',{}).get('modified'))
"
echo "=== search ==="
timeout 20 curl -sS "https://registry.npmjs.org/-/v1/search?text=anima&size=12" | python3 -c "
import json,sys
for o in json.load(sys.stdin)['objects']:
    p=o['package']; print(p['name'],'|',p['version'],'|',(p.get('description') or '')[:90])
"

{"content":[{"text":"anima CSS/JS Animations Library with Physics support\nlatest: {'latest': '0.4.0'}\nrepo: {'type': 'git', 'url': 'https://github.com/lvivski/anima.git'}\nhomepage: https://github.com/lvivski/anima\nversions: ['0.3.5', '0.3.6', '0.3.7', '0.3.10', '0.4.0']\nmodified: 2022-06-13T03:03:38.895Z\n=== search ===\nanima | 0.4.0 | CSS/JS Animations Library with Physics support\nanima-storybook-cli | 0.13.1 | Anima CLI for storybook\nanima-ds-nucleus | 1.0.154 | Anima Design System - A comprehensive React component library\n@meetquinn/animactl | 0.1.29 | Operator CLI for installing and running Anima.\n@anima-protocol/anima | 0.1.7 | Anima.js is a JavaScript library for interacting with the Anima Protocol.\n@animahealth/adk | 0.6.0 | Anima Agent Development Kit - Framework for building production-grade multi-agent AI syste\n@animaapp/playground-sdk | 0.12.1-canary.20a2a4208 | Playground SDK for Anima\nbabel-storybook-anima | 0.4.0 | A babel plugin for storybook anima\nanima-template | 1.0.12 | Anima template\n@animaapp/anima-cli | 1.1.3 | Anima CLI for storybook\n@s0nderlabs/anima | 0.26.0 | anima CLI: sovereign agent gateway on 0G. Runs `anima init` to mint an iNFT and bring up y\n@animaapp/playground-react-sdk | 0.12.1-canary.20a2a4208 | Playground React SDK for Anima\n","type":"text"}]}
Thinking…

"Anima" is ambiguous — many products. The user said "build a simple example using Anima", "tell me how pricing works", "whether this product will be easy for you to manage", "use the hosted product through its SDK or API", "do not start local service stacks".

This phrasing suggests a hosted SaaS product. Candidates:

  1. Anima App (animaapp.com) — Figma-to-code, has a Playground SDK, Code Export API, pricing tiers (Free/Pro/Business/Enterprise).
  2. Anima Protocol (@anima-protocol) — identity protocol on Polygon.
  3. Anima Health ADK — agent framework.
  4. s0nderlabs anima — "sovereign agent gateway on 0G" — requires running local nodes → excluded by constraint.
  5. @meetquinn/animactl — "Operator CLI for installing and running Anima" — local install → excluded.

Given "pricing works" and "hosted product through its SDK or API", Anima App is the most plausible well-known one: it's a hosted product with a documented Code Export API (api.animaapp.com) and clear public pricing. And its SDKs (playground-sdk) exist on npm.

But I should not guess and burn effort. Actually the task says: if blocked, tell them. Also: "If this product has no developer workflow you can act on, say so plainly and stop."

Let me investigate quickly: check animaapp's API docs and pricing page, and the playground-sdk on npm to see if it's usable without local stacks. Let me do a quick fetch.

Note the repo is empty with no clues — I should flag the ambiguity but still deliver something concrete. Let me check the actual docs.

$ cd /tmp && for u in https://www.animaapp.com https://docs.animaapp.com https://api.animaapp.com; do echo "== $u"; timeout 15 curl -sSL -o /dev/null -w "%{http_code} %{url_effective}\n" "$u"; done{"content":[{"text":"== https://www.animaapp.com\n200 https://www.animaapp.com/\n== https://docs.animaapp.com\n200 https://docs.animaapp.com/docs/sign-up-to-ani…ctrl+o
cd /tmp && for u in https://www.animaapp.com https://docs.animaapp.com https://api.animaapp.com; do echo "== $u"; timeout 15 curl -sSL -o /dev/null -w "%{http_code} %{url_effective}\n" "$u"; done
echo "=== npm pkg: playground-sdk ==="
timeout 20 curl -sS https://registry.npmjs.org/@animaapp%2Fplayground-sdk | python3 -c "
import json,sys
d=json.load(sys.stdin)
l=d['dist-tags']['latest']; v=d['versions'][l]
print(d.get('description')); print('latest',l); print('repo',v.get('repository')); print('homepage',v.get('homepage'))
print('deps',v.get('dependencies')); print('keywords',v.get('keywords'))
print('time', d['time'].get(l))
"

{"content":[{"text":"== https://www.animaapp.com\n200 https://www.animaapp.com/\n== https://docs.animaapp.com\n200 https://docs.animaapp.com/docs/sign-up-to-anima\n== https://api.animaapp.com\n200 https://www.animaapp.com/\n=== npm pkg: playground-sdk ===\nPlayground SDK for Anima\nlatest 0.12.1-canary.20a2a4208\nrepo {'url': 'git+https://github.com/AnimaApp/anima-design-to-code.git', 'type': 'git', 'directory': 'playground-db/sdk'}\nhomepage https://github.com/AnimaApp/anima-design-to-code#readme\ndeps {'zod': '^4.3.6', 'crypto-js': '^4.2.0'}\nkeywords None\ntime 2026-04-22T11:46:47.684Z\n","type":"text"}]}
Thinking…

Anima App is live. Let me check its docs for a code export API / SDK and pricing. Let me fetch docs pages.

$ cd /tmp && timeout 20 curl -sSL https://docs.animaapp.com/docs/sign-up-to-anima -o d.html -w "%{http_code}\n"; wc -c d.html; python3 - <<'EOF'{"content":[{"text":"200\n166272 d.html\n/docs/1\n/docs/1-anima-teams\n/docs/1-code-settings\n/docs/1-full-flows-code\n/docs/1-installation-and-commands\n/docs/…ctrl+o
cd /tmp && timeout 20 curl -sSL https://docs.animaapp.com/docs/sign-up-to-anima -o d.html -w "%{http_code}\n"; wc -c d.html; python3 - <<'EOF'
import re,html
t=open('/tmp/d.html',encoding='utf-8',errors='ignore').read()
# extract links from sidebar/nav
links=set(re.findall(r'href="(/docs/[^"#?]+)"',t))
for l in sorted(links): print(l)
EOF

{"content":[{"text":"200\n166272 d.html\n/docs/1\n/docs/1-anima-teams\n/docs/1-code-settings\n/docs/1-full-flows-code\n/docs/1-installation-and-commands\n/docs/1-responsive-pages\n/docs/10-sync\n/docs/11-publish\n/docs/13-custom-domain\n/docs/2-anima-projects\n/docs/2-entrance-animation\n/docs/2-inspect-code\n/docs/2-inspect-code-1\n/docs/2-responsiveness-auto-layout\n/docs/3-copy-code\n/docs/3-copy-code-1\n/docs/3-hover-effects\n/docs/3-playground\n/docs/4-media-element\n/docs/4-open-in-playground\n/docs/4-open-in-playground-1\n/docs/4-sharing\n/docs/5-download-selection\n/docs/5-download-selection-1\n/docs/5-text-input\n/docs/6-breakpoints\n/docs/6-breakpoints-1\n/docs/6-submit-button\n/docs/7-ai-personalization\n/docs/7-ai-personalization-1\n/docs/7-embed-code\n/docs/8-preview\n/docs/9-get-code\n/docs/add-figma-design-system\n/docs/advanced-feature-create-full-flows\n/docs/anima-ai-agent-design-skill\n/docs/anima-api\n/docs/anima-mcp\n/docs/anima-webapp\n/docs/antd-ant-design-anima-for-figma-frontier-in-vscode\n/docs/app-users\n/docs/bootstrap-frontier-in-vscode\n/docs/buddy-figma-design-agent\n/docs/capture-elements\n/docs/chakra-ui-frontier-in-vscode\n/docs/chat-input-and-prompting\n/docs/chrome-extension-clone-private-internal-pages\n/docs/code-and-components-analysis\n/docs/code-injection-copy\n/docs/code-tab\n/docs/component-code-inspect\n/docs/component-matching-copy\n/docs/copy-to-figma\n/docs/database\n/docs/databases\n/docs/debug-mode\n/docs/dev-mode\n/docs/faq\n/docs/features\n/docs/figma\n/docs/figma-panels\n/docs/flow-tab\n/docs/fonts\n/docs/free-chat-bring-your-chatgpt\n/docs/getting-started\n/docs/getting-started-20\n/docs/github\n/docs/import-from-figma\n/docs/integrations\n/docs/matching-override-copy\n/docs/mui-material-ui\n/docs/plane-mode\n/docs/playground-custom-domain\n/docs/playground-faq\n/docs/preferences-settings\n/docs/preview\n/docs/project-visibility\n/docs/publish\n/docs/run-anima-inside-figma\n/docs/shadcn-figma\n/docs/shadcn-frontier-in-vscode\n/docs/sign-up-to-anima\n/docs/starting-from-a-prompt\n/docs/starting-from-a-url\n/docs/starting-from-figma\n/docs/stay-up-to-date\n/docs/tailwind-css\n/docs/team-management\n/docs/training-data-and-privacy\n/docs/translate-figma-into-code\n/docs/version-history\n","type":"text"}]}
Thinking…

There's /docs/anima-api and /docs/anima-mcp. Let's read the API doc.

$ cd /tmp && timeout 20 curl -sSL https://docs.animaapp.com/docs/anima-api -o api.html && python3 - <<'EOF'{"content":[{"text":" Anima for agents Anima API Anima’s API lets you expand your product offering by turning Figma designs or live websites into clean, product…ctrl+o
cd /tmp && timeout 20 curl -sSL https://docs.animaapp.com/docs/anima-api -o api.html && python3 - <<'EOF'
import re,html
t=open('/tmp/api.html',encoding='utf-8',errors='ignore').read()
m=re.search(r'<article.*?</article>', t, re.S) or re.search(r'<main.*?</main>', t, re.S)
s=m.group(0) if m else t
s=re.sub(r'<script.*?</script>','',s,flags=re.S)
s=re.sub(r'<[^>]+>',' ',s)
s=html.unescape(s)
s=re.sub(r'[ \t]+',' ',s)
s=re.sub(r'\n\s*\n+','\n',s)
print(s[:4000])
EOF

{"content":[{"text":" Anima for agents Anima API Anima’s API lets you expand your product offering by turning Figma designs or live websites into clean, production-ready code — ideal for automation, AI agents, and developer-facing features. /*! tailwindcss v4.1.17 | MIT License | https://tailwindcss.com */\n@layer theme, base, components, utilities;\n@layer utilities;\n 👉 To get access, contact us \n 👉 For more details, visit the Anima SDK GitHub README. \n The Anima SDK allows you to generate code from: \n Figma to Code \nGenerate high-quality code from Figma files using Anima’s codegen engine. \n Website to Code (URL → Code) \nClone any public website with HTML or React code. \n SDK \n Note : The package @animaapp/anima-sdk is designed to run on the backend. \n Settings Options \n The following options can be passed to the settings parameter when calling generateCode or generateCodeFromWebsite . \n Note : Not all options are available for both Figma designs and websites. We'll mark availability for each. \n Option Type Description language \"typescript\" | \"javascript\" The programming language to use for code generation. <br>**Note**: Only TypeScript is currently available for websites. framework \"react\" | \"html\" The framework to use for code generation. styling \"plain_css\" | \"css_modules\" | \"styled_components\" | \"tailwind\" | \"sass\" | \"scss\" | \"inline_styles\" The styling strategy for the generated code. <br>**Note**: Only `tailwind` is currently available for websites. uiLibrary \"mui\" | \"antd\" | \"radix\" | \"shadcn\" UI component library to use (React only). <br>**Note**: Only `shadcn` is currently available for websites. You may also omit this to use vanilla React. responsivePages Array<{ name: string; framesId: string[] }> Override responsive breakpoints from the plugin. <br>**Note**: Only available for Figma designs. enableTranslation boolean Enable translation support (HTML only). <br>**Note**: Only available for Figma designs. enableCompactStructure boolean Generate a more compact file structure. <br>**Note**: Only available for Figma designs. enableAutoSplit boolean Automatically split components based on complexity. <br>**Note**: Only available for Figma designs. autoSplitThreshold number Threshold for splitting components. <br>**Note**: Only available for Figma designs. disableMarkedForExport boolean Disable the \"marked for export\" feature. <br>**Note**: Only available for Figma designs. allowAutoSelectFirstNode boolean Auto-select first valid node on pages with multiple children. Default: `true`. <br>**Note**: Only available for Figma designs. enableGeneratePackageLock boolean Generate a package-lock.json file. \n Utils \n isValidFigmaUrl \n Check if a given Figma link is a valid design for code generation. \n Anima SDK for React \n We offer an official React package: @animaapp/anima-sdk-react . \n Getting Top-Level Node IDs \n To get the top-level node IDs from a Figma file, you can use the useFigmaFile hook: \n function FigmaNodeExplorer() \\{ &#x20;\n&#x20; const \\{ data, isLoading, error } = useFigmaFile(\\{\n&#x20; fileKey: \"your-figma-file-key\",\n&#x20; authToken: \"your-figma-token\",\n&#x20; params: \\{\n&#x20; depth: 2, // depth: 1 - only Pages, depth: 2 - Pages + top-level nodes\n&#x20; },\n&#x20; });\nif (isLoading) return <div>Loading Figma file...</div>;\\\nif (error) return <div>Error loading file: {error.message}</div>;\nconst pages = data?.document?.children ?? \\[];\\\nconst topLevelNodeIds = pages.flatMap((page) => page.children).map((frame) => frame.id);\nreturn (<div>\n <h3>Top-level Node IDs:</h3>\n <ul>\n {topLevelNodeIds.map(nodeId => (\n <li key={nodeId}>{nodeId}</li>\n ))}\n </ul>\n</div>);\n}```\n``` \n These node IDs can then be used in the nodesId parameter when calling generateCode() . \n Assets Storage \n The generated code may contain assets. You can choose whether to let us host them, provide you with the asset links to download and host them yourself, or return the assets together with the source files. \n ⚙️ Development \n See DEVELOPMENT.md to learn how to develo\n","type":"text"}]}
Thinking…

There's a real SDK: @animaapp/anima-sdk on npm. But "👉 To get access, contact us" — access is gated. Let me check npm for @animaapp/anima-sdk and the GitHub README. Also check pricing page.

Let me check if the SDK is publicly installable and whether an API key is required. And pricing page.

$ cd /tmp && timeout 20 curl -sS https://registry.npmjs.org/@animaapp%2Fanima-sdk | python3 -c "{"content":[{"text":"desc Anima's JavaScript utilities library\nlatest 0.27.0 time 2026-06-17T12:10:52.153Z\nrepo {'url': 'git+https://github.com/AnimaApp/anima…ctrl+o
cd /tmp && timeout 20 curl -sS https://registry.npmjs.org/@animaapp%2Fanima-sdk | python3 -c "
import json,sys
d=json.load(sys.stdin)
l=d['dist-tags']['latest']; v=d['versions'][l]
print('desc',d.get('description'));print('latest',l,'time',d['time'].get(l))
print('repo',v.get('repository'));print('homepage',v.get('homepage'))
print('deps',v.get('dependencies'));print('main',v.get('main'),'exports',list((v.get('exports') or {}).keys()))
print('versions',list(d['versions'])[-8:])
"
echo "=== pricing ==="
timeout 20 curl -sSL https://www.animaapp.com/pricing -o pr.html -w "%{http_code}\n"

{"content":[{"text":"desc Anima's JavaScript utilities library\nlatest 0.27.0 time 2026-06-17T12:10:52.153Z\nrepo {'url': 'git+https://github.com/AnimaApp/anima-sdk.git', 'type': 'git'}\nhomepage https://github.com/AnimaApp/anima-sdk#readme\ndeps {'zod': '^4.3.6', 'pako': '^2.1.0', 'deepcopy': '^2.1.0', '@figma/rest-api-spec': '^0.27.0'}\nmain None exports ['import', 'require']\nversions ['0.23.2', '0.23.5', '0.23.7', '0.24.0-wip', '0.24.0', '0.25.0', '0.26.0', '0.27.0']\n=== pricing ===\n200\n","type":"text"}]}
Thinking…

The SDK is public on npm. Now let me read the GitHub README for anima-sdk to build a correct example, and extract pricing from the pricing page.

Let me fetch the README from raw.githubusercontent.com.

$ cd /tmp && timeout 20 curl -sSL https://raw.githubusercontent.com/AnimaApp/anima-sdk/main/README.md -o sdk-readme.md -w "%{http_code}\n"; wc -l sdk-readme.md; head -120 sdk-readme.md{"content":[{"text":"200\n608 sdk-readme.md\n# Anima SDK\n\n<img src=\"https://avatars.githubusercontent.com/u/20587282?s=200&v=4\" align=\"right\" />\n\n> Desi…ctrl+o
{"content":[{"text":"200\n608 sdk-readme.md\n# Anima SDK\n\n<img src=\"https://avatars.githubusercontent.com/u/20587282?s=200&v=4\" align=\"right\" />\n\n> Design to code, automated\n\nThe Anima SDK enables seamless code generation from multiple sources:\n\n* **Figma** → Transform Figma designs into high-quality code.\n* **Websites** → Convert websites from URLs or MHTML payloads into high-quality code.\n* **Prompts** (Early Preview) → Generate a webapp from natural language descriptions\n\n**Converting non-public websites into code, using mhtml or other  ways  requires a specific license from Anima, please contact us.**\n\n## Setup Overview\n\nWe provide two packages for API integration: `anima-sdk` and `anima-sdk-react`.\n\nThe `anima-sdk` package is designed for server-side use, while `anima-sdk-react` is optimized for React applications.\n\nFor security best practices, we recommend creating an `Anima` instance from `anima-sdk` on your backend to keep your Anima token private. Create a middleware endpoint on your backend following this pattern:\n\n```mermaid\nsequenceDiagram\n    Frontend->>+Backend: Request a new code generation job\n    Backend->>Anima: Forward this request to Anima\n    loop SSE\n        Anima->>Backend: Send updates about the job\n        Backend->>Frontend: Send updates about the job\n    end\n```\n\nTo simplify frontend integration, we provide `anima-sdk-react`, which initiates requests and processes [SSE](https://developer.mozilla.org/en-US/docs/Web/API/Server-sent_events/Using_server-sent_events) messages from your backend.\n\nLet's explore each package in detail.\n\n## `anima-sdk`\n\n### Installing the Anima SDK\n\nThe Anima SDK is hosted on NPM, so you can add it to your project with:\n\n```npm i @animaapp/anima-sdk```\n\n### Code Generation Examples\n\nCheck [`example-server`](/example-server) for a tiny implementation of an endpoint that calls the Anima API.\n\nBelow are code examples for generating code from different sources.\n\n#### Convert Figma Designs to Code\n\n```ts\nimport { Anima } from \"@animaapp/anima-sdk\";\n\nconst anima = new Anima({\n  auth: {\n    token: \"Your Anima Token\",\n    userId: \"x\", // Optional, only used if you want to link the request to an external id\n  },\n});\n\nconst { files } = await anima.generateCode({\n  fileKey: \"Figma Design Key\",\n  figmaToken: \"Your Figma Token\",\n  nodesId: [\"1:2\"],\n  settings: {\n    language: \"typescript\",\n    framework: \"react\",\n    styling: \"tailwind\",\n    uiLibrary: \"shadcn\",\n    codegenSettings: {\n      timeoutMs: 60_000,\n    },\n  },\n  tracking: {\n    externalId: \"x\", // Optional, used to override the userId from auth, if provided\n  },\n});\n\nconsole.log(files); // High-quality React code from your Figma design!\n```\n\nFor Figma imports (F2C), `settings.codegenSettings.timeoutMs` sets the maximum job duration in milliseconds. It must be an integer from 1 to 300,000; when omitted, the server default applies.\n\n#### Convert Websites to Code\n\n```ts\nimport { Anima } from \"@animaapp/anima-sdk\";\n\nconst anima = new Anima({\n  auth: {\n    token: \"Your Anima Token\",\n    userId: \"x\", // Optional, only used if you want to link the request to an external id\n  },\n});\n\nconst { files } = await anima.generateCodeFromWebsite({\n  url: \"https://www.example.com\", // The URL of the website to convert\n  settings: {\n    framework: \"react\",\n    language: \"typescript\",\n    styling: \"tailwind\",\n  },\n  tracking: {\n    externalId: \"x\", // Optional, used to override the userId from auth, if provided\n  },\n});\n\nconsole.log(files); // High-quality React code from your website!\n```\n\n##### Website Scraping Limits\n\nWebsite imports support optional scraping limits through `settings.codegenSettings`:\n\n```ts\nconst { files } = await anima.generateCodeFromWebsite({\n  url: \"https://www.example.com\",\n  settings: {\n","type":"text"}]}
Thinking…

Good. Now pricing. Let me extract text from the pricing page. Also check the README for any pricing/token info and the "example-server" directory.

Let me parse pricing page HTML.

$ cd /tmp && python3 - <<'EOF'{"content":[{"text":"194\nPricing Plans - Anima\nAgentGrid.io:\nA shared drive for humans and agents\nGet it now →\nAgentGrid.io:\nA drive for humans and agents…ctrl+o
cd /tmp && python3 - <<'EOF'
import re,html
t=open('/tmp/pr.html',encoding='utf-8',errors='ignore').read()
t=re.sub(r'<script.*?</script>','',t,flags=re.S)
t=re.sub(r'<style.*?</style>','',t,flags=re.S)
t=re.sub(r'<[^>]+>','\n',t)
t=html.unescape(t)
lines=[l.strip() for l in t.split('\n') if l.strip()]
print(len(lines))
print('\n'.join(lines[:250]))
EOF

{"content":[{"text":"194\nPricing Plans - Anima\nAgentGrid.io:\nA shared drive for humans and agents\nGet it now →\nAgentGrid.io:\nA drive for humans and agents\nGet it →\nClone website\nClone any website\nClone private websites\nImage to HTML\nFigma to code\nFigma to code\nFigma to HTML\nFigma to React\nAdobe XD to HTML/React\nAgentGrid.io\nAgentGrid.io - Shared workspace for humans and agents\nAgents\nAI Website Builder\nBuddy: Figma Agent\nAnima MCP\nAnima API\nDesign agent skill\nBlog\nPricing\nLogin\nSignup\nClone website\nClone any website\nClone private websites\nImage to HTML\nFigma to code\nFigma to code\nFigma to HTML\nFigma to React\nAdobe XD to HTML/React\nAgentGrid.io\nAgentGrid.io - Shared workspace for humans and agents\nAgents\nAI Website Builder\nBuddy: Figma Agent\nAnima MCP\nAnima API\nDesign agent skill\nBlog\nPricing\nLogin\nSignup\nForget token anxiety. Focus on your creativity.\nBuild freely with simple, predictable pricing\nTrusted by the leading Vibe Coding platforms and over 1.5M Figma users\nFrequently asked questions\nWhat's included in the Free plan?\nOn the Free plan, you get 5 chat messages per day in the AI Playground, 5 Figma design imports or website clones in the AI Playground, and 5 code generations in the Figma plugin.\nWhat are code generations?\nA code generation counts each time Anima produces code for you — whether you're exporting from the Figma plugin, importing a design into the Playground, cloning a website, generating from a prompt, or using the Anima MCP server.\nDoes Anima offer an Enterprise Plan?\nYes! Anima's Enterprise plan offers SSO, MFA, Enterprise grade SLAs, and better security required for compliance. The plan starts at $500/mo paid annually.\nContact sales\nDoes Anima offer an API?\nYes! Anima’s API and SDK let you automate code generation from Figma designs, website clones, or prompts.\nContact us to get access\nHow do billing and payments work?\nPlans are billed monthly or annually. You can pay with credit cards, Apple Pay, Google Pay, and for Enterprise—wire transfer or invoice are also an option.\nCan I change or cancel my plan?\nYes. You can change your plan anytime from the settings. If you upgrade, you’ll only pay the difference for the remaining time in your billing cycle. You can cancel anytime and keep access until the end of your current cycle.\nOne and a half million users\ncobi.bean\nThere’s a new one I found that actually seems like the first “Figma -> Code” plugin that works. It’s a\n@ycombinator\nproject too. It’s called\n@AnimaApp\nMiguel Fernandez\nNew\n@boltdotnew\n+\n@AnimaApp\nFigma to Code just got released. Spoiler: it’s the best tool by far right now.\nEnzo Faleiro\nYes! Anima is the only one that works perfectly!\nAditya Kumar Saroj\nAnima Playground by @AnimaApp is the best alternative to lovable_dev 's Dev Mode\ncobi.bean\nThere’s a new one I found that actually seems like the first “Figma -> Code” plugin that works. It’s a\n@ycombinator\nproject too. It’s called\n@AnimaApp\nMiguel Fernandez\nNew\n@boltdotnew\n+\n@AnimaApp\nFigma to Code just got released. Spoiler: it’s the best tool by far right now.\nEnzo Faleiro\nYes! Anima is the only one that works perfectly!\nAditya Kumar Saroj\nAnima Playground by @AnimaApp is the best alternative to lovable_dev 's Dev Mode\nAlex Shirazi\nTools I use every day:\n•ChatGPT/Claude for flows + content\n•Figma (with\n@AnimaApp\n)\nAndrew Baisden\nI tested a new Figma to Code tool by\n@AnimaApp\nwhich is the BEST design-to-code platform.\nDeepak Mathews Koshy\nI tried out a few Figma plugins to export a single page to HTML and CSS.\nThe best one, which maintained the layout and provided the most accurate version for further improvement, was @AnimaApp\nAlex Shirazi\nTools I use every day:\n•ChatGPT/Claude for flows + content\n•Figma (with\n@AnimaApp\n)\nAndrew Baisden\nI tested a new Figma to Code tool by\n@AnimaApp\nwhich is the BEST design-to-code platform.\nDeepak Mathews Koshy\nI tried out a few Figma plugins to export a single page to HTML and CSS.\nThe best one, which maintained the layout and provided the most accurate version for further improvement, was @AnimaApp\nReady to start building?\nYour path from creativity to code.\nStart now\nWe help product teams deliver the best version of their vision.\nAnima\nAbout us\nPricing\nCareers\nCopyright infringement\nAgentGrid.io\nUse Cases & Articles\nHow to export Figma to HTML\nHow to export Figma to React\nClaude Design to Figma\nClaude Design to Website\nFigma prototype to app / website\nFigma to code component\nGraphic Design in 2026\nUX Basics article\n7 Best AI wireframing tools\nAI & Design in 2026\nClaude Design review\nWhat are user flows\nGoogle IO 2026 review\nDesign & Code tools\nFigma to code plugin\nBuddy - Figma UX Generator\nClone any website\nClone private websites\nAdobe XD\nResources\nBlog\nDocumentation\nHelp Center\nChangelog\nAnima\nAbout us\nPricing\nCareers\nCopyright infringement\nAgentGrid.io\nUse Cases & Articles\nHow to export Figma to HTML\nHow to export Figma to React\nClaude Design to Figma\nClaude Design to Website\nFigma prototype to app / website\nFigma to code component\nGraphic Design in 2026\nUX Basics article\n7 Best AI wireframing tools\nAI & Design in 2026\nClaude Design review\nWhat are user flows\nGoogle IO 2026 review\nDesign & Code tools\nFigma to code plugin\nBuddy - Figma UX Generator\nClone any website\nClone private websites\nAdobe XD\nResources\nBlog\nDocumentation\nHelp Center\nChangelog\nMade with\nin TLV & NYC.\nPrivacy & Terms of Use\n© 2026 Anima | All rights reserved.\n","type":"text"}]}
Thinking…

Pricing tiers (plan names/prices) are rendered client-side (not in static HTML). Let me look for JSON in the page or a NEXT_DATA / framer data. Let me grep for "$" amounts in the raw HTML.

$ cd /tmp && grep -oE '\$[0-9]+[^"<]{0,40}' pr.html | head -40; echo "--- plans ---"; grep -oiE '(Free|Pro|Business|Enterprise|Starter|Teams)[^"<]{0,30}/?(mo|month)' pr.html | head; echo "--- json blobs…{"content":[{"text":"$500/mo paid annually.\n--- plans ---\nprovided the mo\nprovided the mo\n--- json blobs ---\n\"name\":\"Where can I see a breakdown of my t…ctrl+o
cd /tmp && grep -oE '\$[0-9]+[^"<]{0,40}' pr.html | head -40; echo "--- plans ---"; grep -oiE '(Free|Pro|Business|Enterprise|Starter|Teams)[^"<]{0,30}/?(mo|month)' pr.html | head; echo "--- json blobs ---"; grep -oE '"(planName|name|price|monthly|annual)"[^,]{0,60}' pr.html | head -30

{"content":[{"text":"$500/mo paid annually.\n--- plans ---\nprovided the mo\nprovided the mo\n--- json blobs ---\n\"name\":\"Where can I see a breakdown of my team members and costs?\"\n\"name\":\"Can I change plans after I purchase?\"\n\"name\":\"How will I be charged?\"\n\"name\":\"What forms of payment do you accept?\"\n\"name\":\"Can I cancel my plan at any time?\"\n\"name\":\"What is your return policy?\"\n","type":"text"}]}
Thinking…

Plan prices are in client-rendered content (Framer). Let me check if there's a JSON in the page with plan data, maybe in a script tag with "Framer" data or an API call. Let's grep for "generation" or "credits" or "seats".

Alternatively check the help center / pricing FAQ docs page. Let me grep the docs FAQ page for plan names and prices.

$ cd /tmp && grep -oE 'https://[^"]*(framerusercontent|\.json)[^"]*' pr.html | head -20; echo "=== faq doc ==="; timeout 20 curl -sSL https://docs.animaapp.com/docs/faq -o faq.html && python3 - <<'EOF'{"content":[{"text":"=== faq doc ===\nround\nGetting Started\nStarting from a prompt\nStarting from a URL\nChrome Extension: Clone Private & Internal Pages\nSta…ctrl+o
cd /tmp && grep -oE 'https://[^"]*(framerusercontent|\.json)[^"]*' pr.html | head -20; echo "=== faq doc ==="; timeout 20 curl -sSL https://docs.animaapp.com/docs/faq -o faq.html && python3 - <<'EOF'
import re,html
t=open('/tmp/faq.html',encoding='utf-8',errors='ignore').read()
t=re.sub(r'<script.*?</script>','',t,flags=re.S); t=re.sub(r'<style.*?</style>','',t,flags=re.S)
t=re.sub(r'<[^>]+>','\n',t); t=html.unescape(t)
lines=[l.strip() for l in t.split('\n') if l.strip()]
txt='\n'.join(lines)
import sys
i=txt.lower().find('plan')
print(txt[max(0,i-200):i+3000])
EOF

{"content":[{"text":"=== faq doc ===\nround\nGetting Started\nStarting from a prompt\nStarting from a URL\nChrome Extension: Clone Private & Internal Pages\nStarting from Figma\nImport Multi-Screen Flows (Pro)\nFeatures\nChat input and prompting\nPlan Mode\nDebug Mode\nImport from Figma\nCode Tab\nData & Users\nDatabase Management\nApp Users\nFlow tab\nPreview\nPublish\n🌐\nCustom Domain\nCapture Elements\nCopy to Figma\nVersion History\nFonts\n🆕\nAdd Figma Design System\nProject Visibility\nIntegrations\nGithub\nFigma\nTeam Management\nPlayground FAQ\nTraining data and privacy\nBYOK/ BYOM: Bring your ChatGPT subscription or API key\nBuddy - Figma Design Agent\n🤖\nBuddy – Figma AI Design Agent\nFigma plugin\nFigma\nDesign Mode:  Inspect\nCode settings\nInspect code\nCopy code\nPrompt in Playground\nDownload code\nBreakpoints\nAI Personalization\nDev Mode: Plugin\nCode settings\nInspect code\nCopy code\nPrompt in playground\nDownload selection\nBreakpoints\nAI Personalization\nDev Mode: Figma Panels\nDesign Mode: Websites & Prototypes\nResponsiveness: Breakpoints\nResponsiveness: Auto-Layout\nEntrance animation\nHover effects\nMedia element\nText input\nSubmit button\nEmbed code\nPreview\nSync\nGet code\nPublish\nCustom domain (Legacy Sync Flow)\nAnima for agents\nAnima MCP\nAnima API\nAnima CLI\nIntegrations\nTailwind CSS | Figma | VSCode\nMUI (Material-UI) | Figma | VSCode\nAntD (Ant Design) | Figma | VSCode\nShadCN | VSCode\nShadCN | Figma\nBootstrap | VSCode\nChakra UI | VSCode\nFrontier - VS Code (Legacy)\nGetting Started\nInstallation and Commands\nPreferences Settings\nCode and Components Analysis\nComponent Matching\nMatching Override\nCode Injection\nTranslate Figma Into Code\nStay Up-to-date\nFAQ\nAnima Webapp (legacy)\nAnima Webapp\nTeams\nProjects\nThe new AI Playground\nSharing\nPowered by\nFrontier - VS Code (Legacy)\nFAQ\nFrequently Asked Questions About Frontier by anima\n• What if the code component was updated?\nA\n: Frontier continuously synchronizes with your code and design files to stay updated. It automatically scans your codebase every time you open VS Code. Additionally, you can trigger a manual scan anytime using the command\nAnima: Analyse codebase\n.\n• Can Frontier detect libraries like MUI and AntD?\nA\n: Yes, Frontier can detect and seamlessly integrate with popular libraries such as MUI, AntD, and others if they are already part of your existing project. For projects that do not yet include these libraries, or to enhance detection in a new project, follow these steps:\nOpen the Library Project\n: Start by opening the project that contains the UI library (e.g., MUI, AntD) whose components you wish to use in VSCode.\nRun the Anima Command\n: Execute\nAnima: Export components Library Data\nwithin the library project. This command scans the library and generates detailed component data, storing this information in a\n.anima\nfolder created within the library project.\nCopy the\n.anima\nFolder\n: After the\nlibrary.json\nfile is generated, copy the\n.anima\nfolder from the library project to the root directory of the project where you intend to use these components.\nEnable Anima Matching\n: Placing the\n.anima\nfolder in your current project allows Anima to access the component data of the UI library. This setup lets Anima match these external library components to Figma designs, ev\n","type":"text"}]}
Thinking…

Plan prices aren't in static HTML. Pricing tier prices are client-rendered. I could try to find the pricing data via the Framer asset, but that's getting heavy. Let me try one quick approach: search for a JSON of plans within pr.html script tags containing "credits" or "seat".

Actually, let me grep for "per month" or numbers in pr.html raw.

Alternatively check help center article about pricing/plans. Or check the changelog/blog. Let me do a quick grep for numbers near "generation" in pr.html.

Honestly, I have enough on pricing qualitatively: Free plan limits (5 chat messages/day, 5 imports/clones, 5 code generations in plugin), usage metered by "code generations", Enterprise from $500/mo annual, monthly/annual billing, plan changes prorated, cancel anytime. API access = "contact us to get access" (not self-serve).

Let me make one attempt to get actual tier prices: try fetching with a headless approach? No headless browser likely. Let's check if there's a JSON in framer scripts.

$ cd /tmp && python3 - <<'EOF'{"content":[{"text":"--\ncredit >> n\\nYou’ll be able to add or remove team members at any time. When you remove or downgrade people to viewers, you’ll get cred…ctrl+o
cd /tmp && python3 - <<'EOF'
import re
t=open('/tmp/pr.html',encoding='utf-8',errors='ignore').read()
for kw in ['seat','credit','generation','per month','monthly','annual','Free','Pro','Business']:
    hits=[m.start() for m in re.finditer(kw,t)][:3]
    for h in hits:
        seg=t[max(0,h-120):h+160].replace('\n',' ')
        print(kw,'>>',seg[:260])
    print('--')
EOF

{"content":[{"text":"--\ncredit >> n\\nYou’ll be able to add or remove team members at any time. When you remove or downgrade people to viewers, you’ll get credits for your next payment.\"}]},{\"@type\":\"Question\",\"name\":\"Can I change plans after I purchase?\",\"acceptedAnswer\":[{\"@type\":\"Answer\",\"te\ncredit >> n\",\"name\":\"What forms of payment do you accept?\",\"acceptedAnswer\":[{\"@type\":\"Answer\",\"text\":\"We support payment through credit card and Paypal.\"}]},{\"@type\":\"Question\",\"name\":\"Can I cancel my plan at any time?\",\"acceptedAnswer\":[{\"@type\":\"Answer\",\"text\":\"Yes, \ncredit >> <div data-v-5f96158f=\"\" data-v-db14490c=\"\"><p data-v-5f96158f=\"\">Plans are billed monthly or annually. You can pay with credit cards, Apple Pay, Google Pay, and for Enterprise—wire transfer or invoice are also an option.</p></div></div></div></div><div class=\"\n--\ngeneration >> 5 chat messages per day in the AI Playground, 5 Figma design imports or website clones in the AI Playground, and 5 code generations in the Figma plugin.</p></div></div></div></div><div class=\"faq-item\" data-v-db14490c=\"\" data-v-58f4261a=\"\"><div class=\"faq-item\ngeneration >> 4844\" stroke=\"#FF6250\" stroke-width=\"2.15625\" stroke-linecap=\"round\" data-v-db14490c=\"\"></path></svg>     What are code generations?   </div> <div class=\"faq-item-content text-mulish-lg\" data-v-db14490c=\"\"><div class=\"faq-item-content-wrapper\" data-v-db14490c=\ngeneration >> s=\"faq-item-content-wrapper\" data-v-db14490c=\"\"><div data-v-5f96158f=\"\" data-v-db14490c=\"\"><p data-v-5f96158f=\"\">A code generation counts each time Anima produces code for you — whether you're exporting from the Figma plugin, importing a design into the Playgr\n--\n--\nmonthly >> m-content-wrapper\" data-v-db14490c=\"\"><div data-v-5f96158f=\"\" data-v-db14490c=\"\"><p data-v-5f96158f=\"\">Plans are billed monthly or annually. You can pay with credit cards, Apple Pay, Google Pay, and for Enterprise—wire transfer or invoice are also an option.</\n--\nannual >> an offers SSO, MFA, Enterprise grade SLAs, and better security required for compliance. The plan starts at $500/mo paid annually.</p><div class=\"buttons space-y-xs align-auto\" data-v-9532c03c=\"\" data-v-5f96158f=\"\"><a href=\"https://anima-forms.typeform.com/to/g\nannual >> rapper\" data-v-db14490c=\"\"><div data-v-5f96158f=\"\" data-v-db14490c=\"\"><p data-v-5f96158f=\"\">Plans are billed monthly or annually. You can pay with credit cards, Apple Pay, Google Pay, and for Enterprise—wire transfer or invoice are also an option.</p></div></d\n--\nFree >> oke=\"#FF6250\" stroke-width=\"2.15625\" stroke-linecap=\"round\" data-v-db14490c=\"\"></path></svg>     What's included in the Free plan?   </div> <div class=\"faq-item-content text-mulish-lg\" data-v-db14490c=\"\"><div class=\"faq-item-content-wrapper\" data-v-db14490c=\"\"\nFree >> s=\"faq-item-content-wrapper\" data-v-db14490c=\"\"><div data-v-5f96158f=\"\" data-v-db14490c=\"\"><p data-v-5f96158f=\"\">On the Free plan, you get 5 chat messages per day in the AI Playground, 5 Figma design imports or website clones in the AI Playground, and 5 code g\n--\nPro >> ><meta data-n-head=\"ssr\" data-hid=\"og:description\" property=\"og:description\" content=\"Unlock up to 60% savings with our Pro plan, featuring 5000 code exports/month, unlimited Figma inspects, and more exclusive benefits. Elevate your projects with Anima's advan\nPro >> t today! \"><meta data-n-head=\"ssr\" data-hid=\"description\" name=\"description\" content=\"Unlock up to 60% savings with our Pro plan, featuring 5000 code exports/month, unlimited Figma inspects, and more exclusive benefits. Elevate your projects with Anima's advan\nPro >> s\"==e[n]||1==e[n]||1==e.msDoNotTrack||t[o]&&t[o][a]&&t[o][a]()?1:0}(window,navigator,\"doNotTrack\",\"external\",\"msTrackingProtectionEnabled\"),function(o,a,i,r,g){o[g]={},o._gtm_inject=function(t){var e,n;o.doNotTrack||o[g][t]||(o[g][t]=1,o[r]=o[r]||[],o[r].push(\n--\n--\n","type":"text"}]}
Thinking…

Good: "Pro plan, featuring 5000 code exports/month, unlimited Figma inspects". Plan cards rendered client-side but there might be an API endpoint for plans. I have enough for a qualitative pricing summary. I'll be honest that exact tier prices are rendered client-side and I couldn't extract them from the static page (only Free limits, Pro ~5000 exports/mo, Enterprise from $500/mo annual).

Now: build a simple example. Constraint: "use the hosted product through its SDK or API. Do not start local service stacks or wait for long-running commands."

Anima SDK is a hosted API — npm package, calls Anima's API with a token. A "simple example" = a small Node script that calls generateCodeFromWebsite. But it requires an Anima token, which is gated ("contact us to get access"). No ANIMA token in env. So the example can be written and type-checked but not executed end-to-end without a token.

Let me build it: a small TypeScript/Node project in /sandbox/repo with:

  • package.json depending on @animaapp/anima-sdk
  • src/generate.ts using generateCodeFromWebsite (no Figma token needed → simplest)
  • writes output files to out/
  • .env.example with ANIMA_TOKEN
  • README with pricing notes & how to run

Should I npm install? That's not a local service stack; it's a dependency install. It might take a while but is fine (short). Let's try — it lets me verify the API surface (types, exports) so the example actually compiles. Keep it light: install only that package, no dev server.

Let me check node/npm availability.

$ node -v; npm -v; ls /usr/local/lib/node_modules 2>/dev/null{"content":[{"text":"v22.23.2\n10.9.8\n@anthropic-ai\n@earendil-works\n@openai\ncorepack\nnpm\n","type":"text"}]}
Thinking…

Let me set up the project and install just @animaapp/anima-sdk (and typescript? maybe skip tsc to stay light — but type checking is useful). Install sdk only, plus typescript as dev dep is ~ fine. Let's keep light: install the SDK, verify exports via node, then write the example in JS/TS with tsx? Avoid extra deps. I'll write TypeScript but verify the API surface by importing the package in Node directly (it's ESM/CJS both). Then use node --experimental-strip-types? Node 22.23 supports type stripping with --experimental-strip-types (stable-ish in 22.18+ as --experimental-strip-types; actually Node 22.18 enables type stripping by default). Let me test.

Let's do the install.

$ cd /sandbox/repo && npm init -y >/dev/null 2>&1 && timeout 180 npm i @animaapp/anima-sdk 2>&1 | tail -5{"content":[{"text":"\n2 packages are looking for funding\n run `npm fund` for details\n\nfound 0 vulnerabilities\n","type":"text"}]}
Thinking…

Installed. Now inspect the exports and types to write accurate code.

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk && cat package.json | python3 -c "import json,sys; d=json.load(sys.stdin); print(d['version']); print(json.dumps(d.get('exports'),indent=1)); print(d.…{"content":[{"text":"0.27.0\n{\n \"import\": \"./dist/index.js\",\n \"require\": \"./dist/index.cjs\"\n}\n./dist/index.d.ts\n=== files ===\ndist\npackage.json\n…ctrl+o
cd /sandbox/repo/node_modules/@animaapp/anima-sdk && cat package.json | python3 -c "import json,sys; d=json.load(sys.stdin); print(d['version']); print(json.dumps(d.get('exports'),indent=1)); print(d.get('types'))"; echo "=== files ==="; ls; echo "=== d.ts surface ==="; ls dist 2>/dev/null | head

{"content":[{"text":"0.27.0\n{\n \"import\": \"./dist/index.js\",\n \"require\": \"./dist/index.cjs\"\n}\n./dist/index.d.ts\n=== files ===\ndist\npackage.json\n=== d.ts surface ===\nindex.cjs\nindex.cjs.map\nindex.d.ts\nindex.js\nindex.js.map\n","type":"text"}]}
Thinking…

Interesting: no "types" export mapping but "types": "./dist/index.d.ts". Let me look at the d.ts for Anima class, generateCodeFromWebsite signature, and result shape (files).

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk && wc -l dist/index.d.ts && grep -nE "declare class Anima|generateCodeFromWebsite|generateCode\(|type AnimaInit|interface AnimaInit|CodegenResponse|fi…{"content":[{"text":"906 dist/index.d.ts\n5:export declare class Anima {\r\n16: generateCode(params: GetCodeParams, handler?: GetCodeHandler, signal?: AbortS…ctrl+o
cd /sandbox/repo/node_modules/@animaapp/anima-sdk && wc -l dist/index.d.ts && grep -nE "declare class Anima|generateCodeFromWebsite|generateCode\(|type AnimaInit|interface AnimaInit|CodegenResponse|files:|getFigmaFile|class Anima" dist/index.d.ts | head -40

{"content":[{"text":"906 dist/index.d.ts\n5:export declare class Anima {\r\n16:    generateCode(params: GetCodeParams, handler?: GetCodeHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n17:    generateCodeFromWebsite(params: GetCodeFromWebsiteParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n53:     * @deprecated This method will be removed soon, please use `generateCodeFromWebsite` instead.\r\n65:    files: AnimaFiles;\r\n146:    files: Record<string, {\r\n248:export declare const createCodegenResponseEventStream: (anima: Anima, params: GetCodeParams) => Promise<Response>;\r\n358:    files: AnimaFiles;\r\n388:        files: AnimaFiles;\r\n453:        files: AnimaFiles;\r\n514:        files: AnimaFiles;\r\n553:    files: AnimaFiles;\r\n","type":"text"}]}
Thinking…

Let me read key type definitions: Anima constructor params, GetCodeFromWebsiteParams, AnimaSDKResult, AnimaFiles, and handlers.

read /sandbox/repo/node_modules/@animaapp/anima-sdk/dist/index.d.ts{"content":[{"text":"import { GetFileResponse } from '@figma/rest-api-spec';\r\nimport { GetMeResponse } from '@figma/rest-api-spec';\r\nimport { Node as Node_2…ctrl+o
{"content":[{"text":"import { GetFileResponse } from '@figma/rest-api-spec';\r\nimport { GetMeResponse } from '@figma/rest-api-spec';\r\nimport { Node as Node_2 } from '@figma/rest-api-spec';\r\n\r\nexport declare class Anima {\r\n    #private;\r\n    constructor({ auth, apiBaseAddress, figmaRestApi, }?: {\r\n        auth?: Auth;\r\n        apiBaseAddress?: string;\r\n        path?: string;\r\n        figmaRestApi?: FigmaRestApi;\r\n    });\r\n    protected hasAuth(): boolean;\r\n    set auth(auth: Auth);\r\n    protected get headers(): Record<string, string>;\r\n    generateCode(params: GetCodeParams, handler?: GetCodeHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n    generateCodeFromWebsite(params: GetCodeFromWebsiteParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n    discoverSubpages(params: DiscoverSubpagesParams, signal?: AbortSignal): Promise<DiscoverSubpagesResult>;\r\n    /**\r\n     * Generates code from a text prompt using AI.\r\n     *\r\n     * This method sends a prompt to the Anima API and generates code based on the description provided.\r\n     * It supports real-time streaming of the generation process through Server-Sent Events (SSE).\r\n     *\r\n     * @param params - The parameters for code generation\r\n     * @param params.prompt - The text prompt describing what code to generate\r\n     * @param params.settings - Code generation settings (framework, language, styling, etc.)\r\n     * @param params.assetsStorage - Optional asset storage configuration\r\n     * @param params.tracking - Optional tracking information\r\n     * @param params.webhookUrl - Optional webhook URL for completion notification\r\n     * @param handler - Event handler for processing SSE messages during generation\r\n     * @param signal - Optional AbortSignal to cancel the request\r\n     * @returns Promise resolving to AnimaSDKResult with generated files and metadata\r\n     *\r\n     * @example\r\n     * ```typescript\r\n     * const result = await anima.generateCodeFromPrompt({\r\n     *   prompt: \"Create a login form with email and password fields\",\r\n     *   settings: {\r\n     *     framework: \"react\",\r\n     *     language: \"typescript\",\r\n     *     styling: \"tailwind\"\r\n     *   }\r\n     * }, {\r\n     *   onStart: ({ sessionId }) => console.log(\"Started:\", sessionId),\r\n     *   onGeneratingCode: ({ progress }) => console.log(\"Progress:\", progress),\r\n     *   onCodegenCompleted: () => console.log(\"Generation completed!\")\r\n     * });\r\n     * ```\r\n     */\r\n    generateCodeFromPrompt(params: GetCodeFromPromptParams, handler?: GetCodeFromPromptHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n    /**\r\n     * @deprecated This method will be removed soon, please use `generateCodeFromWebsite` instead.\r\n     */\r\n    generateLink2Code(params: GetLink2CodeParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n    attachToGenerationJob<T extends SSEGetCodeFromFigmaMessage | SSEGetCodeFromWebsiteMessage | SSEGetCodeFromPromptMessage>(params: AttachToGenerationJobParams, handler?: ((message: T) => void) | Record<string, any>, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n}\r\n\r\nexport declare type AnimaFiles = Record<string, {\r\n    content: string;\r\n    isBinary: boolean;\r\n}>;\r\n\r\nexport declare type AnimaSDKResult = BaseResult & {\r\n    files: AnimaFiles;\r\n    assets?: Array<{\r\n        name: string;\r\n        url: string;\r\n    }>;\r\n    /**\r\n     * Image-mode only.\r\n     */\r\n    viewport?: ImageToCodeViewport;\r\n    viewportReason?: string;\r\n};\r\n\r\nexport declare type AssetsStorage = {\r\n    strategy: \"host\";\r\n} | {\r\n    strategy: \"external\";\r\n    url: string;\r\n};\r\n\r\nexport declare type AttachToGenerationJobParams = {\r\n    sessionId: string;\r\n};\r\n\r\n/**\r\n * Creates a Server-Sent Events (SSE) `Response` that forwards all messages from the code generation stream.\r\n *\r\n * But, if the first message indicates an error (e.g., connection failed), the function returns a 500 response with the error message.\r\n *\r\n * @param {Anima} anima - The Anima instance to use for creating the data stream.\r\n * @param {GetCodeFromPromptParams} params - The parameters for the code generation request.\r\n * @returns {Promise<Response>} - A promise that resolves to an HTTP response.\r\n */\r\nexport declare const attachToGenerationJobResponseEventStream: (anima: Anima, params: AttachToGenerationJobParams) => Promise<Response>;\r\n\r\n/**\r\n * Creates a ReadableStream to output code generation result.\r\n *\r\n * The stream is closed when the code generation ends.\r\n *\r\n * @param {Anima} anima - An Anima service instance to generate the code from.\r\n * @param {GetCodeFromPromptParams} params - Parameters required for the code generation process.\r\n * @returns {ReadableStream<StreamCodeFromPromptMessage>} - A ReadableStream that emits messages related to the code generation process.\r\n */\r\nexport declare const attachToGenerationJobStream: (anima: Anima, params: AttachToGenerationJobParams) => ReadableStream<StreamCodgenMessage | StreamCodeFromWebsiteMessage | StreamCodeFromPromptMessage>;\r\n\r\nexport declare type Auth = {\r\n    token: string;\r\n    teamId: string;\r\n} | {\r\n    token: string;\r\n    userId?: string;\r\n};\r\n\r\nexport declare type BaseResult = {\r\n    sessionId: string;\r\n    figmaFileName?: string;\r\n\n[787 more lines in file. Use offset=121 to continue.]","type":"text"}]}
Thinking…

There's also generateCodeFromPrompt — the simplest example (no Figma, no URL). That's a great "simple example": prompt → React code. But it's "Early Preview".

Let me look at GetCodeFromPromptParams and GetCodeFromWebsiteParams and handler types.

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk/dist && grep -n "GetCodeFromPromptParams\|GetCodeFromWebsiteParams\|GetCodeFromPromptHandler\|GetCodeFromWebsiteHandler\|SettingsCodegen\|declare type…{"content":[{"text":"17: generateCodeFromWebsite(params: GetCodeFromWebsiteParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaS…ctrl+o
cd /sandbox/repo/node_modules/@animaapp/anima-sdk/dist && grep -n "GetCodeFromPromptParams\|GetCodeFromWebsiteParams\|GetCodeFromPromptHandler\|GetCodeFromWebsiteHandler\|SettingsCodegen\|declare type Settings" index.d.ts | head -20

{"content":[{"text":"17:    generateCodeFromWebsite(params: GetCodeFromWebsiteParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n51:    generateCodeFromPrompt(params: GetCodeFromPromptParams, handler?: GetCodeFromPromptHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n55:    generateLink2Code(params: GetLink2CodeParams, handler?: GetCodeFromWebsiteHandler, signal?: AbortSignal): Promise<AnimaSDKResult>;\r\n94: * @param {GetCodeFromPromptParams} params - The parameters for the code generation request.\r\n105: * @param {GetCodeFromPromptParams} params - Parameters required for the code generation process.\r\n199: * @param {GetCodeFromPromptParams} params - The parameters for the code generation request.\r\n202:export declare const createCodeFromPromptResponseEventStream: (anima: Anima, params: GetCodeFromPromptParams) => Promise<Response>;\r\n212: * @param {GetCodeFromPromptParams} params - Parameters required for the code generation process.\r\n215:export declare const createCodeFromPromptStream: (anima: Anima, params: GetCodeFromPromptParams) => ReadableStream<StreamCodeFromPromptMessage>;\r\n223: * @param {GetCodeFromWebsiteParams} params - The parameters for the code generation request.\r\n226:export declare const createCodeFromWebsiteResponseEventStream: (anima: Anima, params: GetCodeFromWebsiteParams) => Promise<Response>;\r\n234: * @param {GetCodeFromWebsiteParams} params - Parameters required for the code generation process.\r\n237:export declare const createCodeFromWebsiteStream: (anima: Anima, params: GetCodeFromWebsiteParams) => ReadableStream<StreamCodeFromWebsiteMessage>;\r\n371:export declare type GetCodeFromPromptHandler = ((message: SSEGetCodeFromPromptMessage) => void) | {\r\n393:export declare type GetCodeFromPromptParams = {\r\n436:export declare type GetCodeFromWebsiteHandler = ((message: SSEGetCodeFromWebsiteMessage) => void) | {\r\n464:export declare type GetCodeFromWebsiteParams = {\r\n539:export declare type GetLink2CodeHandler = GetCodeFromWebsiteHandler;\r\n","type":"text"}]}
Thinking…

Let me read the relevant sections of the .d.ts for GetCodeFromWebsiteParams / GetCodeFromPromptParams and handler types to write accurate code.

read /sandbox/repo/node_modules/@animaapp/anima-sdk/dist/index.d.ts{"content":[{"text":"export declare type GeneratingCodePayload = {\r\n status: \"success\" | \"running\" | \"failure\";\r\n progress: number;\r\n files…ctrl+o
{"content":[{"text":"export declare type GeneratingCodePayload = {\r\n    status: \"success\" | \"running\" | \"failure\";\r\n    progress: number;\r\n    files: AnimaFiles;\r\n};\r\n\r\n/**\r\n * Codegen errors from the worker\r\n */\r\nexport declare type GetCodeFromFigmaErrorReason = \"Selected node type is not supported\" | \"Invisible group nodes are unsupported\" | \"Selected node is a page with multiple children\" | \"Selected node is a page with no valid children\" | \"There is no node with the given id\" | \"Invalid Figma token\" | \"Anima API connection error\" | \"Figma token expired\" | \"Invalid user token\" | \"Figma file not found\" | \"Figma rate limit exceeded\" | \"Figma selection too large\" | \"Invalid responsive page node type\" | \"Unknown\";\r\n\r\n/**\r\n * Errors from the Prompt To Code Flow\r\n */\r\nexport declare type GetCodeFromPromptErrorReason = \"Invalid prompt\" | \"Generation failed\" | \"Unknown\";\r\n\r\nexport declare type GetCodeFromPromptHandler = ((message: SSEGetCodeFromPromptMessage) => void) | {\r\n    onQueueing?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onStart?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onAssetsUploaded?: () => void;\r\n    onAssetsList?: ({ assets, }: {\r\n        assets: Array<{\r\n            name: string;\r\n            url: string;\r\n        }>;\r\n    }) => void;\r\n    onGeneratingCode?: ({ status, progress, files, }: {\r\n        status: \"success\" | \"running\" | \"failure\";\r\n        progress: number;\r\n        files: AnimaFiles;\r\n    }) => void;\r\n    onCodegenCompleted?: () => void;\r\n};\r\n\r\nexport declare type GetCodeFromPromptParams = {\r\n    prompt: string;\r\n    guidelines?: string;\r\n    images?: Array<{\r\n        url: string;\r\n    }>;\r\n    assetsStorage?: AssetsStorage;\r\n    settings: GetCodeFromPromptSettings;\r\n    tracking?: TrackingInfos;\r\n    webhookUrl?: string;\r\n};\r\n\r\nexport declare type GetCodeFromPromptSettings = BaseSettings & {\r\n    language?: \"typescript\";\r\n    framework: \"react\" | \"html\";\r\n    styling: \"tailwind\" | \"inline_styles\";\r\n    uiLibrary?: \"shadcn\" | \"custom_design_system\";\r\n    dsId?: string;\r\n    fastMode?: boolean;\r\n    /**\r\n     * Hard override for the p2c routing classifier.\r\n     *\r\n     * - `true`  — Skip the LLM-driven classifier entirely and run the\r\n     *   image-to-code sub-agent directly. **Bypasses the multi-screen\r\n     *   safety check** — the caller is responsible for ensuring the\r\n     *   attached image is a single screen, not a multi-screen prototype /\r\n     *   moodboard. Saves ~1s + a vision LLM call per request.\r\n     * - `false` — Skip the classifier and force creative mode.\r\n     * - unset   — The agent decides automatically: a vision LLM call\r\n     *   classifies the intent and downgrades multi-screen inputs to\r\n     *   creative mode as a safety net.\r\n     *\r\n     * Requires at least one attached image. With no image attached this\r\n     * field has no effect.\r\n     */\r\n    imageMode?: boolean;\r\n};\r\n\r\n/**\r\n * Errors from the Website To Code Flow\r\n */\r\nexport declare type GetCodeFromWebsiteErrorReason = \"Scraping is blocked\" | \"Unknown\";\r\n\r\nexport declare type GetCodeFromWebsiteHandler = ((message: SSEGetCodeFromWebsiteMessage) => void) | {\r\n    onQueueing?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onStart?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onAssetsUploaded?: () => void;\r\n    onAssetsList?: ({ assets, }: {\r\n        assets: Array<{\r\n            name: string;\r\n            url: string;\r\n        }>;\r\n    }) => void;\r\n    onGeneratingCode?: ({ status, progress, files, }: {\r\n        status: \"success\" | \"running\" | \"failure\";\r\n        progress: number;\r\n        files: AnimaFiles;\r\n    }) => void;\r\n    onCodegenCompleted?: () => void;\r\n};\r\n\r\nexport declare type GetCodeFromWebsiteHTMLOptimizations = {\r\n    extractInlineAssets?: boolean;\r\n    pruneComputedCSSNoise?: boolean;\r\n    factorRepeatedCSSDeclarations?: boolean;\r\n};\r\n\r\nexport declare type GetCodeFromWebsiteParams = {\r\n    url?: string;\r\n    /** @deprecated Use `mhtmlUrl` instead. */\r\n    mhtml?: string;\r\n    mhtmlUrl?: string;\r\n    assetsStorage?: AssetsStorage;\r\n    settings: GetCodeFromWebsiteSettings;\r\n    tracking?: TrackingInfos;\r\n    webhookUrl?: string;\r\n    prompt?: string;\r\n    images?: Array<{\r\n        url: string;\r\n    }>;\r\n    dsId?: string;\r\n    htmlOptimizations?: GetCodeFromWebsiteHTMLOptimizations;\r\n    subpages?: WebsiteSubpage[];\r\n    experimental_useNewReactEngine?: boolean;\r\n};\r\n\r\nexport declare type GetCodeFromWebsiteSettings = BaseSettings & {\r\n    language?: \"typescript\";\r\n    framework: \"react\" | \"html\";\r\n    styling: \"tailwind\" | \"inline_styles\" | \"vanilla_css\" | \"semantic_css\";\r\n    uiLibrary?: \"shadcn\";\r\n};\r\n\r\nexport declare type GetCodeHandler = ((message: SSEGetCodeFromFigmaMessage) => void) | {\r\n    onQueueing?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onStart?: ({ sessionId }: {\r\n        sessionId: string;\r\n    }) => void;\r\n    onPreCodegen?: ({ message }: {\r\n        message: string;\r\n    }) => void;\r\n    onAssetsUploaded?: () => void;\r\n    onAssetsList?: ({ assets, }: {\r\n        assets: Array<{\r\n            name: string;\r\n            url: string;\r\n\n[403 more lines in file. Use offset=505 to continue.]","type":"text"}]}
Thinking…

Now write the example. Plan:

/sandbox/repo

  • package.json (type: module, scripts)
  • .env.example → ANIMA_TOKEN
  • src/anima-example.ts — prompt→code (simplest, no external inputs) with a website→code variant behind a flag? Keep it simple: one file, src/generate.ts, that does website→code by default from CLI arg, since website→code is GA and prompt is "early preview". Actually simplest demo requiring no Figma: website → code. I'll support both: node src/generate.ts --url https://example.com or --prompt "...". Keep it small.

Hmm, "Stay light" — one script, plus README. Node 22 can run TS via type stripping (node 22.18+ enables by default? Node 22.18.0 enabled --experimental-strip-types by default). Let me verify quickly with a test file. If not, use --experimental-strip-types flag explicitly.

Let me verify type stripping works and also verify SDK import works.

$ cd /tmp && printf 'const x: number = 1;\nconsole.log("ts ok", x);\n' > t.ts && node t.ts 2>&1 | tail -3; cd /sandbox/repo && node -e "import('@animaapp/anima-sdk').then(m=>console.log('sdk exports:',O…{"content":[{"text":"ts ok 1\nsdk exports: [\n 'Anima',\n 'CodegenError',\n 'ExpiredFigmaToken',\n 'FigmaRestApi',\n 'FileNotExportable',\n 'MalformattedF…ctrl+o
cd /tmp && printf 'const x: number = 1;\nconsole.log("ts ok", x);\n' > t.ts && node t.ts 2>&1 | tail -3; cd /sandbox/repo && node -e "import('@animaapp/anima-sdk').then(m=>console.log('sdk exports:',Object.keys(m)))"

{"content":[{"text":"ts ok 1\nsdk exports: [\n  'Anima',\n  'CodegenError',\n  'ExpiredFigmaToken',\n  'FigmaRestApi',\n  'FileNotExportable',\n  'MalformattedFigmaToken',\n  'MissingFigmaToken',\n  'NeedsReauthFigmaToken',\n  'NotFound',\n  'RateLimitExceeded',\n  'RequestTooLarge',\n  'ResponseError',\n  'UnknownFigmaApiException',\n  'UnknownForbiddenFigmaError',\n  'attachToGenerationJobResponseEventStream',\n  'attachToGenerationJobStream',\n  'createCodeFromPromptResponseEventStream',\n  'createCodeFromPromptStream',\n  'createCodeFromWebsiteResponseEventStream',\n  'createCodeFromWebsiteStream',\n  'createCodegenResponseEventStream',\n  'createCodegenStream',\n  'createLink2CodeResponseEventStream',\n  'createLink2CodeStream',\n  'findChildrenNode',\n  'formatToFigmaLink',\n  'getRelatedScreenFiles',\n  'isNodeCodegenCompatible',\n  'isNotFound',\n  'isRateLimitExceeded',\n  'isRequestTooLarge',\n  'isUnknownFigmaApiException',\n  'isValidFigmaUrl',\n  'validateSettings'\n]\n","type":"text"}]}
Thinking…

Node runs TS natively (type stripping). SDK imports fine. Now write the example.

Files:

  • package.json (rewrite; keep anima-sdk dep, add scripts, type: module)
  • .env.example
  • src/generate.ts
  • README.md
  • .gitignore already covers node_modules

Let me check current package.json to preserve dep version.

$ cd /sandbox/repo && cat package.json{"content":[{"text":"{\n \"name\": \"repo\",\n \"version\": \"1.0.0\",\n \"description\": \"\",\n \"main\": \"index.js\",\n \"scripts\": {\n \"test\": \…ctrl+o
{"content":[{"text":"{\n  \"name\": \"repo\",\n  \"version\": \"1.0.0\",\n  \"description\": \"\",\n  \"main\": \"index.js\",\n  \"scripts\": {\n    \"test\": \"echo \\\"Error: no test specified\\\" && exit 1\"\n  },\n  \"keywords\": [],\n  \"author\": \"\",\n  \"license\": \"ISC\",\n  \"dependencies\": {\n    \"@animaapp/anima-sdk\": \"^0.27.0\"\n  }\n}\n","type":"text"}]}
Thinking…

Now write the example files.

src/generate.ts: CLI with --url or --prompt, writes files to out/. Uses handler for progress. Reads token from process.env.ANIMA_TOKEN (with dotenv? avoid extra dep — Node 22 supports --env-file). Use node --env-file=.env src/generate.ts. Good, no deps.

Write files: skip binary content (write placeholder). Let's write it.

write /sandbox/repo/package.json{"content":[{"text":"Successfully wrote 681 bytes to /sandbox/repo/package.json","type":"text"}]}
Thinking…

Now write src/generate.ts.

Design:

  • parse args: --url, --prompt, --out, --framework, --styling
  • require ANIMA_TOKEN, else exit with clear message
  • build Anima instance
  • call generateCodeFromWebsite or generateCodeFromPrompt with handler logging progress
  • write files to out dir (skip binary), print summary

Careful with type stripping: no enums/namespaces; type-only imports must use import type. Fine.

Node's --check with strip-types may not work; simplify typecheck script — remove it? Keep simple: drop typecheck script since no tsc installed. Actually I set "typecheck" with || true, which is noise. Let me rewrite package.json scripts without typecheck. I'll do that after writing generate.ts.

Also --env-file-if-exists requires Node 22.9+. We have 22.23 — fine.

Let me write the file.

write /sandbox/repo/src/generate.ts{"content":[{"text":"Successfully wrote 4060 bytes to /sandbox/repo/src/generate.ts","type":"text"}]}
Thinking…

Note: generateCodeFromPrompt settings type GetCodeFromPromptSettings allows styling "tailwind"|"inline_styles" and framework react|html — matches. Website settings allows more. But my shared settings object typed loosely — TS inference: settings is inferred as {language:"typescript", framework: "react"|"html", styling:"tailwind"|"inline_styles", assetsStorage:{strategy:"host"}, tracking:{externalId:string}}. Website settings requires framework and styling from a wider union — narrower is assignable. BaseSettings may have codegenSettings optional. Should be OK.

But note: tracking type TrackingInfos — check it accepts externalId. Let me verify BaseSettings and TrackingInfos quickly.

Also fix package.json typecheck script.

Then run without token to confirm the guard path works (no network call). And run with a fake token to see it reach the API and return an auth error — that's a real end-to-end smoke test of the hosted API without a local stack, and quick. Good idea: verifies request plumbing. It'll fail with 401/403 — acceptable and informative.

Let me check types first.

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk/dist && grep -n -A14 "declare type TrackingInfos\|declare type BaseSettings" index.d.ts{"content":[{"text":"125:export declare type BaseSettings = {\r\n126- codegenSettings?: Record<string, unknown>;\r\n127-};\r\n128-\r\n129-export declare clas…ctrl+o
{"content":[{"text":"125:export declare type BaseSettings = {\r\n126-    codegenSettings?: Record<string, unknown>;\r\n127-};\r\n128-\r\n129-export declare class CodegenError extends Error {\r\n130-    status?: number;\r\n131-    detail?: unknown;\r\n132-    constructor({ name, reason, status, detail, }: {\r\n133-        name: string;\r\n134-        reason: CommonApiError | GetCodeFromFigmaErrorReason | CodegenRouteErrorReason | SDKErrorReason | GetCodeFromWebsiteErrorReason | DiscoverSubpagesErrorReason | GetCodeFromPromptErrorReason;\r\n135-        status?: number;\r\n136-        detail?: unknown;\r\n137-    });\r\n138-}\r\n139-\r\n--\n870:export declare type TrackingInfos = {\r\n871-    externalId: string;\r\n872-};\r\n873-\r\n874-export declare class UnknownFigmaApiException extends Error {\r\n875-    constructor({ cause }: {\r\n876-        cause: unknown;\r\n877-    });\r\n878-}\r\n879-\r\n880-export declare class UnknownForbiddenFigmaError extends Error {\r\n881-    reason: string | null;\r\n882-    constructor({ reason }: {\r\n883-        reason: string | null;\r\n884-    });\r\n","type":"text"}]}
Thinking…

Types check out. Fix package.json scripts (remove bogus typecheck, add tsc-free check). Then smoke test.

I'll replace typecheck script with nothing (or a node --check? --check doesn't work for TS). Remove it.

Then run:

  1. without token → guard message.
  2. with ANIMA_TOKEN=dummy → expect auth error from API (proves request reaches hosted API). Timeout 60s.
edit /sandbox/repo/package.json{"content":[{"text":"Successfully replaced 1 block(s) in /sandbox/repo/package.json.","type":"text"}],"details":{"diff":" ...\n 6 \"description\": \"Minim…ctrl+o
{"content":[{"text":"Successfully replaced 1 block(s) in /sandbox/repo/package.json.","type":"text"}],"details":{"diff":"    ...\n  6   \"description\": \"Minimal example of generating code with the hosted Anima API via @animaapp/anima-sdk\",\n  7   \"scripts\": {\n  8     \"example:website\": \"node --env-file-if-exists=.env src/generate.ts --url https://example.com --out out/website\",\n  9     \"example:prompt\": \"node --env-file-if-exists=.env src/generate.ts --prompt \\\"A pricing page with three tiers and a monthly/annual toggle\\\" --out out/prompt\",\n-10     \"typecheck\": \"node --experimental-strip-types --check src/generate.ts || true\"\n+10     \"example:figma\": \"node --env-file-if-exists=.env src/figma.ts\"\n 11   },\n 12   \"engines\": {\n 13     \"node\": \">=22.6\"\n 14   },\n    ...","patch":"--- /sandbox/repo/package.json\n+++ /sandbox/repo/package.json\n@@ -6,9 +6,9 @@\n   \"description\": \"Minimal example of generating code with the hosted Anima API via @animaapp/anima-sdk\",\n   \"scripts\": {\n     \"example:website\": \"node --env-file-if-exists=.env src/generate.ts --url https://example.com --out out/website\",\n     \"example:prompt\": \"node --env-file-if-exists=.env src/generate.ts --prompt \\\"A pricing page with three tiers and a monthly/annual toggle\\\" --out out/prompt\",\n-    \"typecheck\": \"node --experimental-strip-types --check src/generate.ts || true\"\n+    \"example:figma\": \"node --env-file-if-exists=.env src/figma.ts\"\n   },\n   \"engines\": {\n     \"node\": \">=22.6\"\n   },\n","firstChangedLine":10}}
Thinking…

I referenced src/figma.ts in package.json but haven't written it. I said "keep light" — but a Figma example is the flagship use case and it's just another small script. Options: write it (small, ~40 lines) or remove the script. Writing it is fine and adds value; it needs FIGMA_FILE_KEY, FIGMA_TOKEN, node ids. Let me write it — small.

Actually "stay light" — two scripts is still light. I'll write src/figma.ts concisely.

Let me also write .env.example and README.md, then smoke test.

Check GetCodeParams shape for figma: fileKey, figmaToken, nodesId, settings. Let me confirm field names quickly.

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk/dist && grep -n -A22 "declare type GetCodeParams" index.d.ts; grep -n -A20 "declare type Settings =" index.d.ts | head -30{"content":[{"text":"519:export declare type GetCodeParams = {\r\n520- fileKey: string;\r\n521- figmaToken?: string;\r\n522- figmaRateLimitMaxWait?: nu…ctrl+o
{"content":[{"text":"519:export declare type GetCodeParams = {\r\n520-    fileKey: string;\r\n521-    figmaToken?: string;\r\n522-    figmaRateLimitMaxWait?: number;\r\n523-    nodesId: string[];\r\n524-    assetsStorage?: AssetsStorage;\r\n525-    settings: CodegenSettings;\r\n526-    tracking?: TrackingInfos;\r\n527-    webhookUrl?: string;\r\n528-    prompt?: string;\r\n529-    images?: Array<{\r\n530-        url: string;\r\n531-    }>;\r\n532-};\r\n533-\r\n534-export { GetFileResponse }\r\n535-\r\n536-/**\r\n537- * @deprecated This type is deprecated and will be removed soon.\r\n538- */\r\n539-export declare type GetLink2CodeHandler = GetCodeFromWebsiteHandler;\r\n540-\r\n541-/**\r\n","type":"text"}]}
Thinking…

Let me check CodegenSettings fields for figma example.

$ cd /sandbox/repo/node_modules/@animaapp/anima-sdk/dist && grep -n -A25 "declare type CodegenSettings" index.d.ts{"content":[{"text":"157:export declare type CodegenSettings = BaseSettings & {\r\n158- language?: \"typescript\" | \"javascript\";\r\n159- model?: string…ctrl+o
{"content":[{"text":"157:export declare type CodegenSettings = BaseSettings & {\r\n158-    language?: \"typescript\" | \"javascript\";\r\n159-    model?: string;\r\n160-    framework: \"react\" | \"html\";\r\n161-    styling: \"plain_css\" | \"tailwind\" | \"inline_styles\";\r\n162-    uiLibrary?: \"mui\" | \"antd\" | \"radix\" | \"shadcn\" | \"clean_react\" | \"custom_design_system\";\r\n163-    responsivePages?: Array<{\r\n164-        name: string;\r\n165-        framesId: string[];\r\n166-    }>;\r\n167-    enableTranslation?: boolean;\r\n168-    enableUILibraryTheming?: boolean;\r\n169-    enableCompactStructure?: boolean;\r\n170-    enableAutoSplit?: boolean;\r\n171-    autoSplitThreshold?: number;\r\n172-    disableMarkedForExport?: boolean;\r\n173-    allowAutoSelectFirstNode?: boolean;\r\n174-    enableDisplayScreenModelId?: boolean;\r\n175-    enableGeneratePackageLock?: boolean;\r\n176-    enableAnimationsPreset?: boolean;\r\n177-    enableDisplayDataId?: boolean;\r\n178-    enableDisplayDataName?: boolean;\r\n179-    enableDisplayDataVariant?: boolean;\r\n180-    url?: string;\r\n181-    prompt?: string;\r\n182-    images?: Array<{\r\n","type":"text"}]}
Thinking…

Now write src/figma.ts, .env.example, README.md.

write /sandbox/repo/src/figma.ts{"content":[{"text":"Successfully wrote 2911 bytes to /sandbox/repo/src/figma.ts","type":"text"}]}
Thinking…

Now .env.example and README.md, then smoke test.

Careful: process.env.FIGMA_FILE_KEY ??= key; — env values are string|undefined, fine.

Write .env.example and README.

write /sandbox/repo/.env.example{"content":[{"text":"Successfully wrote 253 bytes to /sandbox/repo/.env.example","type":"text"}]}
Thinking…

Now smoke test: run without token, and with a dummy token to see the hosted API respond (auth error). Keep timeout short.

$ cd /sandbox/repo && echo "--- no token ---" && node src/generate.ts --url https://example.com; echo "exit=$?"; echo "--- dummy token ---"; ANIMA_TOKEN=dummy-invalid-token timeout 90 node src/generate.…{"content":[{"text":"--- no token ---\nMissing ANIMA_TOKEN.\n 1. Copy .env.example to .env\n 2. Put your Anima API token in it (API access is granted by Anima…ctrl+o
cd /sandbox/repo && echo "--- no token ---" && node src/generate.ts --url https://example.com; echo "exit=$?"; echo "--- dummy token ---"; ANIMA_TOKEN=dummy-invalid-token timeout 90 node src/generate.ts --prompt "A pricing page with three tiers" --out out/prompt 2>&1 | tail -8; echo "exit=$?"

{"content":[{"text":"--- no token ---\nMissing ANIMA_TOKEN.\n  1. Copy .env.example to .env\n  2. Put your Anima API token in it (API access is granted by Anima — see README)\n\nexit=1\n--- dummy token ---\n→ generating from prompt (react/tailwind)\n\nAnima generation failed: Invalid Anima token\nexit=0\n","type":"text"}]}
Thinking…

Excellent — the SDK reaches the hosted API and returns "Invalid Anima token", proving plumbing works end-to-end. Note exit=0 is from tail pipe, fine.

Also check the --url path quickly? It would also fail auth. Fine.

Now write README.md with: what this is, quickstart, pricing, manageability notes, blocked status.

Pricing facts I verified:

  • Free plan: 5 chat messages/day in AI Playground, 5 Figma imports or website clones in Playground, 5 code generations in Figma plugin.
  • Metering unit = "code generation" (each time Anima produces code — plugin export, Playground import, website clone, prompt generation, MCP server use).
  • Pro plan advertised: up to 60% savings, 5000 code exports/month, unlimited Figma inspects (from the pricing page meta description).
  • Enterprise: from $500/mo billed annually, SSO/MFA/SLAs.
  • Billing monthly or annually; card/Apple Pay/Google Pay; Enterprise wire/invoice. Prorated upgrades; cancel anytime, access until end of cycle. Removing/downgrading team members credits next payment.
  • API/SDK access: "Contact us to get access" — not self-serve; also non-public website conversion via MHTML requires a specific license.
  • Exact tier prices are rendered client-side on the pricing page, so I couldn't extract numbers beyond the above.

Note the pricing page FAQ also mentioned PayPal (older JSON-LD) vs card/Apple Pay/Google Pay — minor discrepancy; I'll not dwell.

Manageability assessment for me (an agent): Easy parts: single npm package, plain Node, no local services, no DB, deterministic CLI, typed SDK, SSE progress handlers, output is plain files → easy to diff/commit. Friction: API access gated behind "contact us" (can't self-provision a token — hard blocker for unattended runs); usage metered per generation so retries burn quota; Figma path needs a second credential (Figma token) plus node IDs; long-running generations (up to 300s timeout) mean I should not run them synchronously in tight loops — use webhookUrl / attachToGenerationJob to resume; generated code is non-deterministic so diffs churn.

Let me write README.md and verify figma.ts arg guard runs.

write /sandbox/repo/README.md{"content":[{"text":"Successfully wrote 4791 bytes to /sandbox/repo/README.md","type":"text"}]}
Thinking…

Final checks: run figma.ts guard, add .env to .gitignore, confirm npm scripts parse, and confirm the --url path also reaches API (quick). Also check .gitignore has .env — it doesn't. Add it.

$ cd /sandbox/repo && printf '\n# Local secrets\n.env\n' >> .gitignore && node src/figma.ts; echo "exit=$?"; echo "--- website path smoke ---"; ANIMA_TOKEN=dummy timeout 60 node src/generate.ts --url ht…{"content":[{"text":"Need ANIMA_TOKEN, FIGMA_FILE_KEY, FIGMA_TOKEN and --nodes <id[,id]> (or --figma-url <url>)\nexit=1\n--- website path smoke ---\n→ cloning h…ctrl+o
cd /sandbox/repo && printf '\n# Local secrets\n.env\n' >> .gitignore && node src/figma.ts; echo "exit=$?"; echo "--- website path smoke ---"; ANIMA_TOKEN=dummy timeout 60 node src/generate.ts --url https://example.com 2>&1 | tail -3; echo "--- scripts ---"; npm run 2>&1 | head -20; git status --short

{"content":[{"text":"Need ANIMA_TOKEN, FIGMA_FILE_KEY, FIGMA_TOKEN and --nodes <id[,id]> (or --figma-url <url>)\nexit=1\n--- website path smoke ---\n→ cloning https://example.com (react/tailwind)\n\nAnima generation failed: Invalid Anima token\n--- scripts ---\nScripts available in anima-example@1.0.0 via `npm run-script`:\n  example:website\n    node --env-file-if-exists=.env src/generate.ts --url https://example.com --out out/website\n  example:prompt\n    node --env-file-if-exists=.env src/generate.ts --prompt \"A pricing page with three tiers and a monthly/annual toggle\" --out out/prompt\n  example:figma\n    node --env-file-if-exists=.env src/figma.ts\n M .gitignore\n?? .env.example\n?? README.md\n?? package-lock.json\n?? package.json\n?? src/\n","type":"text"}]}
Thinking…

Everything works. Done. Now summarize concisely: what I built, pricing, manageability verdict, blocked item.

Note ambiguity: "Anima" — I picked AnimaApp (design-to-code). Mention that assumption briefly.

Files: /sandbox/repo/{package.json, src/generate.ts, src/figma.ts, .env.example, README.md, .gitignore}.

Assumed "Anima" = AnimaApp (animaapp.com, Figma/website/prompt → code), since that's the hosted product with a public SDK (@animaapp/anima-sdk) and published pricing. Say the word if you meant Anima Protocol / Anima Health / s0nderlabs' anima.

Built (hosted API only, no local stacks)

/sandbox/repo
├── package.json      # single dep: @animaapp/anima-sdk@0.27.0, npm run example:*
├── src/generate.ts   # URL → code  or  prompt → code   (no extra creds)
├── src/figma.ts      # Figma file → code               (Anima + Figma token + node id)
├── .env.example      # ANIMA_TOKEN / FIGMA_FILE_KEY / FIGMA_TOKEN
├── README.md         # quickstart, pricing, manageability notes
└── .gitignore        # + .env

Node ≥22 runs the .ts files directly (type stripping) — no build step, no dev server, nothing long-running. Output is plain files under out/; binary assets return as hosted URLs.

Verified: install, SDK API surface (generateCode, generateCodeFromWebsite, generateCodeFromPrompt, handlers), arg handling, and that requests actually reach Anima's hosted API — a dummy token returns Invalid Anima token end-to-end. Blocked: a real generation. API/SDK access is not self-serve — docs say "contact us to get access", and there's no ANIMA_TOKEN here. Drop a real token in .env and the same commands produce real code. (MHTML/private-site cloning needs a separate Anima license.)

Pricing

  • Metered in "code generations" — each time Anima produces code (plugin export, Playground import, website clone, prompt, MCP call).
  • Free: 5 Playground chat messages/day, 5 Playground imports/clones, 5 plugin code generations.
  • Pro: up to ~60% savings, 5,000 code exports/month, unlimited Figma inspects.
  • Enterprise: from $500/mo billed annually (SSO, MFA, SLAs, compliance).
  • Monthly or annual; card/Apple Pay/Google Pay (Enterprise: wire/invoice). Upgrades prorated, cancel anytime with access to cycle end, seat removals credit the next payment.
  • Caveat: plan cards are client-rendered, so exact Free/Pro price points weren't extractable from the static page — only the figures above appear in its own text/metadata.

Easy for me to manage? Mostly yes, with one human-gated step.

Easy: one public npm package, zero infra to run/patch/monitor; observable SSE progress handlers; declarative settings (framework/styling/uiLibrary) so output-style changes are one-line; output is plain files → clean diffs and PRs. Friction: token can't be self-provisioned (blocks unattended bootstrap); quota burns per generation so no blind retries; Figma runs can take up to 300s → prefer webhookUrl + attachToGenerationJob({sessionId}) over blocking; Figma flow needs a second credential plus node IDs; generated code is non-deterministic, so treat out/ as an artifact until frozen after review.

AX Fundamentals

23 checks. Open an area for details.

This check is a quick preview. Test more tasks and models with Gauge Agents.

Test your product with Gauge Agents

AX Check by Gauge