About Store API
Mozello Store API allows external applications to communicate and exchange data with Mozello online store. You can change product data and stock and you can receive notifications about orders, stock changes and payment status changes.
API calls
Basics
The base URL for all API calls is https://api.mozello.com/v1/
API calls are made to the corresponding API URL which, in turn, responds with a JSON object. Optional properties might be omitted or returned as null. The returned HTTP status will be 200 for successful or partially successful API calls, and 4XX or 5XX for unsuccessful API calls.
GET, POST, PUT and DELETE HTTP methods are used for standard API methods that perform Get/List, Create, Update and Delete actions with a resource. POST HTTP method is used for non-standard methods.
Payloads are in JSON format.
For authentication an API key must be sent in an HTTP header of each request (see example below). API key can be generated from your Mozello account control panel under Store > Store settings > API.
Authorization: ApiKey MZL-d4fcd4c02c88eafaeaef7f87f6796f12
Example
Request (raw HTTP)
DELETE /v1/store/product/uid-1234567890/ HTTP/1.1
Host: api.mozello.com
Success response
{
"error": false
}
Error response
{
"error": true,
"error_code": 401,
"error_message": "Unauthorized"
}
Request modifiers
Additional GET parameters might serve as request modifiers. These can be used for sorting, filtering and pagination. See description of the method for request modifiers available to it.
Pagination
List methods that return multiple items implement pagination. These methods take page_size parameter and may return a link to the next page as next_page_uri. The maximum page size may be limited.
Reverse sorting
List methods can use desc parameter with value 1 to swap the default order.
Filtering
List methods can use filter parameter to filter returned items by some field (e.g. created_at, modified_at).
The filter parameter value is a URL-encoded string in format <field><expression><value>.
For example filter=created_at%3E%3D2022-03-07%2008%3A45%3A10 that decodes to
created_at>=2022-03-07 08:45:10.
Allowed expressions: >, <, =, <=, >=, <>.
Product and order lists accept several filters, which must all match: repeat the parameter as filter= or
filter[]=. For example a date range:
filter=created_at%3E%3D2022-03-01&filter=created_at%3C2022-04-01.
Example
Request with request modifiers (raw HTTP)
LIST /v1/store/products/?filter=created_at%3E%3D2022-03-07%2008%3A45%3A10&desc=1&page_size=5 HTTP/1.1
Host: api.mozello.com
Response
{
"error": false,
"products": []
}
Products
List products
GET /store/products/ - returns list of product data
Example return data:
{
"products": [
...
],
"next_page_uri": "/store/products/?page_size=20&page_start=id:222"
}
Supported request modifiers: pagination, reverse sorting, filtering by created_at, modified_at.
Get product
GET /store/product/<product-handle>/ - returns product data
Return values
Returns product which corresponds to product data structure. Missing values may be omitted.
Example return data:
{
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"de": "Geräte"
},
{
"en": "Smartphones",
"de": "Smartphones"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro",
"de": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"de": "<b>Ein ziemlich gutes</b> Telefon."
},
"meta_title": {
"en": "Buy Apple iPhone 12 Pro",
"de": null
},
"meta_description": {
"en": "Order the iPhone 12 Pro online with free delivery.",
"de": null
},
"url": {
"en": "apple-iphone-12-pro",
"de": null
},
"options": [
{
"option_name": {
"en": "Memory",
"de": "Speicher"
},
"display_style": "list",
"values": [
{
"value_name": "128 GB",
"value_handle": "uid-5011"
},
{
"value_name": "256 GB",
"value_handle": "uid-5012"
}
]
},
{
"option_name": {
"en": "Color",
"de": "Farbe"
},
"display_style": "colors",
"values": [
{
"value_name": {
"en": "Space Grey",
"de": "Space Grau"
},
"value_handle": "uid-5021",
"color_code": "#333333"
},
{
"value_name": {
"en": "Pacific Blue",
"de": "Pazifik Blau"
},
"value_handle": "uid-5022",
"color_code": "#003366"
}
]
}
],
"variants": [
{
"variant_no": 1,
"variant_handle": "uid-1024",
"option_value_handle1": "uid-5011",
"option_value_handle2": "uid-5021",
"option_value_handle3": null,
"picture_handle": "uid-101",
"price": null,
"sale_price": null,
"sku": "WHATEVR1",
"stock": 1
},
{
"variant_no": 2,
"variant_handle": "uid-1025",
"option_value_handle1": "uid-5012",
"option_value_handle2": "uid-5022",
"option_value_handle3": null,
"picture_handle": "uid-102",
"price": null,
"sale_price": null,
"sku": "WHATEVR2",
"stock": 5
}
],
"pictures": [
{
"uid": "uid-100001",
"url": "https://example.mozfiles.com/phone1.jpg"
},
{
"uid": "uid-100002",
"url": "https://example.mozfiles.com/phone2.jpg"
}
],
"variant_pictures": [
{
"uid": "uid-101",
"url": "https://example.mozfiles.com/phone_gray.jpg"
},
{
"uid": "uid-102",
"url": "https://example.mozfiles.com/phone_blue.jpg"
}
],
"price": 100.5,
"sale_price": 95,
"sku": null,
"stock": null,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro",
"weight": 189
}
Add product
POST /store/product/ - add a product.
Parameters
- product - product data, except pictures and variant_pictures.
Product handle is mandatory when creating a new product. Only category or category handle can be specified, not both.
Important notes on handling images
Use Add product picture to add pictures and Add product variant picture to add variant pictures after you have added the product.
Example
Add product:
{
"product": {
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"de": "Geräte"
},
{
"en": "Smartphones",
"de": "Smartphones"
}
]
},
"title": {
"en": "Apple iPhone 12 Pro",
"de": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"de": "<b>Ein ziemlich gutes</b> Telefon."
},
"url": {
"en": "apple-iphone-12-pro",
"de": null
},
"options": [
{
"option_name": {
"en": "Memory",
"de": "Speicher"
},
"display_style": "list",
"values": [
{
"value_name": "128 GB",
"value_handle": "new-1-1"
},
{
"value_name": "256 GB",
"value_handle": "new-1-2"
}
]
},
{
"option_name": {
"en": "Color",
"de": "Farbe"
},
"display_style": "colors",
"values": [
{
"value_name": {
"en": "Space Grey",
"de": "Space Grau"
},
"value_handle": "new-2-1",
"color_code": "#333333"
},
{
"value_name": {
"en": "Pacific Blue",
"de": "Pazifik Blau"
},
"value_handle": "new-2-2",
"color_code": "#003366"
}
]
}
],
"variants": [
{
"variant_no": 1,
"option_value_handle1": "new-1-1",
"option_value_handle2": "new-2-1",
"option_value_handle3": null,
"picture_handle": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR1",
"stock": 1
},
{
"variant_no": 2,
"option_value_handle1": "new-1-2",
"option_value_handle2": "new-2-2",
"option_value_handle3": null,
"picture_handle": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR2",
"stock": 5
}
],
"price": 100.5,
"sale_price": 95,
"sku": null,
"stock": null,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro",
"weight": 189
}
}
Update product
PUT /store/product/<product-handle>/ - update product.
Parameters
- product - product data, except handle, pictures and variant_pictures.
- api_options - optional api options.
Only category or category handle can be specified, not both.
Important notes on updating variants
- Make sure your variants items include variant_handle and your options property values items include value_handle, otherwise these items will be completely overwritten.
- Use another API - batch_update_by_sku to quickly update some variant data
Important notes on handling images
Use Add product picture and Delete product picture to change pictures for the product.
Example
Update product price:
{
"product": {
"price": 100.5
}
}
Delete product
DELETE /store/product/<product-handle>/ - deletes a particular product.
Add or update batch of products
POST /store/products/batch_update/ - updates a batch of products
Parameters
- products - array of product data items, except pictures
- api_options - optional api options.
Only category or category handle can be specified, not both.
Notes on adding new products
- Product handle is mandatory when creating new products
- Use new, unique product handles to add new products
Notes on updating products
- Either product handle or SKU parameter is mandatory when updating
- If specified handle exists, corresponding product is updated.
- If specified handle does not exist, new product is created.
- If no handle is passed, SKU is used to identify product to be updated.
- If SKU does not exist or same SKU exists on multiple items, entry is ignored.
Important notes on updating variants
- Make sure your variants items include variant_handle and your options property values items include value_handle, otherwise these items will be completely overwritten.
- Use another API - batch_update_by_sku to quickly update some variant data
Important notes on handling images
Use Add product picture and Delete product picture to change pictures for the product.
Example
Add or update products with variants (depending on whether handle exists):
{
"products": [
{
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"de": "Geräte"
},
{
"en": "Smartphones",
"de": "Smartphones"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro",
"de": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"de": "<b>Ein ziemlich gutes</b> Telefon."
},
"url": {
"en": "apple-iphone-12-pro",
"de": null
},
"options": [
{
"option_name": {
"en": "Memory",
"de": "Speicher"
},
"display_style": "list",
"values": [
{
"value_name": "128 GB",
"value_handle": "uid-5011"
},
{
"value_name": "256 GB",
"value_handle": "uid-5012"
}
]
},
{
"option_name": {
"en": "Color",
"de": "Farbe"
},
"display_style": "colors",
"values": [
{
"value_name": {
"en": "Space Grey",
"de": "Space Grau"
},
"value_handle": "uid-5021",
"color_code": "#333333"
},
{
"value_name": {
"en": "Pacific Blue",
"de": "Pazifik Blau"
},
"value_handle": "uid-5022",
"color_code": "#003366"
}
]
}
],
"variants": [
{
"variant_no": 1,
"variant_handle": "uid-1024",
"option_value_handle1": "uid-5011",
"option_value_handle2": "uid-5021",
"option_value_handle3": null,
"picture_handle": "uid-101",
"price": null,
"sale_price": null,
"sku": "WHATEVR1",
"stock": 1
},
{
"variant_no": 2,
"variant_handle": "uid-1025",
"option_value_handle1": "uid-5012",
"option_value_handle2": "uid-5022",
"option_value_handle3": null,
"picture_handle": "uid-102",
"price": null,
"sale_price": null,
"sku": "WHATEVR2",
"stock": 5
}
],
"price": 100.5,
"sale_price": 95,
"sku": null,
"stock": null,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro",
"weight": 189
}
]
}
Update price by handle:
{
"products": [
{
"handle": "uid-1234567890",
"price": 100.5
}
]
}
Update stock or price by sku
POST /store/products/batch_update_by_sku/ - updates price or stock based on SKU.
Useful when variants are used as separate products with separate SKUs.
Parameters
-
products - array of SKU items
- sku - unique, existing SKU
- price - product or variant price
- special_price - product or variant special price
- stock - product or variant stock
Notes on updating products by SKU
- SKU and one of product or product variant properties are required
- If SKU does not exist or same SKU exists on multiple items, entry is ignored.
- Please observe item rate limits when updating multiple products
Example
Update some products or product variants by SKU:
{
"products": [
{
"sku": "SOMESKU1",
"stock": 5
},
{
"sku": "SOMESKU2",
"price": 50.55
}
]
}
Delete products
POST /store/products/batch_delete/ - deletes products by handle or SKU.
Parameters
-
products - array of product handles or SKUs
- handle or sku
Notes on deleting products
- If handle is specified, product with that handle is deleted
- If SKU is specified, all products with that SKU are deleted
Example
Delete some products:
{
"products": [
{
"sku": "SOMESKU1"
},
{
"handle": "uid-1234567890"
}
]
}
List product pictures
GET /store/product/<product-handle>/pictures/ - returns list of product pictures
Example return data:
{
"pictures": [
{
"uid": "uid-1234567890",
"url": "https://site-1234567890.mozfiles.com/files/1234567890/catitems/image1234567890.jpg"
}
]
}
Add product picture
POST /store/product/<product-handle>/picture/ - add a product picture.
Parameters
- picture - picture data
Example
Add product picture:
{
"picture": {
"filename": "greenshirt.jpg",
"data": "/9j/2wBDAAMCAgICAgMCAgIDAwMDBAYEBAQEBAgGBgUGCQgKCgkICQkKDA8MCgsOCwkJDRENDg8QEBEQCgwSExIQEw8QEBD/yQALCAABAAEBAREA/8wABgAQEAX/2gAIAQEAAD8A0s8g/9k="
}
}
Delete product picture
DELETE /store/product/<product-handle>/picture/<picture-handle>/ - deletes a particular product picture.
List product variant pictures
GET /store/product/<product-handle>/variant_pictures/ - returns list of product variant pictures
Example return data:
{
"variant_pictures": [
{
"uid": "uid-1234567890",
"url": "https://site-1234567890.mozfiles.com/files/1234567890/catitems/variantimage1234567890.jpg"
}
]
}
Add product variant picture
POST /store/product/<product-handle>/variant_picture/ - add a product variant picture.
Parameters
- variant_picture - picture data
Notes on variant pictures
This method adds pictures to the variant pictures list. Update the product and set picture_handle of the product variants to assign the picture.
Example
Add product variant picture:
{
"variant_picture": {
"filename": "greenshirt.jpg",
"data": "/9j/2wBDAAMCAgICAgMCAgIDAwMDBAYEBAQEBAgGBgUGCQgKCgkICQkKDA8MCgsOCwkJDRENDg8QEBEQCgwSExIQEw8QEBD/yQALCAABAAEBAREA/8wABgAQEAX/2gAIAQEAAD8A0s8g/9k="
}
}
Delete product variant picture
DELETE /store/product/<product-handle>/variant_picture/<picture-handle>/ - deletes a particular product variant picture.
Categories
List categories
GET /store/categories/ - returns list of category data
Example return data:
{
"categories": [
...
],
"next_page_uri": "/store/categories/?page_size=20&page_start=id:222"
}
Get category
GET /store/category/<category-handle>/ - returns category data
Return values
Returns category which corresponds to category data structure. Missing values may be omitted.
Example return data:
{
"handle": "uid-123",
"title": {
"en": "Gadgets",
"lv": "Ierīces"
},
"meta_title": {
"en": "Gadgets and accessories",
"lv": null
},
"meta_description": {
"en": "Shop gadgets and accessories online.",
"lv": null
},
"level": 1,
"previous_handle": null,
"parent_handle": "uid-321",
"seo_url": {
"en": "gadgets",
"lv": "ierices"
},
"picture": "https://www.example.com/image-file-1.jpg"
}
Add category
POST /store/category/ - add a category.
Parameters
- category - category data, except handle and level
Example
Add category:
{
"category": {
"title": {
"en": "Gadgets",
"lv": "Ierīces"
},
"previous_handle": null,
"parent_handle": "uid-321",
"seo_url": "gadgets",
"picture": {
"filename": "gadgets.jpg",
"data": "/9j/2wBDAAMCAgICAgMCAgIDAwMDBAYEBAQEBAgGBgUGCQgKCgkICQkKDA8MCgsOCwkJDRENDg8QEBEQCgwSExIQEw8QEBD/yQALCAABAAEBAREA/8wABgAQEAX/2gAIAQEAAD8A0s8g/9k="
}
}
}
Update category
PUT /store/category/<category-handle>/ - update category.
Parameters
- category - category data, except handle, level, previous_handle and parent_handle
- api_options - optional api options.
Example
Update category:
{
"category": {
"title": {
"en": "Electronics",
"lv": "Elektronika"
},
"seo_url": "electronics"
}
}
Delete category
DELETE /store/category/<category-handle>/ - deletes a particular category.
Additional conditions
The category must not contain sub-categories. Any products from this category will have their category unassigned.
Move category
POST /store/category/<category-handle>/move/ - move category in category tree.
Parameters
- category - only parent_handle and previous_handle
- parent_handle - handle of the new parent or null
- previous_handle - handle of the sibling category to move after or null
Additional conditions
The operation will fail if invalid move is requested or level constraints are breached.
Example
Move category:
{
"parent_handle": null,
"previous_handle": "uid-234"
}
Orders
List orders
GET /store/orders/ - returns list of order data
Parameters
- archived - whether to list archived orders, true, false
Example return data:
{
"orders": [
...
],
"next_page_uri": "/store/orders/?page_size=20&archived=true&page_start=id:222"
}
Supported request modifiers: pagination, reverse sorting, filtering by created_at.
Get order
GET /store/order/<order-number>/ - returns order data
Return values
Returns order which corresponds to order data structure. Missing values may be omitted.
Example return data:
{
"order_id": "MZ-1234567-123456",
"uuid": "9f3c1a7b2d4e5f60718293a4b5c6d7e8",
"created_at": "2020-12-30 15:25:33",
"payment_status": "pending",
"dispatched": false,
"archived": false,
"name": "John Smith",
"company": "Universal Exports LTD",
"vat_id": "LV40001234567",
"company_id": "40001234567",
"email": "johnsmith@example.com",
"phone": "+371 22222222",
"country_name": "Latvia",
"country_code": "lv",
"address": "Summer street 10",
"city": "Riga",
"province_code": "",
"zip": "LV-1000",
"shipping": {
"country_name": "Latvia",
"country_code": "lv",
"address": "Summer street 10",
"city": "Riga",
"province_code": "",
"zip": "LV-1000",
"pickup_point_id": ""
},
"notes": "",
"custom_fields": [
{
"name": "custom_123",
"label": "Gift message",
"value": "Happy birthday!",
"group": "additional"
}
],
"payment_method": "paypal",
"shipping_method": "omniva-latvija",
"shipping_tracking_code": "AA111111111111EE",
"shipping_tracking_url": "",
"currency": "EUR",
"subtotal": 100,
"shipping_price": 10,
"shipping_tax_inclusive_percent": 21,
"shipping_tax_exclusive_percent": null,
"taxes": 23.1,
"total": 133.1,
"discount_code": "",
"discount_amount": 0,
"cart": [
{
"product_handle": "uid-1234567890",
"product_name": "Trousers, Red, XXL, TR-12345",
"product_variant": ["Red", "XXL"],
"product_variant_handle": "uid-1024",
"product_price": 50,
"product_price_original": 50,
"product_sku": "TR-12345",
"product_quantity": 1,
"weight": 700,
"tax_inclusive_percent": 21,
"tax_exclusive_percent": 0
},
{
"product_name": "Sweater",
"product_price": 50,
"product_price_original": 50,
"product_quantity": 1,
"weight": 400,
"tax_inclusive_percent": 21,
"tax_exclusive_percent": 0
}
],
"print_url": "https://mystore.mozello.com/m/invoice/9f3c1a7b2d4e5f60718293a4b5c6d7e8/"
}
Update order
PUT /store/order/<order-number>/ - updates order
Parameters
- order
- payment_status - new payment status paid, pending or failed
- archived - new archived status true, false
- dispatched - new dispatched status true, false. When set to true, order is automatically archived
- shipping_tracking_code - new delivery tracking code
- shipping_tracking_url - new delivery tracking URL
- shipping_label_url - new shipping label URL to printable label as PDF file
Example
Update Order Status:
{
"order": {
"payment_status": "paid",
"archived": false
}
}
Cancel order
POST /store/order/<order-number>/cancel/ - cancels a pending order and returns its items to stock.
Use this endpoint to terminate an order that is not going to complete (for example, suspected fraud, buyer abandonment, or a duplicate submission). It marks the order as failed and releases the held stock for every payment method, including manual ones such as bank wire, cash on delivery, or pay in store, where setting payment_status to failed via the Update order endpoint would normally leave stock reserved.
Calling this endpoint on an order that has already been cancelled will not re-run the cancellation or re-release stock; the failure/log step is safely skipped. The archive flag, if provided, is still applied on subsequent calls, so a merchant can cancel first and archive later. Orders that have already been paid cannot be cancelled via this endpoint and will produce an error.
Parameters
- reason (optional) - free-form text recorded in the order log for audit purposes, up to 200 characters
- archive (optional) - when true, the order is also moved to the archive. Defaults to false
Return values
Returns the updated order which corresponds to order data structure.
Example
{
"reason": "fraud",
"archive": true
}
Customers
List customers
GET /store/customers/ - returns the store's customers
A customer is a buyer record aggregated automatically from orders (by e-mail, or by phone and country when there is no e-mail), covering both guest buyers and registered accounts. Customers are not created or edited through the API: their name, contact details and addresses follow their latest order. The only editable field is the marketing consent.
Parameters
- page - result page, starting at 1
- page_size - customers per page, 1 to 50 (default 20)
- query - free-text search over e-mail, name, company and phone (word-prefix matching; terms shorter than 3 characters are ignored)
- country - only customers with this billing country code
- marketing_consent - true limits the list to customers who gave marketing consent
- sort_by - last_order (default), last_activity, total_spend or order_count; newest or largest first
Supported request modifiers: pagination (page-based: page, page_count, total_count, next_page_uri),
reverse sorting, filtering by created_at (the customer record's created date).
Example return data:
{
"customers": [
{
"customer_id": 15,
"handle": "uid-15",
"name": "John Smith",
"company": "Universal Exports LTD",
"email": "johnsmith@example.com",
"phone": "+371 22222222",
"country": "lv",
"order_count": 4,
"total_spend": 532.1,
"currency_code": "EUR",
"marketing_consent": true,
"created": "2025-11-02 10:12:00",
"account_id": 7
}
],
"count": 1,
"total_count": 1,
"page": 1,
"page_count": 1
}
total_spend only sums orders placed in the store's current currency. account_id is set when the customer has a registered account (see accounts).
Get customer
GET /store/customer/<handle>/ - returns one customer
Returns a customer data structure.
Update customer
PUT /store/customer/<handle>/ - updates the customer's marketing consent
Parameters
- marketing_consent - true or false. The value is mirrored onto the customer's registered account, if any
Returns the updated customer data structure.
Delete customer
DELETE /store/customer/<handle>/ - deletes the customer record
Additional conditions
A customer with orders cannot be deleted (error 400). A linked registered account is unlinked, not deleted. Because customers are aggregated from orders, the record reappears if the same buyer orders again.
List customer orders
GET /store/customer/<handle>/orders/ - returns the customer's orders, newest id first when desc=1
Parameters
- archived - true lists archived orders instead of current ones
- payment_status - paid, pending or failed
- created_since, created_until - GMT date (
YYYY-MM-DD) or datetime (YYYY-MM-DD HH:MM:SS)
Supported request modifiers: pagination (page_size up to 50, page_start=id:<order id>, next_page_uri), reverse sorting. The order rows are summaries (see the example below); fetch an order by its order_no for the full order data structure.
Example return data:
{
"orders": [
{
"order_id": 467,
"order_no": "MZ-1234567-123456",
"uuid": "9f3c1a7b2d4e5f60718293a4b5c6d7e8",
"created": "2026-06-10 06:43:32",
"payment_status": "pending",
"dispatched": false,
"archived": false,
"status": "awaiting_payment",
"buyer_name": "John Smith",
"company": "",
"email": "johnsmith@example.com",
"phone": "+371 22222222",
"country_code": "lv",
"total": 1006,
"currency": "EUR",
"discount_code": "",
"tracking_code": "",
"customer_id": 15,
"account_id": 7
}
],
"count": 1,
"has_more": true,
"next_page_start": 253,
"next_page_uri": "/v1/store/customer/uid-15/orders/?page_size=1&page_start=id%3A253"
}
Accounts
List accounts
GET /store/accounts/ - returns the store's registered customer accounts (buyer logins)
Parameters
- page - result page, starting at 1
- page_size - accounts per page, 1 to 50 (default 20)
- query - free-text search over e-mail, name and company
- country - only accounts with this billing country code
- status - active or suspended
- sort_by - signup_date (default), last_purchase, last_login, total_spend or order_count; newest or largest first
Supported request modifiers: pagination (page-based: page, page_count, total_count, next_page_uri),
reverse sorting, filtering by created_at. The response also carries accounts_enabled: whether customer
accounts are switched on for the store.
Example return data:
{
"accounts": [
{
"account_id": 7,
"handle": "uid-7",
"email": "johnsmith@example.com",
"name": "John Smith",
"company": "Universal Exports LTD",
"country": "lv",
"status": "active",
"order_count": 4,
"total_spend": 532.1,
"currency_code": "EUR"
}
],
"count": 1,
"total_count": 1,
"page": 1,
"page_count": 1,
"accounts_enabled": true
}
Get account
GET /store/account/<handle>/ - returns one account
Returns an account data structure.
Add account
POST /store/account/ - registers an account on the buyer's behalf
Parameters
An account data structure without the read-only fields. email, name and billing_address.country_code are required; the e-mail must not belong to another account of the store (error 400). Additionally:
- password (optional) - the login password, at least 8 characters. When omitted, a random password is set and the buyer receives the store's password-reset e-mail to choose their own
Additional conditions
Customer accounts must be switched on in the store settings and included in the website's plan (error 400 otherwise). The account starts active and receives the store's auto-assigned loyalty discount unless auto_discount_id is given.
Example
{
"email": "johnsmith@example.com",
"name": "John Smith",
"phone": "+371 22222222",
"billing_address": {
"address": "Summer street 10",
"city": "Riga",
"zip": "LV-1000",
"country_code": "lv"
},
"marketing_consent": true
}
Update account
PUT /store/account/<handle>/ - updates an account
Parameters
Any writable fields of the account data structure, plus password to replace the login password. Only the passed fields change; inside billing_address and shipping_address only the passed keys change. shipping_address set to null means deliveries go to the billing address. auto_discount_id set to null removes the loyalty discount. A changed e-mail must not belong to another account.
Example
{
"status": "suspended",
"shipping_address": {
"city": "Tallinn"
}
}
Delete account
DELETE /store/account/<handle>/ - deletes the account
The buyer can no longer log in. Their orders and customer record stay (the customer is unlinked from the account). To block a login without deleting, set status to suspended instead.
List account orders
GET /store/account/<handle>/orders/ - the orders of the account's customer record
Same parameters and response as List customer orders. An account that never bought anything returns an empty list.
Discounts
List discounts
GET /store/discounts/ - returns all configured discounts
Example return data:
{
"discounts": [
{
"discount_id": 12,
"handle": "uid-12",
"title": {
"en": "Spring sale",
"lv": "Pavasara izpārdošana"
},
"discount_type": "coupon",
"amount_type": "percent",
"amount": 10,
"code": "SPRING10",
"status": "active",
"valid_from": "2026-03-01 00:00:00",
"valid_until": "2026-03-31 23:59:59",
"min_order_amount": null,
"combine_with_special": false,
"auto_assign": false,
"applies_to": "order",
"applies_to_ids": [],
"uses_remaining": 100,
"per_customer_usage_limit": null
}
],
"discounts_enabled": true
}
discounts_enabled is false when the website's plan does not include discounts: configured discounts still exist but do not apply at checkout.
Get discount
GET /store/discount/<handle>/ - returns one discount
Returns a discount data structure.
Add discount
POST /store/discount/ - creates a discount
Parameters
A discount data structure without the read-only fields. discount_type, title (at least the primary language) and amount are required; a coupon also needs a code. Fields that do not apply to the discount type are ignored. Dates are GMT.
Additional conditions
applies_to_ids must list at least one id when applies_to is categories, products or shipping, and every id must exist in the store (error 404 otherwise). A percent amount cannot exceed 100.
A store may hold at most 2500 discounts, of which at most 100automatic and loyalty discounts (error 400 otherwise). Delete expired or used-up discounts to make room.
Example
{
"discount_type": "coupon",
"title": {
"en": "Spring sale"
},
"amount_type": "percent",
"amount": 10,
"code": "SPRING10",
"valid_from": "2026-03-01",
"valid_until": "2026-03-31",
"uses_remaining": 100,
"applies_to": "categories",
"applies_to_ids": [41, 42]
}
Update discount
PUT /store/discount/<handle>/ - updates a discount
Parameters
Any writable fields of the discount data structure. Only the passed fields change; the title map changes only the passed language codes (null clears one); applies_to_ids, when passed, replaces the whole scope list. discount_type cannot be changed - delete and recreate the discount instead. Setting uses_remaining resets a coupon's countdown.
Example
{
"amount": 15,
"valid_until": "2026-04-15"
}
Delete discount
DELETE /store/discount/<handle>/ - deletes the discount
Additional conditions
A loyalty discount that is still assigned to accounts cannot be deleted (error 400); reassign those accounts first. Past orders keep what they were charged.
Notifications
Get store notifications (webhooks)
GET /store/notifications/ - returns configured notifications.
Example return data
{
"notifications_url": "https://www.example.com/notifications.php",
"notifications_wanted": [
"ORDER_CREATED",
"ORDER_DELETED",
"PAYMENT_CHANGED",
"DISPATCH_CHANGED",
"PRODUCT_CHANGED",
"PRODUCT_DELETED",
"STOCK_CHANGED"
]
}
Update store notifications (webhooks)
PUT /store/notifications/ - changes notification configuration.
Updates or removes the URL to which Mozello sends notifications.
Parameters
- notifications_url - the new URL or null
- notifications_wanted - array of notifications to send
Example
Update notifications.
{
"notifications_url": "https://www.example.com/notifications.php",
"notifications_wanted": ["ORDER_CREATED", "ORDER_DELETED", "PAYMENT_CHANGED", "DISPATCH_CHANGED", "PRODUCT_CHANGED", "PRODUCT_DELETED", "STOCK_CHANGED"]
}
API notifications
Notifications are sent via HTTPS call and contain data payload in JSON format.
Notifications include specific HTTP headers:
- X-Mozello-API-Version - API version number
- X-Mozello-Hash - Hash to verify notification data integrity
- X-Mozello-Alias - Website alias
Verifying notification authenticity
The X-Mozello-Hash HTTP header should be used to verify whether this HTTPS call is coming from Mozello. The signature hash is computed by running a sha256 HMAC hash function on the entire POST data body.
PHP example for validating received POST data
$signature = base64_encode(hash_hmac('sha256', $post_body, $api_key, true));
// check if hash matches
$headers = getallheaders();
if ($signature === $headers['X-Mozello-Hash']) {
// Your code here
}
ORDER_CREATED
Triggered when order is created, but before payment is received.
Order corresponds to order data structure. Missing values may be omitted.
Example
{
"event": "ORDER_CREATED",
"order": {
"order_id": "MZ-1234567-123456",
"uuid": "9f3c1a7b2d4e5f60718293a4b5c6d7e8",
"created_at": "2020-12-30 15:25:33", // YYYY-MM-DD HH:MM:SS
"payment_status": "pending", // always pending for ORDER_CREATED
"dispatched": false,
"archived": false,
"name": "John Smith",
"company": "Universal Exports LTD",
"vat_id": "LV40001234567",
"company_id": "40001234567",
"email": "johnsmith@example.com",
"phone": "+371 22222222",
"country_name": "Latvia",
"country_code": "lv",
"address": "Summer street 10",
"city": "Riga",
"province_code": "",
"zip": "LV-1000",
"shipping": {
"country_name": "Latvia",
"country_code": "lv",
"address": "Summer street 10",
"city": "Riga",
"province_code": "",
"zip": "LV-1000",
"pickup_point_id": ""
},
"notes": "",
"custom_fields": [
{
"name": "custom_123",
"label": "Gift message",
"value": "Happy birthday!",
"group": "additional"
}
],
"payment_method": "paypal",
"shipping_method": "omniva-latvija",
"shipping_tracking_code": "AA111111111111EE",
"shipping_tracking_url": "",
"currency": "EUR",
"subtotal": 100,
"shipping_price": 10,
"shipping_tax_inclusive_percent": 21,
"shipping_tax_exclusive_percent": null,
"taxes": 23.1,
"total": 133.1,
"discount_code": "",
"discount_amount": 0,
"cart": [
{
"product_handle": "uid-1234567890",
"product_name": "Trousers, Red, XXL, TR-12345",
"product_variant": ["Red", "XXL"],
"product_variant_handle": "uid-1024",
"product_price": 50,
"product_price_original": 50,
"product_sku": "TR-12345",
"product_quantity": 1,
"weight": 700,
"tax_inclusive_percent": 21,
"tax_exclusive_percent": 0
},
{
"product_handle": "uid-1234567891",
"product_name": "Sweater, SW-12345",
"product_price": 50,
"product_price_original": 50,
"product_sku": "SW-12345",
"product_quantity": 1,
"weight": 400,
"tax_inclusive_percent": 21,
"tax_exclusive_percent": 0
}
],
"print_url": "https://mystore.mozello.com/m/invoice/9f3c1a7b2d4e5f60718293a4b5c6d7e8/"
}
}
ORDER_DELETED
Triggered when order is deleted manually.
Order corresponds to order data structure. Missing values may be omitted.
Example
See example from ORDER_CREATED.
PAYMENT_CHANGED
Triggered on payment status change either manual or automatic.
Order corresponds to order data structure. Missing values may be omitted.
Example
{
"event": "PAYMENT_CHANGED",
"order": {
// full order data for convenience with the new payment status
"payment_status": "paid"
}
}
DISPATCH_CHANGED
Triggered on dispatch status change.
Order corresponds to order data structure. Missing values may be omitted.
Example
{
"event": "DISPATCH_CHANGED",
"order": {
// full order data for convenience with the new payment status
"dispatched": true
}
}
PRODUCT_CHANGED
Triggered when product data has been changed manually by an operator. Does not happen upon product import.
Product corresponds to product data structure. Missing values may be omitted.
Example
{
"event": "PRODUCT_CHANGED",
"product": {
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"lv": "Ierīces"
},
{
"en": "Smartphones",
"lv": "Viedtālruņi"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro",
"lv": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"lv": "<b>Diezgan normāls</b> telefons."
},
"url": {
"en": "apple-iphone-12-pro",
"lv": null
},
"variants": [
{
"variant_no": 1,
"variant_handle": "uid-1024",
"option_name1": {
"en": "Memory",
"lv": "Atmiņa"
},
"option_name2": {
"en": "Color",
"lv": "Krāsa"
},
"option_name3": null,
"option_value1": "128 GB",
"option_value2": {
"en": "Space Grey",
"lv": "Space Pelēka"
},
"option_value3": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR1",
"stock": 1
},
{
"variant_no": 2,
"variant_handle": "uid-1025",
"option_name1": {
"en": "Memory",
"lv": "Atmiņa"
},
"option_name2": {
"en": "Color",
"lv": "Krāsa"
},
"option_name3": null,
"option_value1": "256 GB",
"option_value2": {
"en": "Pacific Blue",
"lv": "Klusā Okeāna Zila"
},
"option_value3": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR2",
"stock": 5
}
],
"price": 100.5,
"sale_price": 95,
"sku": null,
"stock": null,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro",
"weight": 189
}
}
Example without variants
{
"event": "PRODUCT_CHANGED",
"product": {
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"lv": "Ierīces"
},
{
"en": "Smartphones",
"lv": "Viedtālruņi"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro 256 GB Space Grey",
"lv": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"lv": "<b>Diezgan normāls</b> telefons."
},
"url": {
"en": "apple-iphone-12-pro-256-gb-space-grey",
"lv": null
},
"variants": null,
"price": 100.5,
"sale_price": 95,
"sku": "WHATEVR1",
"stock": 5,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro 256 GB Space Grey",
"weight": 189
}
}
STOCK_CHANGED
Triggered when product stock has changed in Mozello for products that use this feature. Does not happen upon product import.
Product corresponds to product data structure. Missing values may be omitted.
Example
{
"event": "STOCK_CHANGED",
"product": {
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"lv": "Ierīces"
},
{
"en": "Smartphones",
"lv": "Viedtālruņi"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro",
"lv": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"lv": "<b>Diezgan normāls</b> telefons."
},
"url": {
"en": "apple-iphone-12-pro",
"lv": null
},
"variants": [
{
"variant_no": 1,
"variant_handle": "uid-1024",
"option_name1": {
"en": "Memory",
"lv": "Atmiņa"
},
"option_name2": {
"en": "Color",
"lv": "Krāsa"
},
"option_name3": null,
"option_value1": "128 GB",
"option_value2": {
"en": "Space Grey",
"lv": "Space Pelēka"
},
"option_value3": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR1",
"stock": 0
},
{
"variant_no": 2,
"variant_handle": "uid-1025",
"option_name1": {
"en": "Memory",
"lv": "Atmiņa"
},
"option_name2": {
"en": "Color",
"lv": "Krāsa"
},
"option_name3": null,
"option_value1": "256 GB",
"option_value2": {
"en": "Pacific Blue",
"lv": "Klusā Okeāna Zila"
},
"option_value3": null,
"price": null,
"sale_price": null,
"sku": "WHATEVR2",
"stock": 5
}
],
"price": 100.5,
"sale_price": 95,
"sku": null,
"stock": null,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro",
"weight": 189
}
}
Example without variants
{
"event": "STOCK_CHANGED",
"product": {
"handle": "uid-1234567890",
"category": {
"path": [
{
"en": "Gadgets",
"lv": "Ierīces"
},
{
"en": "Smartphones",
"lv": "Viedtālruņi"
}
]
},
"category_handle": "uid-123",
"title": {
"en": "Apple iPhone 12 Pro 256 GB Space Grey",
"lv": null
},
"description": {
"en": "A <b>rather good</b> phone.",
"lv": "<b>Diezgan normāls</b> telefons."
},
"url": {
"en": "apple-iphone-12-pro-256-gb-space-grey",
"lv": null
},
"variants": null,
"price": 100.5,
"sale_price": 95,
"sku": "WHATEVR1",
"stock": 0,
"visible": true,
"featured": false,
"tax": null,
"vendor": "Apple",
"model": "iPhone 12 Pro 256 GB Space Grey",
"weight": 189
}
}
PRODUCT_DELETED
Triggered when product has been deleted manually by an operator.
Product corresponds to product data structure. Missing values may be omitted.
Example
See example from PRODUCT_CHANGED.
API data structures
API options structure
API options allow to control some behavior when calling API functions.
- text_update_mode - "overwrite", "merge". The default is overwrite.
This flag controls how multilanguage text field is updated during UPDATE operation in cases when some languages are omitted in multilanguage text parameter.
- overwrite - texts in all languages of the multilanguage field are cleared and replaced by the multilanguage text parameter.
- merge - the languages present in the multilanguage text parameter are updated and the languages omitted from the multilanguage text parameter are not changed.
Multilanguage text data structure
Multilanguage text data is an object with language codes as keys and text values in the corresponding language as values. The language codes must be present in the website.
Alternatively, a simple string can be used instead of the text data object if the website only uses a single language or only the value in the default language needs to be modified.
Example
{
"en": "Memory",
"fr": "Mémoire"
}
Picture data structure
Picture data used in API calls when adding or replacing an image. Will not be returned when List or Get methods are used.
- filename - string
- data - string, base64 encoded image file
Product data structure
Product data used in API calls and notifications. Detailed description of fields.
- handle - string
- created_at - date, read only
- modified_at - date, read only
- category - category path
- category_handle - string or null, category handle
- extra_categories - array of additional categories, maximum 2. Requires a primary category; availability depends on plan.
- category_handle - string, category handle (read only)
- path - array of multilanguage text, same format as category path
- extra_category_handles - array of category handle strings, alternative to extra_categories when adding or updating a product
- title - multilanguage text
- description - multilanguage text
- meta_title - multilanguage text, SEO page title
- meta_description - multilanguage text, SEO meta description
- url - multilanguage text
- full_url - multilanguage text, relative URL path from catalog page
- options - null or array
- option_name - multilanguage text
- display_style - "list", "colors", "buttons"
- values - array
- value_handle - string, handle with "uid-" prefix references existing values, otherwise - new values
- value_name - multilanguage text
- color_code - null or string, HTML hexadecimal color format (e.g. #ff0077)
- variants - null or array
- variant_no - number
- variant_handle - string
- picture_handle - null or string, must reference uid from variant_pictures
- option_value_handle1 - string, must reference value_handle from options.values
- option_value_handle2 - string, must reference value_handle from options.values
- option_value_handle3 - string, must reference value_handle from options.values
- price - float
- sale_price - float
- sku - string
- barcode - string
- stock - null or whole number
- pictures - null or array
- uid - string
- url - string
- variant_pictures - null or array
- uid - string
- url - string
- price - float
- sale_price - float
- sku - string
- barcode - string
- stock - null or whole number
- min_amount - null or whole number, minimum quantity per order
- max_amount - null or whole number, maximum quantity per order
- visible - boolean
- featured - boolean
- tax - float
- vendor - string
- model - string
- weight - null or whole number, weight in grams
Product category path data structure
Product category path data used in API calls and notifications.
- path - array of multilanguage text. Maximum array length is 2.
- path_seo_url - array of multilanguage text. Parallel array to path containing SEO URL slugs for each category level. Maximum array length is 2.
When a product is added or updated with a category path, each level is matched against existing categories by comparing only the languages given in the path; omitted or null languages are not compared. A plain string is compared with the default language. If several categories match, the first one in the category order is used; use category_handle to pick a specific category. If none matches, a new category with the given titles is created. Paths in extra_categories are matched the same way, but must refer to existing categories.
Category data structure
Category data used in API calls and notifications.
- handle - string
- title - multilanguage text
- meta_title - multilanguage text, SEO page title
- meta_description - multilanguage text, SEO meta description
- level - integer 1..3
- previous_handle - string or null, handle of previous sibling
- parent_handle - string or null, handle of parent sibling
- seo_url - multilanguage text
- full_url - multilanguage text, relative URL path from catalog page
- picture - category picture when adding or updating category or image URL when returning category data.
Order data structure
Order data used in API calls and notifications. Detailed description of fields.
- order_id - string
- uuid - string, the order's stable public identifier
- created_at - date
- payment_status - "paid", "pending", "failed"
- dispatched - boolean
- archived - boolean
- name - string
- company - string
- vat_id - string
- company_id - string
- email - string
- phone - string
- country_name - string (English name)
- country_code - string (2 letter ISO code)
- address - string
- city - string
- province_code - string
- zip - string
- shipping - can be null if shipping address not set
- country_name - string (English name)
- country_code - string (2 letter ISO code)
- address - string
- city - string
- province_code - string
- zip - string
- pickup_point_id - string
- notes - string
- custom_fields - array of custom checkout field values, empty array if none
- name - string, field identifier
- label - string, field label as shown at checkout
- value - string
- group - string, checkout form section: "basic", "company", "address", "shipping" or "additional"
- payment_method - "cash", "wire", "paypal" or "gateway"
- payment_method_details - string, gateway name
- shipping_method - string
- shipping_method_details - string
- shipping_tracking_code - string
- shipping_tracking_url - string
- currency - string
- subtotal - float
- shipping_price - float
- shipping_price_original - float, shipping price before discount
- shipping_tax_inclusive_percent - null or float
- shipping_tax_exclusive_percent - null or float
- taxes - float
- total - float
- discount_code - string
- discount_amount - float
- cart
- product_handle - string
- product_name - string
- product_variant - null or array of string
- product_variant_handle - null or string
- product_price - float, price as ordered
- product_price_original - float, price before discount
- product_sku - string
- product_quantity - whole number
- weight - null or whole number, weight in grams
- tax_inclusive_percent - null or float, item tax rate (tax inclusive)
- tax_exclusive_percent - null or float, item tax rate (tax exclusive)
- taxes_details - summary of taxes
- title - string
- tax_amount - float
- tax_percent - float
- print_url - string/url
Customer data structure
A buyer record aggregated from orders. All fields are read-only except marketing_consent. Dates are GMT.
- customer_id - integer
- handle - string
- name - string
- company - string
- company_id - string
- vat_id - string
- email - string
- phone - string
- billing_address
- address - string
- city - string
- state - string
- zip - string
- country_code - string (2 letter ISO code, lowercase)
- shipping_address - same fields as billing_address, null if deliveries go to the billing address
- marketing_consent - boolean
- order_count - integer
- total_spend - float, orders in the store's current currency only
- currency_code - string
- first_order_at - date
- last_order_at - date
- last_activity_at - date
- created - date, when the customer record was created (the first order, or the registration)
- account_id - integer, null for a guest buyer
Account data structure
A registered buyer login. Dates are GMT.
- account_id - integer, read-only
- handle - string, read-only
- email - string, unique per store
- name - string
- company - string
- company_id - string
- vat_id - string
- phone - string
- billing_address
- address - string
- city - string
- state - string
- zip - string
- country_code - string (2 letter ISO code, lowercase)
- shipping_address - same fields as billing_address, null if deliveries go to the billing address
- password - string, write-only (add and update)
- status - "active", "suspended"
- marketing_consent - boolean
- auto_discount_id - integer, the assigned loyalty discount, null if none
- created - date, read-only
- last_login - date, read-only
- email_bounced - boolean, read-only
- customer_id - integer, read-only, null if the account never bought anything
- order_count - integer, read-only
- total_spend - float, read-only, orders in the store's current currency only
- currency_code - string, read-only
Discount data structure
Dates are GMT. Fields that do not apply to the discount type are null in responses and ignored on write.
- discount_id - integer, read-only
- handle - string, read-only
- title - multilanguage text, up to 50 characters
- discount_type - "coupon", "automatic", "loyalty"; fixed after creation
- amount_type - "percent", "amount"; automatic discounts are always "percent"
- amount - float
- code - string, coupons only
- status - "active", "scheduled", "expired", "error"; read-only, derived from the validity dates
- valid_from - date, null if open-ended; coupon and automatic only
- valid_until - date, null if open-ended; coupon and automatic only
- min_order_amount - float, null if none
- combine_with_special - boolean, whether the coupon also applies to products on sale; coupons only
- auto_assign - boolean, whether new accounts get this discount; loyalty only, one discount at a time
- applies_to - "order", "categories", "products", "shipping"
- applies_to_ids - array of category, product or delivery method ids; empty for "order"
- uses_remaining - integer, counts down on use, null if unlimited; coupons only
- per_customer_usage_limit - integer, null if unlimited; loyalty only
Rate limits and failures
When sending product updates, please do not send more than 1000 items at a time.
Do not send more than 5 API requests per second. Also, anything over 300 requests per minute will result in temporary Access Denied 403 status. Please contact us, if you need more.
Mozello will retry failed notifications for 48 hours.