GraphQL for HCL Commerce

The GraphQL markup language is available for any API. It is a server-side interpreter for processing queries using a data type system you design. With GraphQL, your data and code are independent of any database or storage system.

Introduction to GraphQL

REST responses often contain too much or not enough data, requiring a second request. GraphQL addresses this issue by retrieving just the data you need using a single request. GraphQLmakes APIs fast, versatile, and developer friendly.

GraphQL is comparable to REST in many aspects, and it frequently uses the same HTTP(s) transports as REST. Instead of using a variety of route URIs and HTTP verbs, it utilises a single endpoint with a specified schema that describes how to both fetch and alter data. Consequently, network costs are reduced and latency is decreased because you no longer have to make multiple server requests.

GraphQL makes it simple to construct APIs on time and search your data using a GraphQL schema that is automatically built. This ensures that when you use GraphQL to manipulate data, the resolver sends your request to the REST controller.

The following example demonstrates the fundamental differences between the REST API and GraphQL when it comes to fetching data from an API:

GET : https://@localhost/wcs/resources/store/1/cart/@self

In the above example, a REST API would use a GET request to retrieve a record. It will collect and return a full response. With a REST API, you typically collect all data by accessing multiple resources.

In GraphQL, you need only send a query containing specific data requirements to the GraphQL server. The following example demonstrates how multiple REST requests may be replaced with a single GraphQL request.

A data query and update language for building supporting APIs:

A single GraphQL request
  • Multiple resources can be queried in a single request
  • Query by example response filtering
  • Examine the connections between related resources
query {
  cartGetCart(storeId:”1”) {
    grandTotal
    grandTotalCurrency
    orderItem {
      partNumber
      quantity
      promotion {
        schedule {
          endDate
        }
      }
    }
  }
  eSpotFindByName(storeId:”1”,name:”TopBrowsed_CatEntries”){
    marketingSpotData {
      behavior
    }
  }  
}

Benefits of GraphQL

GraphQL is a syntax for describing data requirements and interactions. It enables you to request exactly what you need and receive predictable outcomes. By streamlining how you handle your data, you can develop advanced web and mobile apps quickly with GraphQL. In a GraphQL query you specify how the data should e structured as it is returned from the server. This allows you to query only the data you want in the format you require. In a single network request, you may query and obtain numerous chunks of information from various sources, ensuring speedier response times. GraphQL has all these capabilities, combined with excellent developer tools, making it vital for improving the HCL Commerce experience.

For creating APIs, GraphQL is used with REST, not as a replacement. The GraphQL query itself is not faster than REST queries, but since you can choose what fields to query, the GraphQL request is always better. This is in contrast to REST, which frequently returns more data, even if it is not critical or useful. GraphQL also allows developers to obtain several things in a single request, increasing the efficiency of each query.

The main difference between GraphQL and traditional REST APIs is that REST often returns a full data block in a JSON response, which must be processed and distributed. Instead, GraphQL is built on schema, queries, and resolvers, with the goal of improving on the REST concept by enabling you to request a specific type of data rather than the full chunk. You don't have to go through a lot of information since you only get the information you requested.

However, keep in mind that GraphQL and REST are two separate things: GraphQL is a language and a technology, whereas REST is an architecture style. This implies that as more teams use GraphQL, REST will continue to exist.

  • Sales competitiveness

    Applications are now routinely developed for multiple form factors, such as iOS and Android, so it is important to simplify application development across all of these platforms. This is where GraphQL is useful. With GraphQL, you are able to customize the response shape for each request. Additionally, API Endpoint management is simplified, as it exposes a single HTTP Endpoint (/graphql) to fetch required data.

  • Real benefits available for client-server communication

    GraphQL is a language for communicating between remote customers and servers. Resolvers are arbitrary functions that are used to access and manipulate data. The data from these resolver functions is integrated and consolidated by GraphQL, which then provides the output to the client. These resolver functions should, in most cases, be outsourced to a business stack that is responsible for connecting with the different underlying sources of data. Remote APIs, databases, local cache, and almost anything else your programming language can access might be used as data sources.

    • Tailoring responses to only include desired data

      GraphQL queries always deliver expected or accurate responses, with no irrelevant information included. In other words, GraphQL eliminates the issue of Under Fetching and Over Fetching that was once a concern when utilising REST Apis to retrieve data.

    • Issuing multiple operations with a single client-server exchange

      GraphQL is significantly quicker than other communication APIs because it allows you to narrow down your request query by selecting only the fields that you wish to query. It allows you to retrieve all of the data you need from a single request, rather than spreading various pieces of the data across numerous endpoints. Instead of contacting two distinct endpoints, you may receive user information and order information in a single query.

    • Chaining operations across services in a single request

      Links can be used to describe how a value returned by one operation can be input into another operation. By establishing links, processes are connected and navigated as if they are linked. With GraphQL APIs, your application can access all the data it needs in a single API call. This eliminates the need for many API calls for a single operation.

    • Definition of higher level services built by orchestrating lower level ones (‘Backend-for-Frontend’)

      The Backend For Frontend (BFF) layer is made up of several backends that were created to meet the demands of various frontend frameworks, such as desktop, browser, and native-mobile apps. Multiple data sources may be combined into a single GraphQL interface with GraphQL.

    • Built-in introspection and discoverability

      The introspection capability of GraphQL allows you to navigate inside the types and learn the schema, ensuring that your apps only ask for what's feasible and in the right manner. You can see what the schema can query and how the data is organised. You may then use a GraphQL IDE to effortlessly add additional fields to existing queries. GraphQL validates the data format for you, so you don't have to. You simply develop resolvers, which are the methods for receiving data.

      Since the result set or delivered data in GraphQL is highly particular to the client's query, generalising it is very straightforward and easy for the server. Existing customers are unaffected when we add new product features or more fields to the server. Because server fields can be deprecated but still operate, you can utilise the older server without fear.

