Creating Products

Inside this guide:
Introduction
Example Product
Prerequisites
Create a Product
Dealing with errors
Next steps

Introduction

To follow this guide, please ensure you are able to call the Zencargo API either using our API Console or in the HTTP client of your choice. See the Making your first call series of guides for how to do this.

You should also be familiar with the Concepts and how Zencargo models Products.

The Concepts guide covers off exactly how Zencargo models Products. Please read that before starting. The scope of this guide is only to show you how to create Products inside Zencargo and which references you're likely going to store inside your own system. We'll tackle how to update, query, archive and unarchive for a product later guides.

Example Product

Throughout the guide, we'll refer to an example product from an imaginary company: The Bluth Company imports goods to the UK. The want to create the following product.

The first step before creating the product is the to create any associated objects.

First let's look at what associated objects can be optionally created before we can create this product.

Prerequisites

Categories

Categories are an associate object for product and is optional. To create a category you can refer directly to CreateCoreProductCategory mutation.

Attributes

Attributes are an associated object for product and is optional. To create an attribute you can refer directly to CreateCoreProductAttribute mutation.

Create a Product

The easiest way to follow along with this guide is by using the API Console, where you'll be able to copy and paste the example code without having to worry about authentication or formatting. If you're using a different HTTP client, make sure you format the GraphQL correctly.

Defining the variables

Copy and paste the block below into the query variables section of the API console, substituting the following.

The CATEGORY_UUID and ATTRIBUTE_UUID can be retrieved when creating a category CreateCoreProductCategory and creating an attribute CreateCoreProductAttribute or querying a category QueryCoreProductAttribute or querying attribute QueryCoreProductAttribute.

Variables

{
  "input": {
    "accountId": YOUR_ACCOUNT_UUID,
    "name": "Blue T-Shirts",
    "skuCode": "10000",
    "barcode": "J48fFJ3811",
    "categoryId": CATEGORY_UUID,
    "dimensions": {
      "width": 5,
      "height": 10,
      "length": 20,
      "unit": "CM"
    },
    "weight": {
      "unit": "G",
      "value": 100
    },
    "unitsPerCarton": 5,
    "characteristics": {
      "hot": false,
      "hazardous": false,
      "specialHandling": false,
      "refrigerated": false,
      "stackable": true,
      "garmentsOnHangers": false,
      "healthCertificate": false,
      "riskLevel": "LOW"
    },
    "attributes": {
      "attributeId": ATTRIBUTE_UUID,
      "value": ATTRIBUTE_VALUE
    },
    "tariffCodes": {
      "tariffRegionCode": "GB",
      "tariffCode": "12345678"
    },
    "sellCostPrices": {
      "sellCostPrice": {
        "value": 5,
        "currency": "GBP"
      },
      "mainPrice": true
    },
    "buyCostPrices": {
      "buyCostPrice": {
        "value": 5,
        "currency": "GBP"
      },
      "manufacturerId": SUPPLIER_UUID
      "mainPrice": true
    }
  }
}

Now that we have our variables, let's look at how to construct the mutation.

Constructing the mutation and input

We'll need to define the mutation and input types. As we discussed previously, the mutation is called CreateCoreProduct and the input type is CreateCoreProductInput

Paste the code below into the query section (the one at the top in the console) and execute it.

mutation ($input: CreateCoreProductInput!) {
    createCoreProduct(input: $input) {
        product {
            id
            name
            skuCode
            barcode
            category {
                id
                name
            }
            dimensions {
                width
                height
                length
                unit
            }
            weight {
                value
                unit
            }
            unitsPerCarton
            cbmPerUnit
            characteristics {
                hot
                hazardous
                specialHandling
                refrigerated
                stackable
                garmentsOnHangers
                healthCertificate
                riskLevel
            }
            attributes {
                attribute {
                    id
                    name
                    type
                }
                value
            }
            tariffCodes {
                tariffCode
                tariffRegionCode
            }
            sellCostPrices {
                sellCostPrice {
                    value
                    currency
                }
                mainPrice
            }
            buyCostPrices {
                buyCostPrice {
                    value
                    currency
                }
                manufacturer {
                    id
                }
                mainPrice
            }
            status
        }
    }
}

You should get back this response, which mimics the body of the response you'd get in a real HTTP request.

NOTE: The various ids e.g. product id and category id will not match what you get back in the actual response.

