Skip to main content
A submission is one extraction job for a URL. You create it, the engine processes it asynchronously, and when it finishes it produces an extraction (referenced by extraction_id) whose output is the design system.

Creating submissions

There are two ways to submit work:
  • Single URL: POST /design/submissions with a url.
  • Map mode: POST /design/submissions?map=true treats url as a domain root, discovers the site’s pages, and submits each one as its own extraction. The response shape changes to reflect the multiple URLs discovered. Use max_urls to cap discovery; the server clamps it to 200.
To extract a brand from its guidelines PDF instead of a URL, upload the file to POST /design/submissions/brand-kit. See Brand kit.

Submission options

The single-URL request accepts a few options:
  • force: re-run extraction even when a cached result exists.
  • enable_deep_analysis: run additional, slower analysis steps for a higher-fidelity result.
  • sections: choose which parts of the design system to extract. Omit it or pass null for a full extraction.

Extract only selected sections

Pass a nonempty sections array when you know which parts of a website you need:
This request runs a fresh extraction for colors and typography. Omit force to allow reuse of an eligible full cached extraction. The API returns 202 with a submission_id. Poll that submission as usual. A completed response has this shape, abbreviated:
The empty objects above stand in for the extracted data. Unrequested design-system keys are absent. Captured artifacts remain available separately.

Available sections

You can request any combination of the design-system sections:
The value "sections" means descriptions of the page’s sections in order. It is one possible value inside the request’s sections array. Fresh full extractions include brand_assets by default. Pass "sections": ["brand_assets"] to collect only brand imagery from ads, social channels, and campaigns. This is separate from assets, which contains logos and media from the website. See Brand assets for sources, fields, and examples. Fewer sections can reduce extraction time. Selecting fewer sections does not change the credit price.

Selection rules

  • Omit sections or send null for a full extraction. An explicit list, even one containing every section, creates a selective extraction.
  • An empty array or an unknown section name returns 422. Duplicate names are removed.
  • Selection is supported for single-URL submissions. You cannot combine it with map=true or enable_deep_analysis: true.
  • Status, history, and result responses report the original selection in top-level sections. A full extraction reports sections: null.
  • completed means the requested sections have finished extracting. It does not mean every design-system section was extracted.
If explicitly requested assets or icons cannot be extracted after retries, the submission fails and its credits are refunded. Successfully finding no assets or icons is a valid result. Similarity search and prompt enhancement require a full extraction. They reject selective submissions with 422 FULL_EXTRACTION_REQUIRED, including selective submissions served from a full cache hit. Submit the URL without sections when you need those features.

Pages on localhost

The engine crawls the URL you submit, so the page must be reachable from it. You can use a publicly facing URL directly. If the page is served by a server running on localhost, make it reachable over the Tastelabs SSH tunnel. Only Tastelabs can access a page exposed this way.
The steps assume your server is running on port 3000 on localhost. Adjust SERVER_PORT accordingly, then submit the printed URL as url. The same URL works as candidate_url for a brand-adherence job. The tunnel closes when ssh exits or the deadline passes, and a submission against a closed tunnel fails with Page not reachable. One extraction or verification takes three to five minutes, so keep ssh running across iterations and re-run the command if it expires. For static files without a server, use the Python built-in server:
A crawl-<uuid> URL names whatever you publish behind it right now, not a site, so it is never served from cache. Every submission of a tunnel URL runs a fresh extraction and cache_hit is always false.

Status and progress

Each submission has a top-level status: accepted, queued, crawling, extracting, completed and failed It also reports a finer-grained current_step as the workflow streams:
Track progress with GET /design/submissions/{id} for a single submission, or GET /design/submissions for a paginated list.

Filtering the list

The list is deduplicated by URL and returns the newest submissions first. Narrow it with:
  • status: one lifecycle status.
  • q: free-text search over the source URL (a case-insensitive substring).
  • api_key_id: only submissions created with one API key. Useful for separating environments that share an account.
  • kind: website for URL extractions or brand_kit for brand kits. Each item reports its kind.
Alongside the page, total counts everything matching the filter and totals breaks that down into completed, failed, and in_progress. The four in-progress statuses fold into in_progress, so the three buckets sum to total. Both counts ignore pagination, which makes them safe to render as a summary without walking every page. Each item also reports credits_consumed (net of any refund) and api_key_name, so you can attribute spend without a second call.

Polling for the result

Extraction is asynchronous, so poll GET /design/submissions/{id}/result:
  • 200: may contain a partial design_system while the workflow runs. Keep polling until status is completed or failed.
  • 409 (NOT_READY): no checkpoint has landed yet. Retry shortly.
  • 404: the submission doesn’t exist or isn’t accessible to the caller.
Read result.design_system once status is completed. See The design system for the structure. The full design system is a large payload. Add ?sections=colors,typography to return only the sections you need, which keeps polling responses small. See Requesting only the sections you need. The GET query filter only narrows an existing result. It does not start extraction work or add sections omitted from the original submission. For a selective extraction, omitting the GET filter returns all originally requested sections.

Downloading the whole extraction

An extraction is more than its design system: it also has the captured HTML and CSS, the screenshot, and every logo, image, and icon the design system references. GET /design/submissions/{id}/download returns a manifest listing all of them as one flat file tree, so you can write the extraction to disk in one pass. Every entry has a relative path and exactly one source:
  • content: inline text to write at that path. This is how guidelines.json (the design system) arrives.
  • url: a file to download to that path, such as crawl/html.html or crawl/screenshot.jpeg.
Assets are mirrored to the engine’s storage before the manifest is built, so the URLs keep working even after the origin site changes. The submission must be completed: an in-progress one returns 409 NOT_READY. Like the result endpoint, authentication is optional, so a public extraction can be downloaded without a key. For selective extractions, guidelines.json contains only the requested design-system sections.

Caching and freshness

Full extraction results can be cached and reused across submissions. When a request is served from a previous full extraction for the URL, cache_hit is true. Selective results are saved and remain retrievable by submission ID, but they are never reused as cache sources, even for another request with the same selection. An eligible full cached extraction can satisfy a selective request. Its response still contains only the requested sections. To know when the data was actually extracted (its freshness), read completed_at. It is on the submission envelope, on GET /design/submissions/{id}, the /result endpoint, and the list. On a cache hit, completed_at points to the original extraction, not the time you sent the request, so a cached result may have been extracted earlier. On a fresh run, it is the moment the extraction just completed. While a submission is still running, completed_at is null. Set force: true on the request to bypass the cache and run a fresh extraction. A fresh full result becomes eligible for cache reuse; a fresh selective result does not. New fields are not added retroactively to saved results. For example, an extraction created before Brand Assets was introduced may have no brand_assets data. Submit it again with force: true to collect those images.

Visibility and sharing

By default a result is private to its owner. Use PATCH /design/submissions/{id}/visibility with { "is_public": true } to make it public. Public results can be read from GET /design/submissions/{id}/result without authentication, which makes extractions shareable. Only the owner can change visibility.