Skip to main content
cURL
Cost: 1 API credit per write.
This creates a real listing on Etsy, as a draft unless you send state: "active". Needs the listings:write scope and the Listing optimization workspace permission. shop_id is optional when the workspace has one connected shop; with several, 400 shop_id_required lists them.
state: "active" publishes the listing on Etsy, last, inside the same write. Publishing costs the seller Etsy’s $0.20 listing fee, and a publish can’t be reverted. Send dry_run=true first to see what would be sent.

What a listing needs

Every listing needs title, description, price, quantity, category_id (from Search categories), who_made and when_made. who_made: "someone_else" also needs production_partner_ids. When a publish lacks something, the answer is 400 listing_not_publishable, its missing names what, and nothing is sent. Find processing profiles with List processing profiles. Each URL in images and files is https with a host name of at most 128 characters: letters, digits, ., - and _. Any other answers 400 invalid_request, and nothing is sent.

How the write runs

The answer is 202 with the write’s change, outcome: "applying". Poll Get change at Location. Once it has succeeded, its target is the new listing. Alura makes the draft first. A digital listing’s files are uploaded right after it, then the rest of the content, then the publish. If a step fails after the draft exists, the draft stays: the change names it and what landed (applied_fields, failed_fields). A file that fails leaves the draft unpublished. Finish the draft with Update listing, never by creating again. A retry under the same Idempotency-Key answers the same change and never creates a second listing. Once the write has finished, that retry answers 200 with the new listing’s id, url, state and change. The listing’s content isn’t read back: Get listing shows it after the next sync. See Idempotency.
The same request within 10 minutes (longer while the earlier write’s outcome is still being checked: then 409 write_outcome_unknown, and for up to 24 hours after Alura stops checking, until the time that answer names) answers the earlier write instead of creating a second listing, and the Alura-Write-Deduplicated header names that write’s change. To create it again on purpose, send allow_duplicate: true under a new Idempotency-Key.
On Alura’s test shop, a publish counts toward its cap on listings activated through the API at once. Past it, the answer is 409 test_shop_active_cap with cap and active, and nothing is sent.
To copy an existing listing instead, use Duplicate listing. Credits and limits says when a write is charged.

Authorizations

Authorization
string
header
required

An API key: Authorization: Bearer alura_sk_....

Headers

Idempotency-Key
string

Makes a retry safe: the same key with the same request within 24 hours answers from the first write (with Idempotent-Replayed: true) and never writes to Etsy twice; a write that failed with nothing written (Retry-After set) is tried again under it. The same key with a different request is a 409 conflict; while the first request still runs, 409 idempotency_processing (or the same 202). Required for relative changes such as adjust_price, and to add a listing file, image or video, or to change the alt text of an image (each uploads to Etsy, so a blind retry would upload again); a dry_run=true needs none.

Required string length: 1 - 255

Query Parameters

dry_run
boolean

true: plan the write and send nothing: what it would change, the Etsy calls it would make, and nothing reserved, charged or recorded. Free; counts toward the per-minute write limit.

Body

application/json
title
string
required

The title, 1-140 characters.

Required string length: 1 - 140
description
string
required

The description.

Maximum string length: 50000
price
required

The price of the listing's one offering in the shop's currency, as a decimal string such as "24.99" (a number with at most 2 decimals is accepted too); above 0 and at most 50,000.

quantity
integer
required

The quantity in stock, 1-999.

Required range: 1 <= x <= 999
category_id
string
required

Etsy's category (its taxonomy_id), from browse_categories or GET /v1/etsy/categories.

Pattern: ^[1-9][0-9]{0,9}$
who_made
enum<string>
required

Etsy's who_made. someone_else needs production_partner_ids.

Available options:
i_did,
someone_else,
collective
when_made
string
required

Etsy's when_made, for example made_to_order, 2020_2026 or before_2007.

Pattern: ^[a-z0-9_]{1,20}$
tags
string[]

Every tag, at most 13; replaces them all (an empty list removes every tag). Not with tags_add or tags_remove.

Maximum array length: 13
Required string length: 1 - 30
materials
string[]

Every material, at most 13; replaces them all.

Maximum array length: 13
Required string length: 1 - 45
is_supply
boolean

true: a craft supply or tool; false (the default on Etsy): a finished product.

type
enum<string>

physical (the default): a shipped item, which needs shipping_profile_id and processing_profile_id. digital: a download buyers get after they buy, which needs at least one image and one of files to be published.

Available options:
physical,
digital
section_id
string

A section of the shop. A section of another shop is 404.

Pattern: ^[0-9]{1,20}$
shipping_profile_id
string

A shipping profile of the shop; required for a physical listing. A profile of another shop is 404.

Pattern: ^[0-9]{1,20}$
return_policy_id
string

A return policy of the shop; needed to publish, outside the EU. A policy of another shop is 404.

Pattern: ^[0-9]{1,20}$
processing_profile_id
string

A processing profile of the shop (GET /v1/workspace/processing-profiles); required for a physical listing (set on its offering). A profile of another shop is 404.

Pattern: ^[0-9]{1,20}$
production_partner_ids
string[]

The production partners who help make the item; required when who_made is someone_else.

Maximum array length: 50

A production partner of the shop. A partner of another shop is 404.

Pattern: ^[0-9]{1,20}$
images
string[]

The listing's images, in order (the first is the main image), at most 10 https URLs; needed to publish a listing (physical or digital).

Maximum array length: 10

An https URL of the image Alura fetches (a public address, no redirects, at most 10 MB; its host name at most 128 characters: letters, digits, ., - and _).

Maximum string length: 2048
files
object[]

A digital listing's files (type: "digital" only), in order, at most 5, each an https URL Alura fetches (at most 20 MB) with the name buyers see; a digital listing needs at least one to be published. Alura uploads them right after the draft is made, before the rest of the content and the publish.

Maximum array length: 5
shop_id
string

The connected shop to create the listing in. Optional when the workspace has one connected shop; with several, 400 shop_id_required lists them.

Pattern: ^[0-9]{1,20}$
state
enum<string>

draft (the default): the listing is created unpublished. active: it is published, last, inside the same write. Publishing costs the seller Etsy's $0.20 listing fee (re-activating a listing too), and a publish cannot be reverted.

Available options:
draft,
active
allow_duplicate
boolean

true: make the listing even when the same request was made in the last 10 minutes, or for up to about 48 hours while the earlier outcome is unknown (by default a repeat within 10 minutes answers that earlier write instead of creating twice). Only with a new request key.

Response

OK: the write landed on Etsy (or, with dry_run=true, what it would do).

object
string
required
Allowed value: "workspace.listing"
id
string | null
required

The new listing on Etsy; null when nothing was created (notices says so).

shop_id
string
required

Etsy ID, as a string.

url
string | null
required

The listing on Etsy.

state
enum<string> | null
required

active when the write published it; draft otherwise (a publish that did not land leaves a draft); null when no listing was created.

Available options:
draft,
active
source_listing_id
string | null
required

The listing it was duplicated from; null for a create.

change
object
required

The write: its change ID and what landed.

notices
object[]
required

Why a part of the answer is unknown; empty when nothing is.

as_of
string
required

When Etsy answered the write.