JSON response

{
  "data": {
    "createCoreProduct": {
      "product": {
        "id": "cfeeb6ee-91c4-46b1-9411-71185d359324",
        "name": "Blue T-Shirts",
        "skuCode": "10000",
        "barcode": "J48fFJ3811",
        "category": {
          "id": "b426b1d7-6210-4cd1-ac65-b3dc184c473b",
          "name": "Clothes"
        },
        "dimensions": {
          "width": 5,
          "height": 10,
          "length": 20,
          "unit": "CM"
        },
        "weight": {
          "unit": "G",
          "value": 100
        },
        "unitsPerCarton": 5,
        "cbmPerUnit": 100,
        "characteristics": {
          "hot": false,
          "hazardous": false,
          "specialHandling": false,
          "refrigerated": false,
          "stackable": true,
          "garmentsOnHangers": false,
          "healthCertificate": false,
          "riskLevel": "LOW"
        },
        "attributes": [
          {
            "attribute": {
              "id": "b6e596dd-203b-4867-a553-b782d5b0ea10",
              "name": "Colour",
              "type": "TEXT"
            },
            "value": "Blue"
          }
        ],
        "tariffCodes": [
          {
            "tariffRegionCode": "GB",
            "tariffCode": "12345678"
          }
        ],
        "sellCostPrices": [
          {
            "sellCostPrice": {
              "value": 5,
              "currency": "GBP"
            },
            "mainPrice": true
          }
        ],
        "buyCostPrices": [
          {
            "buyCostPrice": {
              "value": 5,
              "currency": "GBP"
            },
            "manufacturer": {
              "id": "b426b1d7-6210-4cd1-ac65-b3dc184c473b"
            },
            "mainPrice": true
          }
        ],
        "status": "ACTIVE"
      },
      "errors": []
    }
  }
}

Congratulations! You've created your first Product inside Zencargo. Looking over the data we got back it's worth reiterating a point: you're getting back only the data you requested, not what was created as you might expect from another type of API.

One thing we're not requesting is any errors. This call succeeded, but that won't always be the case.

Let's finish our guide with the final part: how to uncover errors.

Dealing with errors in your mutations

By now, you're familiar with the idea that you can request what you'd like from the return value of the mutation. As you can see from our CreateCoreProduct mutation documentation, we are able to retrieve an errors field.

In real requests and responses, there are two places that errors can be returned by Zencargo:

{
  "errors": [
    "system errors will be found in here"
  ],
  "data": {
    "NameOfTheOperation": {
      "errors": [
        "Field validation errors will also be found in here"
        ]
    }
  }
}

NOTE: the API console only allows for you to introspect the "data" property of the response. You can trigger errors at the top level by using another HTTP client.

How you handle errors is entirely down to you. You can consult the official GraphQL docs or literature online for different strategies. For now, we'll focus on one specific use case: an error when you try to send a mutation containing invalid data.

In your API console, leave the variables data the same, but add an errors object in the query, in the top level.

mutation ($input: CreateCoreProductInput!) {
    createCoreProduct(input: $input) {
        product {
            id
            name
            skuCode
            barcode
            category {
                id
                name
            }
            dimensions {
                width
                height
                length
                unit
            }
            weight {
                value
                unit
            }
            unitsPerCarton
            cbmPerUnit
            characteristics {
                hot
                hazardous
                specialHandling
                refrigerated
                stackable
                garmentsOnHangers
                healthCertificate
                riskLevel
            }
            attributes {
                attribute {
                    id
                    name
                    type
                }
                value
            }
            tariffCodes {
                tariffCode
                tariffRegionCode
            }
            sellCostPrices {
                sellCostPrice {
                    value
                    currency
                }
                mainPrice
            }
            buyCostPrices {
                buyCostPrice {
                    value
                    currency
                }
                manufacturer {
                    id
                }
                mainPrice
            }
        }
        errors {
            path
            message
        }
    }
}

Run this mutation again, with the same variables, you'll get back this response

JSON Response

{
  "data": {
    "createCoreProduct": {
      "errors": [
        {
          "message": "SKU code has already been taken.",
          "path": "skuCode"
        }
      ],
      "product": null
    }
  }
}

As you can see, we tried to create a second Product with a duplicate skuCode and we got back an errors array containing objects. These objects tell us the path and message. You can use these, if you like, to inform your retry strategy.

Next Steps