Example

Create cart:

mutation {
  cartCreateOrder(storeId: "1", description: "Test Order description") {
    outOrderId
  }
}

response:
{
  "data": {
    "cartCreateOrder": {
      "outOrderId": "1050717601"
    }
  }
}
Add an item to cart:
mutation {
  cartAddOrderItem(storeId: "1", requestBody: {orderId: "1050717601", orderItem: {productId: "12687", quantity: "2"}}) {
    orderItem {
      orderItemId
    }
  }
}

response:
{
  "data": {
    "cartAddOrderItem": {
      "orderItem": [
        {
          "orderItemId": "15001"
        }
      ]
    }
  }
}
Update order item:
mutation {
  cartUpdateOrderItem(storeId: "1", requestBody: {orderId: "1050717601", orderItem: {quantity: "3", orderItemId: "15001", productId: "12687"}}) {
    orderId
  }
}

response:
{
  "data": {
    "cartUpdateOrderItem": {
      "orderId": "1050717601"
    }
  }
}
Get cart:
query {
  cartGetCart(storeId:"1"){
    orderId
    orderItem{
      quantity
    }
  }
}

response:
{
  "data": {
    "cartGetCart": {
      "orderId": "1050717601",
      "orderItem": [
        {
          "quantity": "3.0"
        }
      ]
    }
  }
}
Calculate order:
mutation {
  cartCalculateOrder2(storeId: "1", orderId: "1050717601") {
    orderId
    viewTaskName
  }
}

response:
{
  "data": {
    "cartCalculateOrder2": {
      "orderId": [
        "1050717601"
      ],
      "viewTaskName": "RedirectView"
    }
  }
}
Pre-checkout:
mutation {
  cartPreCheckout(storeId: "1", requestBody: {orderId: "1050717601"}) {
    orderId
  }
}

response:
{
  "data": {
    "cartPreCheckout": {
      "orderId": "1050717601"
    }
  }
}
Adding payment instructions:
mutation {
  paymentInstructionAddPaymentInstruction(storeId: "1", requestBody: {orderId: "1050717601", resourceId: "https://localhost:443/wcs/resources/store/1/cart/@self/payment_instruction", paymentInstruction: {email1: "a1@a1.com", email2: "a2@a2.com", fax1: "", fax2: "", phone1: "123", phone2: "234", mobilePhone1: "1", mobilePhone1Country: "23", nickName: "Hello", billingAddressId: "3074457359254738956", piAmount: "9.42", state: "MH", payMethodId: "COD", piDescription: "COD"}, xIsPurchaseOrderNumberRequired: "false", xIsPersonalAddressesAllowedForShipping: "true", resourceName: "cart"}) {
    orderId
  }
}

response:
{
  "data": {
    "paymentInstructionAddPaymentInstruction": {
      "orderId": "1050717601"
    }
  }
}
Checkout:
mutation {
  cartCheckOut(storeId: "1", requestBody: {orderId: "1050717601"}) {
    orderId
  }
}

response:
{
  "data": {
    "cartCheckOut": {
      "orderId": "1050717601"
    }
  }
}
Cancel order:
mutation {
  cartCancelOrder(storeId: "1", orderId: "1050717601") {
    viewTaskName
  }
}