Managing Inventory
Basic Inventory Concepts
You as a seller may sell the same product in many different ways.
Two copies of a book for sale may both be in used condition, but show very different signs of use.
Or you sell many copies of one book in new condition, with some stored in one warehouse and some in another warehouse (such that handling and transport times differ).
The Kaufland marketplace permits you to save an id_offer
on inventory units to uniquely identify different units of the same product, so these similar units can be tracked and managed independently of one another.
Every inventory change is performed with respect to a single storefront.
Inventory changes performed directly by REST API specify the storefront, and adding an inventory CSV file requires specifying which storefront the file pertains to.
If you are selling on multiple storefronts, units will be connected via your id_offer
.
When units are connected by id_offer
, we ensure that their warehouse and quantity are kept in sync.
Other properties of connected units are allowed to differ by storefront and are not kept in sync (e.g., prices, shipping group, handling time, note).
If you don't want inventory and warehouse to be considered as shared information between two units, they must have different id_offer
.
In order to minimize erroneous synchronization of quantity and warehouse, we will reject attempts to create a unit if we already store a unit with same id_offer
and different EAN or condition, or which is fulfilled by Kaufland.
id_offer
field must be UNIQUE across the seller's entire inventory.
For example, if you use the
id_offer
value "xyz-123"
to offer a product,
then you cannot use the same id_offer
value "xyz-123"
for any other offer
unless offering same Product in a different storefront.
Creating Units
Once you have added an product to the Kaufland marketplace (see the Managing Product Data page), or if the product already exists on the site, you need to add your inventory information. There are two ways to do this:
- REST API: use the
/units/
endpoint to upload inventory data one product at a time. - CSV Files: use the
/import-files/
REST API endpoints to send inventory data for multiple products at once.
Adding new inventory with the REST API
The simplest way to update your inventory data is to send JSON requests to the /units/
REST API
endpoint. However, you can only update one product at a time this way, so far large volumes of changes,
sending CSV files is more efficient.
Note: We prevent this action for units fulfilled by Kaufland and respond with an HTTP 403 error code. Read more about FBK.
To use this endpoint, you need to send a POST
request with a JSON object that describes your
inventory. Here's an example JSON object:
{
"id_product": 35903281,
"ean": "4011905437873",
"condition": "NEW",
"listing_price": 5999,
"minimum_price": 5100,
"amount": 200,
"note": "",
"id_offer": "AB1234",
"handling_time": 2,
"id_warehouse": "1345",
"id_shipping_group": "3457",
"storefront": "de",
"vat_indicator": "standard_rate"
}
Here are explanations for each property of the object:
-
id_product
: The internal Kaufland ID of the product. You must either specify anid_product
orean
(or both). -
ean
: The EAN of the product. You must either specify anid_product
orean
(or both). -
condition
: "NEW" means that the product is not used. The available conditions are listed below. -
listing_price
: The price you would like to sell the product at, in integral cents in the currency of the storefront (CZK or EUR or PLN). This value must be greater than zero, and has a maximum that differs by currency (maximum 25 million CZK, 1 million EUR or 4.5 million PLN). -
minimum_price
: The minimum price you would be willing to sell at, in integral cents of the storefront currency. If this property is specified, the price of your inventory will automatically be adjusted. Only relevant if you want to use Smart Pricing. -
amount
: How many of the product you have in stock. Note that amount is limited to 99999. -
note
: A note about the products condition for the customer. This gives some extra details for used products. This is limited to 250 characters. -
id_warehouse
: The warehouse ID the product is located in. If not specified, your default warehouse. -
id_offer
: Your internal ID for the unit (offer and unit are synonyms on the Kaufland marketplace). Whatever you set here will be included in the unit, but not the product data. This is used to identify units which should be connected over several storefronts. Read more here. -
handling_time
: The amount of working days till the order is handed over to the carrier. (Always use withtransport_time
, which is part of the shipping group.) Has to be equal to or bigger than zero [>=0]. -
id_shipping_group
: ID of the shipping group the unit should be assigned to. -
storefront
: The storefront parameter indicates on which marketplace the offer should be placed. -
vat_indicator
: VAT indicator determining the VAT rate of the unit. The indicator should match the available VAT indicator of the storefront. You can find the most recent VAT indicator mapping at the/vat-indicators/
REST API endpoint.
If you get a 201
response code, then the unit was created successfully. Otherwise,
you should get a JSON object back with an error message in the message
property, for example:
{
"message": "Can not decode body"
}
Note: The POST /units/
endpoint should be used to add new units to an product. However, if you send
data for an product for which you already have a unit, it might update the existing unit, instead of creating a
new unit. Here are the rules for what happens:
When a new unit is created:
- You have no existing units for the product on the same storefront.
- You have existing units for the product on the same storefront, and they do not have an
id_offer
set, and the newly submitted unit has noid_offer
, but the new unit has a differentcondition
than all of the existing units. - You have existing units for the product on the same storefront, and they do not have an
id_offer
set, but the new unit has anid_offer
. - You have existing units for the product on the same storefront, and they have an
id_offer
set, but the new unit has a differentid_offer
. - You have existing units for the product on the same storefront, and they have an
id_offer
, but you send a new unit without anid_offer
.
When an existing unit is updated:
- You have existing units for the product on the same storefront, and they do not have an
id_offer
set, and the newly submitted unit has noid_offer
, but the new unit has the samecondition
as one of the existing units. - You have existing units for the product on the same storefront, and they have an
id_offer
set, and the new unit has the sameid_offer
as one of the existing units.
Available Conditions
String | Integer |
---|---|
"NEW" | 100 |
"USED___AS_NEW" | 200 |
"USED___VERY_GOOD" | 300 |
"USED___GOOD" | 400 |
"USED___ACCEPTABLE" | 500 |
Updating inventory with CSV files
Since you can only add or update one product at a time through the /units/
REST API endpoint,
it can be more efficient to send a batch file with many units in it. There are two types of inventory CSV files:
- INVENTORY FEED file: a full dump of your entire inventory. Details about this type of file are available on the Inventory CSV Files page.
- INVENTORY COMMAND file: a list of commands to alter your existing inventory in the Kaufland marketplace. Details about this type of file are available on the Inventory CSV Files page.
Allowed VAT indicators
Each storefront has a set of eligible VAT indicators for units. Use the /vat-indicators/
endpoint to find the allowed VAT indicators and their corresponding VAT rates for a storefront. For example, the
German storefront allows 'standard_rate' and 'reduced_rate_1' indicators, corresponding to 19% and 7% VAT
rates respectively. Order units will have a VAT rate in the vat
field corresponding to the VAT indicator
provided for the unit.
Retrieving Units
You can get a list of all of your own units by sending a GET
request to the
/units/
endpoint. Note: it can take
several minutes for units to show up in this list after they are created.
Note: By default this endpoint only returns units which need to be fulfilled by the seller. To get units fulfilled by Kaufland an appropriate filter parameter needs to be applied. Read more about FBK.
Updating Units
To update a single unit, send a PATCH
request to the /units/{id_unit}/
REST API endpoint, replacing {id_unit}
in the URL with the internal Kaufland ID of the unit. The
body of the request should contain a JSON object, similar to the JSON you send to create a new unit,
with one difference: you cannot change the id_product
or id_offer
of a unit. To change
those properties, you must delete the unit and create a new one.
Note: We prevent this action for units fulfilled by Kaufland and respond with an HTTP 403 error code. Read more about FBK.
Note: you can also update units by sending a POST
request to the
/units/
endpoint. See the above
note on updating with a POST request for details.
Updating Units in Bulk
Note: We prevent this action for units fulfilled by Kaufland and respond with an HTTP 400 error code. Read more about FBK.
To update multiple units within the same request you can send a POST
request to the /units/bulk
REST API endpoint, the body of the request should contain an array of JSON objects where each one represent a single unit update, each unit request object would look like the following (The example uses handling time, Please refer to the following page for a full list of fields):
[
{
"unit_id": 12345,
"unit_data": {
"handling_time": 1
}
}
]
This will update the handling time of the unit with id 12345, upon a successful request (not a successful unit update, rather the whole request succeeded) the return code will be 207 which means Multi Status
and the response will be an array of objects each one representing the result of a unit update, with a successful unit update the response should look like the following example:
{
"data": [
{
"id_unit": 12345,
"status_code": 200,
"unit": {
"id_unit": 12345,
"status": "AVAILABLE",
"currency": "EUR",
"condition": "NEW",
"note": null,
"id_warehouse": null,
"id_shipping_group": null,
"id_offer": null,
"listing_price": 100,
"minimum_price": 100,
"price": 100,
"id_product": 1,
"amount": 1,
"date_inserted_iso": "2023-11-30T00:00:00.000Z",
"date_lastchange_iso": "2023-11-30T00:00:00.000Z",
"handling_time": 1,
"shipping_rate": 1,
"storefront": "DE",
"transport_time_min": 1,
"transport_time_max": 1,
"fulfillment_type": "fulfilled_by_merchant"
}
}
]
}
The id_unit
and status_code
combination can be used to determine whether the unit was successfully updated or not, the table below explain what each status code stands for as well as an example response:
Status code | Representation | Example |
---|---|---|
200 | Success |
|
400 | Validation error |
|
404 | Unit Not found |
|
500 | Internal server error |
|
Important: There are a couple of rules to keep in mind when using this endpoint, failure to respect these rules will result in the failure of the entire request: :
- Your request SHOULD NOT have more than 150 units in the body, exceeding this limit will result in a 400 response and will fail the whole request.
- The request SHOULD NOT contain duplicate units, if duplicates are detected the whole request is rejected.
Note: Sending an empty request with just {"data": []}
will result in an empty response []
and won't fail the request. Status code will still be 207.
Full example
The following is an example of a request that will contain three unit updates, where one will update successfully, the second will fail with a validation error and the third one will fail with an internal server error in order to demonstrate the three different cases combined:
The request body:
[
{
"id_unit": 12345,
"unit_data": {
"handling_time": 4,
}
},
{
"id_unit": 45678,
"unit_data": {
"listing_price": 0,
}
},
{
"id_unit": 68576,
"unit_data": {
"note": "",
}
}
]
The response:
{
"data":[
{
"id_unit":12345,
"status_code":200,
"unit":{
"id_unit":12345,
"status":"AVAILABLE",
"currency":"EUR",
"condition":"NEW",
"note":null,
"id_warehouse":null,
"id_shipping_group":null,
"id_offer":null,
"listing_price":100,
"minimum_price":100,
"price":100,
"id_product":1,
"amount":1,
"date_inserted_iso":"2023-11-30T00:00:00.000Z",
"date_lastchange_iso":"2023-11-30T00:00:00.000Z",
"handling_time":4,
"shipping_rate":1,
"storefront":"DE",
"transport_time_min":1,
"transport_time_max":1,
"fulfillment_type":"fulfilled_by_merchant"
}
},
{
"id_unit":45678,
"status_code":400,
"message":"Parameters [listingPrice] are missing or have wrong value.",
"errors":[
{
"field":"listing_price",
"message":"listing_price must be greater than 0"
}
]
},
{
"id_unit":68576,
"status_code":500,
"key":"internal_server_error",
"message":"Internal server error"
}
]
}
Deleting Units
To delete a unit, send a DELETE
request to the /units/{id_unit}/
endpoint, replacing {id_unit}
in the URL with the internal Kaufland ID of the unit.
Note: We prevent this action for units fulfilled by Kaufland and respond with an HTTP 403 error code. Read more about FBK.
Retrieving Single Units
You can get the stored information for a single unit if you have its ID. Just send a GET
request to
the /units/{id_unit}/
endpoint, replacing
{id_unit}
in the URL with the internal Kaufland ID of the unit.