Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Most customers implement Nosto by installing a Nosto extension to their e-commerce platform. The extension provides a working out of the box implementation for majority of websites handling installing tagging and product updates. However, for customized PWA/SPA environments, you should follow the additional SPA/PWA guides.
Implementing by a Nosto Extension
Implement on your SPA
Implement on your PWA
Implement on your Headless
Implement on a standard e-commerce store
When implementing in SPA and PWA environments, product updates must be done via REST API. In case you are using some of the platforms that Nosto has extension for the extension takes care of the product updates.
If you have implemented SPA / PWA on top a platform that Nosto has extension for you will still need to implement the frontend part using Session API. The extension will take care of the product updates, order confirmations, exchange rates and other background processes but displaying the recommendations, popups, etc. must be done using Session API.
In case your website implement some dynamic functionality, you can use the JS API. Note that you can not mix Session API and JS API.
You must use a valid domain for your website. If you are creating a test account and running your store locally, you must use valid TLD as using localhost
is not supported.
You cannot use the following domains as they are reserved by the IANA.
.test
.example
.localhost
.invalid
We recommend using a valid TLD that is aliased to localhost
for testing purposes. You will need to edit your operating-system dependent hosts file to add an alias for the domain you are using.
Nosto periodically crawls your website to keep the catalog data in sync and therefore if you run your webshop locally, Nosto will be unable to crawl your website. In order to overcome this, you will either need to:
make it publicly available using a service such as or
Use the to keep your catalog in sync
To implement Nosto manually you will need to go through the following steps to ensure that the store data is captured by Nosto. The following steps will allow Nosto to gather product, cart and order data, and analyze how individual customers are interacting with this data. The implementation steps listed here are necessary for both functionalities based on crowd logic and 1-1 behavioral personalization.
If the store is built on explicitly supported platforms like Magento, Magento 2, Shopify, Prestashop or Shopware you should go through their platform specific guides instead.
On every page load, the cart content must be tagged. The cart contents are the 1:1 representation of the user's mini-cart.
The cart information is used by the Nosto to tailor the recommendations, dispatch abandoned cart emails and fire Facebook pixel events for retargeting purposes.
Note: The product ID of the product tagging, cart tagging and order tagging must match. Failure to do so will lead to a mismatch in both attribution and statistics across the Nosto product.
Many e-commerce stores utilize SKU:s or "child" products that are sorted under the same "parent" product. To extend the above example with SKU support refer to this article
In cases where a product might have multiple prices in differing currencies, you can also add support for multi-currency. Refer to this article
If the platform itself has support for persistent shopping cart or other technologies that remember the users cart contents you do not need to worry about filling out the cart when a user returns to the site. If your platform generates a restore cart link you can also send that to Nosto by adding it as a new attribute within the parent container "nosto_cart".
The following piece of code is just a rough example on how a restore cart could look like. The idea of the example is to document how this is tagged to Nosto.
Once included on all pages, you can review if the site is transmitting data using the Nosto Debug Toolbar. If you can see cart contents being picked up under "Tagging" → "Cart" then the cart details are correctly set up in the source code. You can further verify your session in the Nosto admin by using the live feed under https://my.nosto.com/admin/$accountID/liveFeed to see if Nosto correctly picks up product view → product carted events.
The translate attribute is a HTML5 standard attribute which specifies whether the value of the element and it's Text
node children should be translated. If your tagging elements are being translated by e.g. Google Translator then this is the way to opt out elements being translated by Google and possibly other vendors.
To start tracking visits and content the Nosto script needs to be active on all pages within the store where the user might navigate. Replace $accountID
from the code below with your own account ID and place the code within the <head>
section of your sites HTML content. You can find your stores account IDs from the account list within the Nosto admin.
Note: The script and the snippet should be added as high up in the <head>
portion of the page so the connection is initialised as soon as possible. As the script is flagged async
, the page load isn’t delayed.
Note: This needs to exist on every page.
Alternatively to the script injection Nosto can also be used as a library dependency in your Javascript application via the following utility library Nosto Js
Once included on all pages, you can review if the site is transmitting data using the Nosto Debug Toolbar. If the debug toolbar executes and shows up on the page Nosto can track visits on the page. You can further verify your session in the Nosto admin by using the live feed under https://my.nosto.com/admin/$accountID/liveFeed
On every page, the customer information should be tagged if the customer is logged in. If the customer isn't logged in, this but can be omitted.
The customer information is primarily used for sending personalised triggered emails and for building multi-channel experiences.
The new marketing-permission flag denotes whether the customer has consented to email marketing. If the marketing-permission field is omitted, we assume that the current customer has not given their consent and Nosto will refrain from sending out any personalized triggered emails.
The marketing permission is false by default but if a user has explicitly agreed to receive marketing then you can set it to true manually. In practice, this means reading and mapping the value from opt-in for marketing in your platform e.g. a consumer explicitly subscribed for marketing emails when checking out.
The marketing-permission should be included as a part of the customer tagging and should be rendered on all pages.
The customer-reference can be leveraged to unify sessions across channels such as between online and offline. It is a unique identifier provided by you that is used in conjunction with the Nosto cookie. The customer-reference can also be used to uniquely identify users in lieu of an email address.
The customer-reference should be a long, secure and a non-guessable identifier. For example, use your internal customer-id or the customer's loyalty program identifier and use a secure hash function like an HMAC-SHA256 to hash it.
Basic tagging
Nosto also supports multiple optional values which may enrich the usage of the service, but are not required. These span elements should be inserted into the "nosto_product" parent container.
Tagging attribute extension
Prices must always be denoted in a simple numerical form using dot as the decimal separator. For example, 1.234,45
is invalid while 1234.45
is valid.
Categories must always be delimited by a slash. For example, /Home/Accessories
is a valid category while Home > Accessories
is not.
Currencies should always be represented in the ISO-4471 three-letter format. For example, use the code USD
instead of $
to represent the United States Dollar.
The availability of a product is represented by InStock
or http://schema.org/InStock
for products that are in stock and saleable. For products that are out of stock or you don't want to be recommended, you can use OutOfStock
or http://schema.org/OutOfStock
The rating of a product must be represented as a number between 0.0 and 5.0. For example, a product cannot be rated 9.1. You must normalize your rating value to fit our specified range.
The three tag fields, tags1
, tags2
and tags3
are simply labels that can be used to annotate tags like discounted
, limited collection
or other use cases where you might want to filter your Nosto recommendations by certain product groupings.
Custom fields accept a key:value pair where the class
of the attribute is the key. Common use cases are material
, color
or other similar unique identifiers.
In the event that you are unable to expose the entire subset of the product tagging, you can simply tag the product-id.
Note: The product tagging must be server-side rendered as the Nosto crawler does not execute Javascript.
When the entirety of the product metadata is tagged, Nosto is able to crawl your site and build a 1:1 replica of your product catalog but in this basic example, you will need to use an alternative mechanism for synchronising your catalog with Nosto.
Note: If you do use this approach, your account-manager must disable crawling for your account. Failure to do so will result in a broken catalog replica.
In order to keep your product catalog in Nosto up to date, you must leverage the Products API.
Nosto does not support a product feed and you must leverage the API in order to synchronise your product catalog.
Once included on all pages, you can review if the site is transmitting data using the Nosto Debug Toolbar. If you can see product attributes being picked up under "Tagging" then the product details are correctly set up. You can further verify that products are being indexed to the catalog under the Nosto admin by navigating to Tools → Products: https://my.nosto.com/admin/$accountID/campaigns/products/list
The translate attribute is a HTML5 standard attribute which specifies whether the value of the element and it's Text
node children should be translated. If your tagging elements are being translated by e.g. Google Translator then this is the way to opt out elements being translated by Google and possibly other vendors.
Nosto utilizes meta tags to track what category or brand a certain visitor is viewing or what page type the currently viewed page is. These values are then used for dynamic filtering for categories and brands applied through the Nosto admin UI or exposure of certain pop-up campaigns for page types.
The category tagging should be exposed whenever a user is viewing a certain category.
The brand tagging should be exposed whenever a user is viewing a certain brand or vendor.
Categories must always be delimited by a slash. For example, /Home/Accessories
is a valid category while Home > Accessories
is not.
With Nosto you can also expose other attributes that should be used for category/brand page filtering. For example when a user clicks on a certain color, only products with that certain color attribute should be exposed by both the category list, and Nosto Onsite Recommendations. Available values correspond to custom fields tagged as part of the .
Page type tagging should be exposed whenever a user is interacting with a page so Nosto understands what kind of page this is.
Page type is optional and used mainly for triggering popups and also to understand what kind of page the user is currently interacting with. The page type must always be lowercase and the accepted values for page type are: front
, category
, produc
, cart
, order
, search
and notfound
.
Once included on all pages, you can review if the site is transmitting data using the Nosto Debug Toolbar. If you can see order contents being picked up under "Tagging" → "Category" then the category and page type tagging are correctly set up in the source code.
The category of your item based on the Google product taxonomy. Use the schema provided by Google here ()
It is possible to tag also the currently viewed product sku. Typically, this would be done on a product detail page when the user chooses a specific color or size and you would like to update recommendations to highlight other products with similar attributes. Most common approach would be to implement it by calling the or the from a click-listener to send the sku information and update the recommendations. If, however, the preference is to use tagging to specify the selected sku instead, that can be done through tagging by adding a span under product with the class name selected_sku_id
, for example: <span class="selected_sku_id">40822930473153</span>
Nosto also supports two attributes that are not crawlable through tagging. This is due to the sensitive nature of the attributes. Those are: supplier_cost
and inventory_level
. To send these two values to Nosto you will need to use the .
Many e-commerce stores utilize SKU:s or "child" products that are sorted under the same "parent" product. To extend the above example with SKU support refer to
In cases where a product might have multiple prices in differing currencies, you can also add support for multi-currency. Refer to
If you want to use Nosto’s margin filter, you need to send supplier cost via since it's a sensitive data that you might not want to expose in the product tagging.
Once included on all pages, you can review if the site is transmitting data using the . If you can see product attributes being picked up under "Tagging" then the product details are correctly set up. You can further verify that products are being indexed to the catalog under the Nosto admin by navigating to the Catalog Explorer: https://my.nosto.com/admin/$accountID/products
The translate attribute is a which specifies whether the value of the element and it's Text
node children should be translated. If your tagging elements are being translated by e.g. Google Translator then this is the way to opt out elements being translated by Google and possibly other vendors.
The translate attribute is a which specifies whether the value of the element and it's Text
node children should be translated. If your tagging elements are being translated by e.g. Google Translator then this is the way to opt out elements being translated by Google and possibly other vendors.
Nosto utilizes tracks what a customer is searching for by reading the search query from the URL's query parameter or from the page source.
When the search term exists as a part of the URL's query parameters e.g. https://www.example.com?q=searchterm
, Nosto can be configured to read the search term and you can skip the search term tagging.
When the search term exists as a part of the URL e.g. https://www.example.com/searchterm
, Nosto is unable to read it from the URL and you will need to tag as a part of the page source. When you implement the tagging for the search term, remember that it is untrusted user input added as part of your page html and it should be html-encoded to prevent XSS vulnerabilities on the site.\
All thank-you and order-confirmation pages must have the conversion tracking markup.
The conversion metadata is used for sending personalised order-followup emails, personalise the recommendations e.g. order-related, for segmentation insights and conversion statistics.
Note: The product ID of the product tagging, cart tagging and order tagging must match. Failure to do so will lead to a mismatch in both attribution and statistics across the Nosto product.
You can omit the buyer tagging either partially, or completely if you do not want Nosto to crawl this information. The user details are stored for possible marketing purposes and mainly observed email address is used in this context. Marketing permission is false by default but if this user has explicitly agreed to receive marketing then you can set it to true manually.
Currencies should always be represented in the ISO-4471 three-letter format. For example, use the code USD
instead of $
to represent the United States Dollar.
Payment provider is the payment method or provider used by a shopper to pay the purchase. Omit the payment provider detail if you do not want Nosto to crawl this information.
Status code will be used to track the order state. Different payment providers may use different status codes.
Many ecommerce stores utilize SKU:s or "child" products that are sorted under the same "parent" product. To extend the above example with SKU support refer to this article
In cases where a product might have multiple prices in differing currencies you can also add support for multi-currency. Refer to this article
Once included on all pages, you can review if the site is transmitting data using the Nosto Debug Toolbar. If you can see order contents being picked up under "Tagging" → "Order" then the order details are correctly set up in the source code.
You can further verify your session in the Nosto admin by using the live feed under: https://my.nosto.com/admin/$accountID/liveFeed to see if Nosto correctly picks up product view → product carted → product bought events. You can export all the order history from the store under Settings → Other → Order report under https://my.nosto.com/admin/$account/account/orders/report
The translate attribute is a HTML5 standard attribute which specifies whether the value of the element and it's Text
node children should be translated. If your tagging elements are being translated by e.g. Google Translator then this is the way to opt out elements being translated by Google and possibly other vendors.
All product pages should contain the product tagging. The product tagging can be the entire metadata or only a small subset of it.
The product tagging is used to pass the context of the current product being viewed which in turn is used to personalise the recommendations e.g. cross-sellers, and commonly also periodically crawled by Nosto to build an index.
Note: The product tagging must be server-side rendered as the Nosto crawler does not execute Javascript.
You can tag your product pages in two different ways:
Tagging all the metadata (Recommended): This approach is the recommended way to tag your product pages. It contains the entirety of the product metadata and leverages the crawler to build a 1:1 replica of your catalog.
Tagging the bare minimum: This approach entails tagging just the product-id and requires you to leverage an API to build a 1:1 replica of your catalog. This is an advanced use-case and requires that your account-manager disables crawling for your website.
This guide introduces you how to implement Nosto on a e-commerce store that does not yet have a dedicated plugin solution. The articles are designed as digestable step-by-step guides that walk you through how to establish the data exchange between the site and Nosto.
First its important to understand a few of the concepts before delving in to the documentation, to make sure that you as a integrator understand the different steps and tools required.
Nosto initializes by using a snippet of Javascript that starts the dialogue to your dedicated account.
Nosto depends on structured data that we extract from your site. At the bare minimum you need to go through all the steps listed under Manual Implementation - Essentials.
You can augment and extend the product tagging and the data collection process with the help of other articles found under this guide.
You can access your own account in the Nosto admin UI my.nosto.com/admin where you can enable/configure/modify features. All templating and layouts are handled within your account.
In case you have already implemented Nosto and established continuous data exchange you can find more information related to troubleshooting or setting up features at help.nosto.com.
Implementation Checklist
As a first step, please check if your e-commerce platform or software is already supported by a Nosto extension or integration. In case the platform is supported we warmly recommend to use an extension and reading the platform specific guide as this saves you some manual effort and time, since the implementation process differs a bit from the one described in this article series and practically automates all the steps.
Second, make sure that you have a Nosto account and if not, sign up on Nosto home page or contact Nosto sales.
Every Nosto account has a unique identifier known as accountID
, which is required in the implementation. If you know that you have an account, but don’t know your accountID
, log-in to your Nosto admin panel and learn where you can find it!
Third, if you first implement Nosto on a local device or on a development environment, bookmark this article about implementing Nosto on a test environment for later reading. No need to jump there yet, as it is also featured as the last article in this series.
The nosto
parameter allows Nosto to attribute clicks on content and recommendations. In the event, you'd like to omit the parameter, you'll need to manually send the product-view event. You can do so by executing the following snippet.
How the attribution is tracked will be entirely dependent upon your implementation.
Implementing Nosto on a native mobile application allows a retailer to collect behavioral events similarly as within a traditional web page. This information will then be merged with Nosto data across other sources, impacting product relationships and real-time statistics across the board.
Read more about the commercial benefits of Mobile Application support here: https://www.nosto.com/products/mobile-app-personalization/
Due to the nature of the technical environment related to Native Application development, both behavioral and transactional data needs to be sent manually, and consequently all requests for personalization features needs to be tailored within the application as well.
Read more about Nosto's GraphQL API: https://docs.nosto.com/techdocs/apis/graphql-an-introduction
Read more about implementing Nosto with GraphQL on IOS and Android: https://docs.nosto.com/techdocs/apis/graphql-an-introduction/graphql-for-ios-and-android
You can define placements for Nosto to use via a code block called div-elements. Each element marks a location in your site where Nosto can hook into and expose onsite content.
Here is an example of a <div>
tag on the site:
The class needs to always reference nosto_element
so Nosto understands that this element is available for onsite content placement. However the id frontpage-nosto-1
is flexible but requires that each unique element-id has a matching placement defined in Nosto's admin dashboard in order to expose campaigns.
Here is an example of a page with multiple <div>
elements:
For multi-channel retailers tying the brick-and-mortar stores into Nosto's personalization solution allows retailers to collect all data into one. This information will then be merged with Nosto data across other sources, impacting product relationships and real-time statistics across the board. Retailers who have unified their data, can also start matching customers across different channels, and personalize every aspect of their shopping journey.
Read more about the commercial benefits of Mobile Application support here: https://www.nosto.com/products/in-store-personalization/
Since Search Templates utilize the Search API under the hood, please also check the Search API FAQ
The functionality enables the sharing of a single instance of search templates across multiple dashboard accounts through linking. This feature proves particularly advantageous in scenarios where there are multiple websites with identical or similar characteristics that necessitate the creation of multiple dashboard accounts (such as supporting multiple languages or environments).
To link multiple accounts contact support!
Even if multiple websites share the same search templates code, we can easily have different logic based on website host or language (or other criteria).
Since it's not possible to target CSS rules by domain, it's recommended to add a special class to the page body and use it to target CSS rules.
By default, the search indexes all SKUs as a single product. Therefore, even when searching by a specific SKU attribute (like SKU color or ID), the search will return the main product along with all SKUs.
However, because the search returns all SKUs, SKU selection logic can be implemented on the frontend side. This is achieved by checking each SKU to see if it contains text from the search query.
These is an example on how to implement SKU selection:
By default, the search API returns 100 values for each facet, and it's not possible to control that limit in the dashboard. However, it is possible to override the facet configuration directly from the code.
The first step is to know the facet ID of the facet you want to overwrite. The facet ID is stored in the dashboard URL. For example, if you open the facet in the facet manager, the URL should be https://my.nosto.com/admin/shopify-123/search/settings/facetManager/6406df867f8beb629fc0dfb9
. This means the facet ID is 6406df867f8beb629fc0dfb9
.
Once the ID is known, it's possible to override any facet setting by specifying overwrite properties in the customFacets
parameter:
Although search engines can understand some JavaScript-rendered code, they often miss search templates. The reason for this is that the rendering of search templates is delayed in order not to hinder the page loading speed.
However, it's still possible to achieve great SEO results while using the code editor:
Category pages - Ensure that the category page already returns the correct meta tags and page title according to SEO recommendations, they bring the biggest impact to the SEO. In category page search templates render only products, so it doesn't significantly impact SEO. Most search engines support structured data (the category page backend should generate these tags using original products). However it does not have any big impact to the SEO. Furthermore, search engines may not favor the discrepancy between structured data and the actual rendered products (cause search engine will see either empty page with loader or nosto search results that are different compared to original).
Search pages - Most search engines don't index search pages, so no optimizations are needed.
If you still have concerns regarding SEO, please consider using API integration.
Nosto supports individual product SKUs under parent products. If you have not set up Product tagging you should start there and extend the tagging if needed.
The SKU attributes should be listed on the last row of the nosto_product
block that you have already implemented on the product pages.
What is a SKU?
Many e-commerce stores have a parent product with individual child products. The parent product is usually something along the lines of "Ski Jacket" whereas the SKUs would then be "Ski Jacket, Blue, Small", "Ski Jacket, Red, Medium". If your store uses SKUs you should add the following attributes to extend your product tagging.
Note: The attribute custom_fields
can contain whatever unique information for individual SKUs that you can >consider helpful. Frequently used attributes would be size, color, material.
Extending the cart tagging with SKU metadata
When tagging the cart contents as outlined here, you can also tag information of the actual SKU that was added to cart. Notice the extra <span class="sku_id">
attribute.
Extending the order tagging with SKU metadata
When tagging the order contents as outlined here, you can also tag information of the actual SKU that was added to cart. Notice the extra <span class="sku_id">
attribute inside each of the purchased_items
.
Once included you can review if the SKUs are picked up by using the Nosto Debug Toolbar. If you can see individual SKUs being picked up below the original product details then this is correctly set up.
You can further verify that products are being indexed to the catalogue under the Nosto admin by navigating to Tools → Products (https://my.nosto.com/admin/$accountID/campaigns/products/list)
No, Nosto does no recommend individual SKUs. While this is something on our roadmap, at the moment, you do not need to send any events when an SKU is selected.
For example, assume you had a product page selling a shoe. In this case, the product tagging would always point to the id of the shoe. No events should be dispatched when the customer selects a particular size such as S, M, L.
In this article, you will learn how to implement multi-currency in Nosto. When the implementation is complete, you will be able to display product prices (in any feature) in different currencies.
Prior to the multi-currency implementation, ensure that the Nosto tagging is correctly in place. Some of the tagging must be slightly amended to support multi-currency.
For instructions on integrating with Shopify's multi-currency, please go here.
The product page tagging must be amended to denote the primary currency code of the product. Typically, most retailers have a primary currency which is the default currency of the inventory.
For example, a US-based retailer who sells in Euros (EUR) and Sterling Pounds (GBP) would have US Dollar (USD) as the primary currency while Euro (EUR) and Sterling Pounds (GBP) would be secondary currencies whose exchange rates would need to be sent via an API.
An additional span tag must be placed within the product page tagging with a class name variation_id
. The tag is a child element of the nosto_product
element.
Note: The code in the
variation_id
element must remain static, regardless of the currency active on-site. This is the primary currency of your catalog. Althoughvariation_id
element often has the same currency code as in theprice_currency_code
element and may seem redundant, they support different use cases and both need to be tagged.
Yes. Prices for all SKUs will automatically be converted using the same logic. As long as your SKUs are tagged, no additional changes are needed.
The cart and order tagging can be left as-is but the prices must be in the customer's currently active currency. For example, a customer shopping in Swiss Francs (CHF) should have all the cart items tagged in Swiss Francs (CHF). Failure to do so will result in incorrect prices in any triggered mails such as abandoned cart or order followup.
Once you have amended the product tagging, an additional DIV element must be added to all the other pages (including the product page itself). The tag should not be encapsulated in the nosto_product
DIV tag. The information sent in the tag refers to the currency active of the customer.
For example, on the site of a US-based retailer who sells in Euros (EUR) and Sterling Pounds (GBP), if the customer changes the currency to Sterling Pounds (GBP), the nosto_variation
element should show GBP
. If the customer changes the currency to Euros (EUR), the nosto_variation
element should show EUR
.
In order to send the exchange rate multipliers to Nosto, you will need to use our exchange-rates API. Below is a small snippet of what the payload looks like.
In the example above, 0.77
is the exchange rate from US Dollars (USD) to British Pounds (GBP) and 0.91
is the exchange rate from US Dollars (USD) to Euros (EUR).
The valid_until
entry defines the expiration date. When the expiration date is reached, the exchange rates won't be applied anymore and prices will be hidden for all the secondary currencies to prevent displaying outdated prices.
When recommendations are served, then exchange rates are dynamically applied to the product prices to reflect the active currency.
Once the tagging changed have been done and the API implemented, you need to configure and enable it from your admin panel under Settings > Other > Multi-Currency. Toggle the Use Multiple Currencies and Use Exchange Rates switches on and set the variation ID of the primary currency via the input field and toggle on the exchange rates switch.
Note: Ensure that the Variation ID of the primary currency matches the value sent via the
variation_id
element in the product tagging.
You will also need to configure the price formatting for your primary and secondary currencies.
Once you enabled multi-currency and made an API call, you can review the exchange rates received by Nosto by navigating to Settings > Other > Multi-currency.
You can also preview the product prices for different currencies by navigating to Tools > Products and choosing a product.
You will see one or more dropdowns that contain the prices and price calculation for the currency.
When you have reviewed your set-up, Nosto updates in real-time product prices for all the currencies and display the appropriate currency to the right target groups of users. You’re all set and ready to go live with our features.
Nosto Search uses product and user behavior data from the Nosto Platform, so if you are implementing Nosto Search, first of all, you need to implement Nosto Platform to your website.
Your search engine will be ready after the Nosto representative enables the Search module for your account. Then you will need to integrate Nosto Search to the website.
By using a pre-built template that can be customized to fully match a website's design using built-in code editor directly in https://my.nosto.com/. In the code editor, you can fully customize the pre-built template's JavaScript, HTML, and CSS code. Changes to the template can be implemented either by client’s developers or Nosto team. Frontend integration uses Preact and JSX templates and renders search results page dynamically in website’s frontend, so no additional integration is needed to the backend. When using Nosto services, no development is needed from the client.
API integration - a robust Search GraphQL API allows to implement Nosto Search into any website or app and gives complete flexibility for developers to build frontend and backend features.
For frontend integrations you can also use our JavaScript library. This library wraps the Search GraphQL API and provides its functionality in a programmatic way.
Can be implemented by Nosto team
Yes
No
No
Expected time to launch live
1-3 weeks*****
4-8 weeks
3-6 weeks
Headless compatible
Yes
Yes
Yes
Fully customizable frontend
Yes
Yes
Yes
Customized and managed only in Nosto dashboard
Yes
No
No
Suitable for complex use cases
Sometimes
Yes
Yes
* This estimation is based on the merchant's team building the templates. When Nosto's frontend team builds templates via the Code Editor, this can take longer due to overall bandwidth from the team.
If you are looking for a fast launch without much effort we recommend going with the fully customizable pre-built templates. This type of integration does not support full API access but comes complete with an out-of-the-box search result page and autocomplete templates that can easily be customized to match most website designs and integrate even advanced custom functionality.
If however you need full control over the search frontend or require complex custom functionality we recommend to go with the API or JavaScript integrations. These integrations do not provide out-of-the-box templates but provide direct access to the Search API, allowing you use the data in whatever way is required for your use cases.
Nosto also supports some advanced use-cases depending on how your store is currently built. You should first read through the following topics to have an understanding of how Nosto works before moving to the advanced use-cases:
The topics listed below extend the essential tagging with support for SKUs, Multi-currency and Customer group pricing.
The page-type tagging enables Nosto to trigger actions, such as showing popups, depending upon a page type. Tagging the page types is optional but without the page-type tagging, you will not be able to avail the use of page type based triggers.
Here is a list of all the valid page types:
The home page of your store should be tagged as front
.
All category pages should be tagged as category
.
All product pages should be tagged as product
.
The shopping cart page should be tagged as cart
.
The checkout page, where order information is filled, should be tagged as checkout
.
The order confirmation page should be tagged as order
.
The search results page should be tagged as search
.
All no-found pages should be tagged as notfound
.
Other pages should be tagged as other
.
Nosto Autocomplete library is designed to simplify the implementation of Search Autocomplete functionality by providing: 🌟 Autocomplete products, keywords and history visualization. 🔄 Automatic bindings to Nosto Search API. 🧩 Autocomplete component state management. 📊 Nosto Analytics out of the box, Google Analytics support. 🏗️ Default Autocomplete components and templates. 🎮 Keyboard navigation.
In this article, you will learn how to implement multi-variants in Nosto. When the implementation is complete, you will be able to display different products at different prices to different customer groups.
Note: You can only change the pricing and the availabilities using this feature.
Note: You cannot use SKUs with this feature at the time of writing.
You will need to implement the multi-variate tagging if you have any such scenarios:
Your store has different prices for B2B and B2C customers
Your store has different prices for logged-in and logged-out customers
Your store has different prices for loyalty customers
Your store has different prices and availabilities for different locations
Prior to the multi-variate implementation, ensure that the Nosto tagging is correctly in place. Some of the tagging must be slightly amended to support multi-variants.
The product page tagging must be amended to denote the primary variation code of the product.
For example, a retailer who has different prices for normal and loyal customers would have GENERAL
as the default variation id and LOYAL
as an extra variation.
An additional span tag must be placed within the product page tagging with a class name variation_id
. The tag is a child element of the nosto_product
element.
Note: The code in the
variation_id
element must remain static, regardless of the current context. For example, if a loyal customer is logged in, thevariation_id
field would stillGENERAL
and not change.
The cart and order tagging can be left as-is but the prices must be in the customer's currently active currency. For example, a customer shopping in Swiss Francs (CHF) should have all the cart items tagged in Swiss Francs (CHF). Failure to do so will result in incorrect prices in any triggered emails such as abandoned cart or order followup.
Once you have amended the product tagging, an additional DIV element must be added to all the other pages (including the product page itself). The tag should not be encapsulated in the nosto_product
DIV tag. The information sent in the tag refers to the segment of the customer.
For example, on the site of a retailer, who has different prices for normal (GENERAL) and loyal (LOYAL) customers, if the customer is a logged in customer and is a known loyalty customer, the nosto_variation
element should show LOYAL
. If the customer logs out or a new customer visits, and there is no way to identify him as a loyal customer, the nosto_variation
element should show GENERAL
.
Once the tagging changed have been done and the API implemented, you need to configure and enable it from your admin panel under Settings > Other > Multi-Currency. Toggle the Use Multiple Currencies switch on and Use Exchange Rates switch off and set the variation ID of the primary currency via the input field and toggle on the exchange rates switch.
Note: Ensure that the Variation ID of the primary currency matches the value sent via the
variation_id
element in the product tagging.Note: Multi-variants cannot be used in conjunction with exchange-rates based multi-currency feature. You must keep the Use Exchange Rates switch off.
You will also need to configure the price formatting for your primary and secondary currencies.
Once you enabled multi-variants you can preview the product prices for different groups by navigating to Tools > Products and choosing a product.
You will see one or more dropdowns that contain the prices and the availability for that group.
When you have reviewed your set-up, you’re all set and ready to go live with our features. Nosto will automatically handle the different customer groups across its feature set.
Category pages can be rendered using search templates over existing category pages.
To render the category page, provide additional configuration parameters to the init
function in the index.js
entry point file. Default configurations for categoryQuery
and isCategoryPage
are already provided. Custom configuration is necessary only if the default settings are not suitable for your application.
The default isCategoryPage
function checks for the presence of an element in the DOM and determines if the page should be considered a category page based on its content.
In the example above, we supply autocomplete query parameters as an object. Additionally, the categoryQuery
parameter can also be supplied as a function. The function flavor can be used for building complex query parameters and provides access to other pre-defined configuration parameters. Section below shows an example of categoryQuery
supplied as a function which provides the product variationId
by accessing the pre-defined categoryId
and categoryPath
methods from the default configuration.
If you want to integrate only Categories without Search or Autocomplete, ensure that the following entries are removed or commented out:
serpComponent
historyComponent
autocompleteComponent
Nosto will attempt to display the original category page products in case Nosto service is unavailable or can't be reached. In addition, the original products are made available for the SEO crawlers, improving the page's ranking in the search engines. To make it possible, it's recommended to hide the original category page products instead of removing or blocking them.
The best approach is to add ns-content-hidden
class name to the same element you are targeting with contentCssSelector
or categoryCssSelector
. This class name will be stripped away by Nosto automatically as soon as the script is initialized.
In addition, you should define CSS to hide the target element:
The isCategoryPage
function should detect whether the current page is a category page. Its result should not be cached, as it needs to dynamically detect the page type since it can change during the app's execution. For example, if the user navigates from a category page to a search page, the function should reflect that change in page type.
The categoryQuery
should generate a category page query based on the current page. It must return either categoryPath
(identical to the categories
field filter) or categoryId
to select the current category. The default implementation extracts the categoryId
and categoryPath
fields from the DOM.
The category component should also be implemented. In most cases, it is the same component as the search page component, except that the search query should not be displayed.
The category page shares a lot of similarities with the search page, so please refer to the search page documentation:
Search automatically tracks to Google Analytics & Nosto Analytics when using the SerpElement
component.
Not all of Nosto's functionality is available for pure GraphQL API integrations. The following features require Using the JavaScript Library:
Analytics
Segmentation
A/B testing
Debug toolbar
Both Search and Categories are built on the same technical foundation and use the same API and product data. For simplicity, we will just refer to Search API in the following documentation.
Use the Search API Playground to try out search queries and browse API reference.
It provides:
Search request schema - you can see field types and inspect what fields are needed for a search request.
Search result schema - you can see return field types with descriptions.
Send requests to the search engine and preview the response.
In the majority of cases, authentication is not a requirement for using search APIs. However in rare case may need to:
Access sensitive data- all sensitive data is restricted for public access (e.g. sorting by & returning sales).
Return all documents - public access require to specify search query, category ID or category path to avoid returning all documents.
Note: Keep your API key secret and do not expose it to the frontend!
Authorization
Bearer SEARCH_KEY
Authentication Token with API_SEARCH
Role is available on dashboard settings page
When integrating Search you have the option to directly access the API, or you can use our existing Search JavaScript library that provides most of the required functionality out of the box.
Search use different API endpoint than other Nosto queries: https://search.nosto.com/v1/graphql
All requests require an account ID, which can be found in the top-right corner of the Admin dashboard, under the shop name.
Replace YOUR_ACCOUNT_ID
with your account id retrieved from the Nosto dashboard.
Replace YOUR_ACCOUNT_ID
with your account id retrieved from the Nosto dashboard.
JS API includes full-featured search function with tracking support.
Replace YOUR_ACCOUNT_ID
with your account id retrieved from the Nosto dashboard.
Replace YOUR_ACCOUNT_ID
with your account id retrieved from the Nosto dashboard.
Upon a successful request, the API will return a 200 status code response, which includes the search data:
API returns a list of errors with explanations. These errors should be logged internally and not displayed to the end user. Instead, display a general message, such as Search is unavailable at the moment, please try again
. This approach ensures that no sensitive information is leaked to the end user.
The API may return some errors even when data is returned. This means that some parts of the response may be missing, but you should still display the available data instead of showing an error to the user. These errors should be logged internally for future reference and troubleshooting.
For features like personalised results and user segments to function effectively, the search function needs access to the user's session information from the front-end.
It's possible to get search session data using the JS API:
The results of this function should be passed to search query sessionParams parameter. In case search is called from backend, it should pass this data to backend (e.g. using form data).
It's also possible to save session data to cookies on page load:
In the search application, you should use variables instead of hardcoded arguments to pass search data. This means that filters, sort, size, and 'from' options should be passed in the 'products' variable. For a full list of available options, please see the reference.
To optimize search speed and reduce network load, select only the necessary data when performing a search query.
Variables should encompass all dynamic query data because it is the most efficient method to pass data, and data is automatically escaped to prevent injection attacks. Avoid generating dynamic queries, as they can lead to security issues if user input is not properly escaped.
To analyze user behavior you need to implement tracking. This can be achieved using our JavaScript library. You need to implement the following methods:
recordSearchSubmit to track search form submissions
To create a search application, call the init
function with your configuration. This will create a new Preact application that renders on the specified contentCssSelector
. It will also bind to the input element identified by the provided inputCssSelector
and execute a search upon form submission.
In the example above, we supply serp query parameters as an object. Additionally, the serpQuery
parameter can also be supplied as a function. The function flavor can be used for building complex query parameters and provides access to other pre-defined configuration parameters. Section below shows an example of serpQuery
supplied as a function which provides the product variation id by accessing the pre-defined variationId
method from the default configuration.
When serpPath
parameter is specified, the application will redirect to the specified search page after a search is conducted. Otherwise, the search will be rendered on the same page without changing the URL path.
When serpPathRedirect
parameter is set to true
, the application after search submission will redirect the page to the search page specified in serpPath
and fetch the page. Default behaviour will rewrite browser history only to the specified path, without fetching the page.
To prevent events from firing on an existing input, you need to provide the CSS selector of the form that the input is in to the initialization configuration. When optional fromCssSelector
is passed, it will unbind the form and the elements inside from existing events. Additionally, formUnbindDelay
in milliseconds as value can be passed to delay the unbinding functionality.
The search results page component should render a full search page using the provided app state. A minimal example might look like this:
When the compressUrlParameters
flag is set to true
, it automatically applies the URL parameter compression functions for filters, sort and pagination.
@nosto/preact
library has pre-built functions for changing search url format:
Product thumbnails and currency formatting are supported via decorators that augment the product data returned by the Nosto Search service.
The following example shows modifications to the init
call to make formatted price texts and product thumbnails available in the result data:
The thumbnailDecorator
takes a size argument and requires the following additional fields to be made available in the result set for accurate thumbnails:
imageHash
for imageUrl
thumbnails
thumbHash
for thumbUrl
thumbnails
alternateImageHashes
for alternateImageUrls
thumbnails
sku.imageHash
for sku.imageUrl
thumbnails
The supported sizes are
The priceDecorator
uses the currency formatting definitions of the Nosto account to format prices into priceText
and listPriceText
fields. The fields required for this mapping are
price
will be formatted to priceText
listPrice
will be formatted to listPriceText
priceCurrencyCode
will be used as the currency code
The same mapping will also be attempted for SKU level data
In addition to the compressUrlParameters
flag the serpUrlMapping
should be used to control the mapping from URL parameter keys to paths in the internal query object. The default looks like this:
The key is the internal path in the query model and the value is the query parameter name that should be used in the URL.
Range Slider
Utilize the useRangeSlider
hook to generate useful context for rendering range inputs. Additionally, employ the component to generate the interactive slider itself. These tools together facilitate the creation of dynamic and interactive range sliders for your application.
Range Selector
If you require an alternative method where values are selected through radio buttons rather than a slider, consider using useRangeSelector
hook. This tool allows users to choose from predefined range intervals with radio buttons, offering a different interaction style.
The range size parameter in the useRangeSelector
hook specifies the size of each interval in the range and determines the total number of range items displayed. Additionally, it automatically rounds the minimum value down to ensure intervals are aligned with the specified range size.
For example, if the minimum product price in the current catalog is 230, and the maximum product price is 1000, the range size of 200 will adjust the starting point to 200 and create intervals displayed under the "Price" filter as follows:
200 - 400
400 - 600
600 - 800
800 - 1000
You can use the toggleProductFilter
function to toggle any filter value. This function will either add the filter value if it's not already applied or remove it if it's currently active, thus providing an efficient way to manipulate product filters in your application.
Use the usePagination
hook to generate useful context for rendering any desired pagination. Utilize the width parameter to adjust how many page options should be visible. Also, remember to scroll to the top on each page change to ensure a seamless navigation experience for users.
Nosto search-templates library provides a simple out-of-the-box solution to implement infinite scroll functionality. Simply wrapping your product rendering with the <InfiniteScroll>
component is generally enough.
As the user scrolls the page down, the wrapper will detect it using the IntersectionObserver
. If it is not supported by the user's browser, a 'load more' button will be shown instead.
When using infinite scroll, consider enabling persistent search cache as well. When this feature is enabled, the latest search API response will be automatically cached and stored in the browser's session storage.
This improves the user experience significantly when the user navigates from a product details page back into the search results using the browser's 'back' function. The data necessary to display the products is already available, and the user will see the products immediately, without waiting for them to load again.
This feature is useful for both paginated and infinite scroll, but the benefits are significantly more visible with the latter.
Since the code editor utilizes the Preact framework, it offers significant flexibility in customizing behavior or integrating the search page with existing elements on your site. For instance, you can implement actions such as 'Add to Cart', 'Wishlist', or 'Quick View'.
Nosto will attempt to display the original search results in case Nosto service is unavailable or can't be reached. In addition, the original products are made available for the SEO crawlers, improving the page's ranking in the search engines. To make it possible, it's recommended to hide the original search results instead of removing or blocking them.
The best approach is to add ns-content-hidden
class name to the same element you are targeting with contentCssSelector
or categoryCssSelector
. This class name will be stripped away by Nosto automatically as soon as the script is initialized.
In addition, you should define CSS to hide the target element:
Search automatically tracks to Google Analytics & Nosto Analytics when using SerpElement
component.
Component parameters:
The SerpElement
component supports any other HTML attribute, e.g. class.
The search page incorporates built-in fallback functionality, allowing users to customize the behavior in case the search service encounters issues. To activate this feature, modify the initialization configuration to include the fallback: true
key-value pair.
To enable fallback functionality, include the following code in the initialization configuration:
Once fallback is enabled, if the search request fails to retrieve data, the search functionality will be temporarily disabled for 10 minutes, and the original content Nosto has overridden will be restored.
The fallback: true
setting only works out of the box if the path is the same for both the dedicated Nosto search page and the native search page, as well as for category pages.
If the behaviour described above is undesirable, the configuration supports an alternative option. Fallback mode can be set to fallback: 'legacy'
, in which case the user will see a page reload if the search request fails. After that, Nosto will not attempt to override the original search results or category pages for 10 minutes.
This behaviour has been the default fallback behaviour before August 20, 2024.
Additionally, it's possible to customize the location to which users are redirected when the search functionality is unavailable. This customization involves specifying functions for both the search engine results page (SERP) and category pages.
To redirect users to a specific location when the search engine is down, define a function for serpFallback
. This function accepts one parameter containing information about the current search query, including the query itself.
Similarly, for category pages, define a function for categoryFallback
. This function also accepts one parameter containing information about the current query, including the category ID or Path.
By customizing these fallback locations, you can enhance the user experience by providing them with alternative navigation options if the search functionality is temporarily unavailable.
Nosto Search engine is relevant out of the box and search API can be used without any initial setup. Nosto Dashboard can be used to further tune search engine configuration:
Autocomplete is an element shown under search input used to display keywords and products for a partial query.
Check out .
To enable autocomplete, additional configuration should be passed to init
function.
In the example above, we supply autocomplete query parameters as an object. Additionally, the autocompleteQuery
parameter can also be supplied as a function. The function flavor can be used for building complex query parameters and provides access to other pre-defined configuration parameters. Section below shows an example of autocompleteQuery
supplied as a function which provides the product variation id by accessing the pre-defined variationId
method from the default configuration.
When the autocomplete component is injected, by default it will become the next sibling of the input field. It is possible to override that behaviour by specifying the dropdownCssSelector
value. If this selector is specified, the dropdown will be injected as the last child of the specified element.
It can also be set to be the first child of the element by using the object selector syntax.
Wrap each keywords and product to AutocompleteElement
element - it will allow clicking or selecting the element directly with keyboard.
To submit a search directly from the autocomplete, use the <button type="submit">
element. This will submit the search form.
History component renders user search history. It is displayed when user clicks on empty search box.
HistoryElement
renders clickable element that triggers search event with provided query.
Autocomplete automatically tracks to Google Analytics & Nosto Analytics when using <AutocompleteElement />
component.
Search Templates allow you to add a search function to your website quickly and easily without the need to use an API. You can customize the design of your search pages and autocomplete boxes to match your brand's look and feel. This saves you a lot of time compared to implementing search functionality through an API.
To get started with Search Templates on your website, navigate to the Search tab under 'On-site' within the Nosto UI. This is where everything for Search can be configured and controlled, including designing the templates for search pages and autocomplete dropdowns, as well as search analytics, query rules and other settings. Synonyms for search queries can also be configured here.
To begin implementing Search, navigate to the Templates tab under Search, and Click on “Open Code Editor”.
You will then be redirected to the Code Editor window, where you can see and edit all project files.
Project structure has the following requirements:
index.js
- this is application entry point that is used when building project. When building project it will recursively scan this file for imports.
build/
- this directory stores build output that will be used when deploying project.
After saving changes (CTRL + S
) build should be triggered and bundled code should be uploaded to CDN. You can preview final result on your website and deploy it when ready.
Additionally, please refer to for further useful information!
Due to performance optimization, the search function will calculate the total count up to 10,000. In this case the search page should display a count of 10,000+
to indicate that more than 10,000 products were found.
Filters and sorting operations are executed on all found products, even if there are more than this limit. Therefore, it's still possible to find other products if you filter or sort them. This should not affect the user experience in any way because it's unlikely that someone would actually view more than 10,000 products with a single search.
As soon as you use the results delivered by Nosto API, you will see that the listings in categories have a different order than listings delivered by your native shop-system, even if you didn't set up any merchandising rules. The products are mainly delivered as indexed during the data sync, but there is no defined behaviour for this. We recommend to always set up at least one global rule before going live with Nosto category merchandising to create product listings matching your business strategies.
For client-side/frontend integrations, Nosto's JavaScript library can be used to simplify the integration. It provides a programming interface to access the Search & Categories API.
For the most basic search the fields
parameter should be provided to specify what product/keyword fields should be returned. Both products
and keywords
can be used separately and together, depending on the use case. For all parameters, see the .
The api.search
function also accepts the following options:
The function automatically loads session parameters required for personalization & segments in the background.
In order to request custom fields, add the entries "customFields.key"
and "customFields.value"
to the requested product fields. This changes the example above like this
For a search page in most cases the facets
parameter should be provided.
Also redirect
& track
should be enabled to automatically track searches to Nosto analytics & redirect if API returns a redirect request.
isKeyword
should be set to true
if search is submitted by clicking a keyword, suggested in the autocomplete.
track
should be enabled to automatically track searches to Nosto analytics.
Furthermore redirect
& track
should be enabled to automatically track searches to Nosto analytics & redirect if API returns a redirect request.
For some of the search features to work properly, such as personalised results and segments, the search function needs to be able to access information about the user's session from the front-end.
The search function of the JS API already includes session state automatically.
To get all session data the following snippet can be used:
The function accepts the following options:
Tracking search events to analytics can be divided into three parts: search
, search submit
, search product click
. These are user behaviours that should be tracked:
search submit (type = serp
)
faceting, paginating, sorting (type = serp
) or (type = category
)
autocomplete input (type = autocomplete
)
search results product click (type = serp
), (type = autocomplete
) or (type = category
)
autocomplete keyword click (type = autocomplete
)
category merchandising results (type = category
)
JS API library provides tracking helpers for all of these cases.
User actions that lead to search results should be tracked with api.recordSearch()
after search request is done:
search submit (type = serp
) - user submits search query in autocomplete component and is landed to SERP
faceting, paginating, sorting (type = serp
) or (type = category
) - user adjusts current search results by filtering (e.g. brand), selecting search page, sorting results
autocomplete input (type = autocomplete
) - user sees partial results while typing in search input
category merchandising results (type = category
) - user sees specific category results when category is selected (category merchandising must be implemented)
You don't need to execute api.recordSearch()
if you call api.search(query, { track: 'serp'|'autocomplete'|'category'})
function from JS API, becauseapi.search()
already calls api.recordSearch()
when track
option is provided.
Example:
Example:
Example:
Search queries are categorised into two groups: organic and non-organic searches.
In order to mark a search query as an organic search you need to call api.recordSearchSubmit(query: string)
. You should call it on search input submit only, before search request is sent.
Organic search - is a search query submitted through search input and which lead to SERP (search engine results page). Following faceting, paginating, sorting queries on organic query is also counted as organic.
Product clicks should be tracked in autocomplete component, SERP, category page with api.recordSearchClick()
by providing component (type), where click occurred, and clicked product data:
Example:
When tracking events, adherence to the following criteria is essential for capturing detailed and valid data:
query
parameter:
The query
string is an essential component for event tracking.
If present, include products.sort
to track sorting behavior.
If applicable, incorporate products.filter
.
searchResults
parameter:
products.hits
array containing objects with a productId
is mandatory.
products.total
number to identify if the search has results.
For accurate pagination tracking, products.from
and product.size
must be included.
For identifying if the request was autocorrected include products.fuzzy
.
For category requests, either products.categoryId
or products.categoryPath
is mandatory.
Bear in mind that search queries are split between organic and non-organic searches. To classify a search as organic, it is crucial to invoke api.recordSearchSubmit()
upon the search input submission, before the actual search request is dispatched. This step is pivotal in ensuring the seamless tracking of organic searches through to the SERP.
Tracking product clicks is fundamental for understanding user interaction. Use api.recordSearchClick()
to monitor this actions correctly, specifying the type
and relevant hit data.
For a basic search, it’s enough to provide accountId
, query,
and select fields that should be returned. You can control which product attributes to select through products.hits
field. See .
For example, if you want to return only productId
and name
, the query would be:
Products offset parameter from
is used for pagination functionality.
The default count of documents returned per page is size = 5
, you can change it with products.size
, and offset of products is controlled with products.from
field:
By default results are sorted by products relevance score.
To change the sorting, use the sort parameter, where you would specify any indexed field which should be sorted by, and order: asc
for ascending and desc
for descending.
By default, you should always sort by relevance. Only if the user selects a different sort method, a sorting rule should be used.
Facets help the user to find products more easily. Faceted navigation is normally found in the sidebar of a website and contains filters only relevant to the current search query. Facets are configured in the Nosto dashboard.
One of the facet types is type = terms
. It returns list if common terms from found documents.
Assume that we have configured facets for customFields.brandname
and categories:
Stats facet returns minimum and maximum number field value from found documents. The most common usage is to render slider filter (e.g. price)/
Filtering by terms
facet, for example by Adidas, Converse brands:
When filtering by multiple same field items, filters will be joined with OR operator and different fields with AND.
If you wish to have more facets, you should configure it in the Nosto dashboard first.
Filtering by stats
field, for example by price:
You can sort using these arguments: lt
(less than), gt
(greater than), lte
(less than or equal to), gte
(greater than or equal to).
Redirects can be used to forward users to special pages depending on their search keywords. For example, users searching for shipping
could be forwarded to https://example.com/shipping.html.
For API integrations GraphQL can only return the target URL. The actual browser redirect must be implemented by the merchant.
For features like personalised results and user segments to function effectively, the search function needs access to the user's session information from the front-end.
Nosto Search engine is relevant out of the box and search API can be used without any initial setup. Nosto Dashboard can be used to further tune search engine configuration:
Nosto provides functionality to retrieve all products for a specific category. This is useful when you want to implement category merchandising using the same API as for Search.
Using the category ID is only fully supported for Shopify merchants. Others should use the category path instead to benefit from full functionality.
Provide the API parameter to fetch all products associated with that category. Additionally should be provided for better analytics data.
Depending on your configuration, fetching a parent category will also include products from the child categories. For example, fetching products for the category Pants
would also include products from the categories Pants -> Shorts
and Pants -> Khakis
.
This is an admin-only setting. Please contact your Nosto representative to adjust this setting.
The category page shares a lot of similarities with the search page, so please refer to the search page documentation:
Autocomplete provides keyword suggestions to assist users in completing their queries, supplemented by a selection of the most relevant products with the ability to see all products on the search results page.
Check out .
When integrating Autocomplete you have the option to directly access the API, or you can use our existing that provides most of the required functionality out of the box.
API can return highlights indicating which parts of a keyword match the search query. This HTML can be used to render and emphasize the matching sections during display.
API only returns redirect url, the actual browser redirect must be implemented by the merchant on keyword selection
Each autocomplete product click should be tracked as a search page virtual view to ensure that the Google Analytics search feature displays the correct conversion rate. For example, if you click any product when the typed query is phone
it should track a virtual page view with the URL /search?q=phone
(adjust the search path and query parameter to match your search page).
Since a product link click would redirect to a new page, to ensure that Google Analytics has time to send the tracking request, it's recommended to save the search query to local storage and track it on page load.
The full list of Configuration options is documented
The returns the minimum and maximum values of numerical fields from search results. This functionality is especially useful when creating interactive elements such as sliders and range selectors. For instance, a price slider can use these min-max values to define its adjustable range, providing a simple way for users to filter products within a specific price range. Similarly, these values are utilized in the RangeSelector to define the overall scope of range selections, allowing for the configuration of selection precision through the range size parameter.
The returns field terms for all products found in the search. This feature analyzes the content of each product and extracts meaningful terms. These terms can then be used to filter or refine search results, providing users with a more accurate and targeted product search.
If the paths differ, you must configure the serpFallback
or categoryFallback
function to ensure proper redirection. See:
- manage which fields are used for search and their priorities,
- create facets (filtering options) for search results page,
Ranking and Personalization - manage how results are ranked,
Synonyms, Redirects, and other search features are also managed through Nosto Dashboard ().
The full list of Configuration options is documented
Search Templates ship with a library called @nosto/preact
that contains functionality to interact with the Nosto Search product. API documentation for the library is available
For category pages in most cases the facets
parameter should be provided. Additionally (for Shopify) and should be also provided.
The results of this function should be passed to search query parameter. In case search is called from backend, it should pass this data to backend (e.g. using ).
On errors from api.search
calls the error object contains a status field that has the HTTP response status which can be used to determine the cause of the error in addition to the error message. The ranges of the status codes used for errors are 400-499 and 500-599. For details on these error codes, go to
The tracking metadata is primarily taken from the third parameter. The and objects must be provided in the api.recordSearch
call instead of partials.
Tip: In case of API integration, use this example GraphQL partial query to integrate with the API and retrieve the necessary response data for precise event tracking.
See all .
To use facet for a specific field you need to first.
It's possible to get search session data using the :
The results of this function should be passed to search query parameter. In case search is called from backend, it should pass this data to backend (e.g. using ).
To analyze user behavior you need to implement tracking. This can be achieved using our . You need to implement the following methods with type = serp
:
to track search result interactions like filtering and pagination
to track result clicks
- manage which fields are used for search and their priorities,
- create facets (filtering options) for search results page,
Ranking and Personalization - manage how results are ranked,
Synonyms, Redirects, and other search features are also managed through Nosto Dashboard ().
Product fields that can be requested in the hits
object are documented . All indexed fields are accessible via the API.
Provide the API parameter to fetch all products associated with that category. This parameter is the same as the categories
product field.
Product fields that can be requested in the hits
object are documented . All indexed fields are accessible via the API.
In some rare cases or is not enough. In these cases can be used to build any query for category & landing pages.
To analyze user behavior you need to implement tracking. This can be achieved using our . You need to implement the following methods with type = category
:
to track category page visits
to track clicks on category results
Redirects are configured in the search dashboard and can be used to forward users to specific pages depending on what they type into the search field. For example, users searching for "shipping" could be directed to .
To analyze user behavior you need to implement tracking. This can be achieved using our . You need to implement the following methods with type = autocomplete
:
to track users typing in the search field and viewing suggestions
to track clicks on autocomplete suggestions
Additionally, see the .
Pagination
Replaces from
parameter with page number.
Before:
/search?products.from=20&q=shorts
After:
/search?page=2&q=shorts
Sorting
Returns shorter sort
parameters.
Before:
/search?q=shorts&products.sort.0.field=price&products.sort.0.order=desc
After:
/search?q=shorts&products.sort=price~desc
Filtering
Compresses filter
parameters. Multiple filter
values are separated by a comma, which is encoded. This is because filter
values can contain non-alphanumeric letters themselves.
Before:
/search?q=shorts&products.filter.0.field=customFields.producttype&products.filter.0.value.0=Shorts&products.filter.0.value.1=Swim&products.filter.1.field=price&products.filter.1.range.0.gte=10&products.filter.1.range.0.lte=30
After:
/search?q=shorts&filter.customFields.producttype=Shorts%7C%7CSwim&filter.price=10~30
1
170x170 px
2
100x100 px
3
90x70 px
4
50x50 px
5
30x30 px
6
100x140 px
7
200x200 px
8
400x400 px
9
750x750 px
10
Original (Square)
11
200x200 px (Square)
12
400x400 px (Square)
13
750x750 px (Square)
hit
Product object.
as
Element to render <SerpElement />
as. Recommended to use as="a".
If a element is used, href attribute is added automatically.
onClick (optional)
Additional onClick callback (tracking callback is already implemented in the component).
maxWait
2000
Maximum execution time in MS
cacheRefreshInterval
60000
Maximum cache time
type
Search type: serp
, autocomplete
, category
request
result
options (optional)
Record search options. Currently is accepts:
isKeyword: boolean
- should be set when keyword in autocomplete is clicked (search is submitted via keyword)
type
Search type: serp
, autocomplete
, category
hit
Object containing productId
and url
, collected from clicked product
accountId
Nosto account ID
query
search query text
id
internal facet ID, used to select specific facets in query
field
facet field, should be used for filtering
type
facet type, in this case terms
name
user friendly facet name configured in the dashboard
data.value
original facet value, it should be displayed in the user interface
data.count
shows how many products will be returned if you select this facet, it should be displayed in the user interface
data.selected
indicates if there is an active filter on this value
name
user friendly facet name configured in the dashboard
terms
facet type, in this case stats
field
facet field, should be used for filtering
id
internal facet ID, used to select specific facets in query
min
minimum field value for documents that match provided query
max
maximum field value for documents that match provided query
redirect
false
Automatically redirect if search returns a redirect
track
null
Track search query by provided type
You can install the Nosto Autocomplete
library via npm:
The Nosto Autocomplete library can be imported and used in various ways, depending on your preferred framework or template language. Some of the supported import methods include:
Base
import { autocomplete } from "@nosto/autocomplete"
Mustache
import { autocomplete, fromMustacheTemplate, defaultMustacheTemplate } from "@nosto/autocomplete/mustache"
Liquid
import { autocomplete, fromLiquidTemplate, defaultLiquidTemplate } from "@nosto/autocomplete/liquid"
Preact
import { autocomplete, Autocomplete } from "@nosto/autocomplete/preact"
React
import { autocomplete, Autocomplete } from "@nosto/autocomplete/react"
Choose the import method that aligns with your project's requirements and technology stack.
❗Do not combine multiple imports as it will fetch multiple bundles.❗
The library handles events through dataset
properties to avoid handling logic in a template. These data-*
attributes are used:
data-ns-hit
- this attribute should be used on clickable keyword
, product
, history
list elements. Stringified unmodified JSON object (product, keyword or history hit) from the search response should be provided as a value. You will need to escape it in Liquid and Mustache templates.
This attribute handles submit keyword/history as search, redirect to product, analytics (if enabled) request.
data-ns-remove-history
- should be used to delete history entries in the autocomplete.
To make an element delete a single history entry when clicked, add data-ns-remove-history={hit.item}
to an element.
To delete all history entries, add data-ns-remove-history="all"
to clear button.
Template examples: Mustache, Liquid, React/Preact
Mustache is based on logic-less templates which can be enhanced with helpers, e.g toJson
, imagePlaceholder
, showListPrice
in example template.
After installation, you can import and use the library in your JavaScript or TypeScript files. Library attaches to existing search input element. Once a search input is loaded, autocomplete
function can initialize event listeners for the Search Autocomplete.
❗autocomplete
should be called once.❗
inputSelector
Yes
N/A
Input element to attach the autocomplete to
dropdownSelector
Yes
N/A
Dropdown element to attach the autocomplete to (empty container's selector should be provided)
render
Yes
N/A
Function to render the dropdown
fetch
Yes
N/A
Function to fetch the search state
submit
No
Search API request
Function to submit the search
minQueryLength
No
2
Minimum length of the query before searching (applied on typing in autocomplete and used in default submit
implementation)
historyEnabled
No
true
Enables search history component
historySize
No
5
Max number of history items to show
nostoAnalytics
No
true
Enable Nosto Analytics
googleAnalytics
No
{ serpPath: "search", queryParamName: "query", enabled: true }
Google Analytics configuration. Set to false
to disable
hitDecorators
No
N/A
Decorate each search hit before rendering
When submitting Search results through Autocomplete, submit
callback is called on these events:
Enter
key press.
Submit button
click.
Keyword
click.
By default submit
checks if query/keyword length satisfies minQueryLength
, sends Search Submit event
to Nosto Analytics, and sends Search request to the Nosto Search API.
In the usual scenario, you want to render Search Results on submit, so you should override submit
function:
To disable submit
pass undefined
value.
\
Setting nostoAnalytics: true
will enable Nosto Analytics tracking. Tracking results can be seen in the Nosto Dashboard under Search & Categories -> Analytics page.
❗Note: you should additionally add click events on your search results page according to Nosto Tech Docs with type: serp || category
according to the results page type.❗
\
By default we send pageview
events to existing GA tag, found in shop site. To send pageview
events with correct search information, a minimal configuration is needed in googleAnalytics
property.
serpPath
- Search query url parameter name
queryParamName
- Search query url parameter name
enabled
- Enable Google Analytics
For example, if search results URL is https://examplenostoshop.com/search-results?query=shoes, then configuration should be:
To disable Google Analytics, set googleAnalytics: false
.
Once the autocomplete component binds to input via inputSelector
and dropdownSelector
, it then renders autocomplete provided in a render
function. It is called on input focus and change events, and renders a dropdown element with the current search result state:
if input is empty and history entries exist, it renders dropdown with history list,
if input is not empty and it passes minQueryLength
rule, it render dropdown with keywords and products.
Render can be adjusted to the desired framework. Moreover, the library provides helpers for Mustache/Liquid template languages.
Examples
Suppose index.html
is
List of autocomplete
initialization examples:
Liquid
Example below uses fromLiquidTemplate
helper which renders string template. Library provides default autocomplete template via defaultLiquidTemplate
and default css for default template:
The template also can be loaded from a file. The library includes a default template, equivalent to string template in above example:
Mustache Mustache template is rendered similarly as Liquid template in the above example:
Or from a file:
React/Preact
One way to initialize autocomplete in a React app, is to call autocomplete
from the useEffect
on component mount, using default <Autocomplete />
component and styles:
The Preact solution does not differ from React a lot:
See library TypeDoc page to see more detailed documentation of the library.
With the Nosto debug toolbar, you can see all the changes made to your website right away. To enable this feature, simply turn on the preview mode. After saving any changes in the code editor, you will be able to see them directly on your website.
Navigate to your website
In the URL, append ?nostodebug=true
to enable the debug toolbar
The Nosto debug toolbar should open up, where you will be asked to log in
Once you have logged in, enable the Preview toggle button at the bottom
You should now be able to view your changes live, via the Search box
Before each deployment search should be manually tested to ensure that everything works correctly.
Autocomplete returns results
Search displays results, facets with counts
You can select multiple facets (on the same field and different fields)
Sorting is working
Pagination is working
Test both mobile & desktop view using Chrome device simulation.
When you finished working on search implementation & carefully tested everything using Nosto debug toolbar, it's time to deploy everything.
Navigate to the Nosto Admin UI
> Search
> Templates
Click on Deploy latest and launch live
It can take up to 15 minutes for deployment to be visible
If the most recent update doesn't work properly, you have the option to revert to any previous update. Reverting won't alter the source, which means you can deploy the latest changes again simply by clicking on the main deployment button.
Navigate to the Nosto Admin UI
> Search
> Templates
Click on the desired deployment, click on ...
and then on Redeploy
If your latest update doesn't work and you don't have a previous working version to go back to, or if you want to completely remove the search function, you can turn off the search templates for a temporary period.
Reverting won't alter the source, which means you can deploy the latest changes again simply by clicking on the main deployment button.
Navigate to the Nosto Admin UI
> Search
> Templates
Click on the Disable Templates
button.
The GraphQL endpoints provide functionality to make it easier to test against a real account.
Every operation made against the GraphQL endpoints cause your website's data to be mutated. When doing performance testing or an equivalent, it is often necessary to exclude test traffic so as to not pollute your live account.
Using the header X-Nosto-Ignore: True
will cause any traffic from being recorded. Queries and Mutations will work normally but any API calls containing this header will not be archived or accrue towards the statistics.
An example of how this header can be leveraged can be found on our Nosto's GraphQL Android Example app.
Every operation made against our GraphQL endpoint returns a unique request identifier contained in an X-Request-Id
response header.
While we ensure that the APIs are as robust as possible if you do encounter an HTTP 5XX response from the endpoint, simply log the request identifier along with the error as the unique request identifier allows our engineers to troubleshoot the issue swiftly.
GraphQL is a query language for APIs. What does this mean for you? Unlike regular SOAP or REST APIs, GraphQL gives you the ultimate flexibility in being able to specify in your API requests specifically what data you need and get back exactly that.
As a query language, it provides you with a lot of flexibility that most normal APIs will not. Without needing to recreate endpoints, you can provide developers with the same functionality as a bulk endpoint. Your queries will be cleaner and easier to understand by combining multiple queries into one request.
The regular API is very well structured and specifically defined. The endpoints have their set requests and responses and that’s what you get whether or not that matches your usage pattern. GraphQL lets you control all of this so that the way you consume the data matches exactly what you need.
This is both a pro and a con. If your use case does not require all of the data, GraphQL can speed up your requests as we do less work on the server-side to fulfill those requests. Conversely, if you need all of the data in one request, your requests could slow down as we do more work to fulfill these requests.
If you would like to access our intelligence engine, you must use GraphQL. The legacy REST APIs are primarily used for sending orders, products and exchange rates.
Geo Segments:
Geo segments rely on the ability to determine the geographical location of the end customer. This typically requires a client-side script that can access the user's IP address. In case of a GraphQL only implementation, this should still be possible if the GraphQL calls are made directly from the end user to Nosto. If the calls are being proxied to a backend server and subsequently forwarded to Nosto, this will essentially hide the end-user's IP from the request and instead, send the backend server IP to Nosto, making it impossible to determine the geolocation of the end user.
The mutation methods allow you to change the session on Nosto's end and request personalized recommendations. Each mutation operation allows you to update the cart and customer information, all while giving you access to recommendations for the sessions.
Any mobile experience built atop Nosto's GraphQL API should use the mutation operation as it feeds data into to the recommender systems while providing personalization data.
_The given example updates the customer's information and his current shopping cart contents sends an event that the customer is currently viewing product number 400 and requests the personalized recommendations associated with a given product for him aliased as front_page_1
.
In order to use the GraphQL endpoints, you'll need to authenticate yourself. You will need a Apps token to access this endpoint. Only a subset of the endpoints can be accessed with a public token. This makes it possible to access functionality like querying product recommendations in an environment where it's not possible to protect the token, for example in a web browser. Each publicly accessible endpoint is denoted in the embedded documentation inside the playground.
Note: Nosto does not rate-limit the API usage but follows a fair-use policy. Nosto reserves the right to revoke API access for any abusive API usage patterns.
You can send your GraphQL requests as JSON to our API and have it correctly interpolate variables passed into it. To do so, set the Content-Type
header to application/json
.
Basic
API_APPS
POST
https://api.nosto.com/v1/graphql
If you want to send raw GraphQL queries to the API, you can still do so but you must set the Content-Type
header to application/graphql
.
Note: If you do not set the correct Content-Type header, the request will be interpreted as JSON and will fail.
Basic
API_APPS
POST
https://api.nosto.com/v1/graphql
You can use the browser's fetch API to request data from GraphQL. You will need to authenticate yourself and set the appropriate content-type headers.
You can send your GraphQL requests as JSON to our API and have it correctly interpolate variables passed into it. To do so, set the Content-Type
header to application/json
.
If you want to send raw GraphQL queries to the API, you can still do so but you must set the Content-Type
header to application/graphql
.
**NOTE:**If you do not set the correct Content-Type header, the request will be interpreted as JSON and will fail.
Mutations can be used to update the product catalog in Nosto. The updateProducts
mutation allows you to update one or more products at a go.
Any validation errors in the product data are accessible in the response. The entire product object is accessible in the response too. In the event that a product validation error led to the product to not be updated, the response would contain the errors as well as the invalid product data.
The given example updates the product #101 and requests the details of the updated products and any associated errors.
The given example updates the price of #101 and requests the details of the updated products and any associated errors.
If you would like to update the order-status for a given order, you can do so using the following request.
Mutations can be used to update the category listing in Nosto. The upsertCategories
mutation allows you to update one or more category at one go. If the category doesn't already exist, a new one is created.
A category can have the following fields:
id
The category identifier. If a category with this id doesn't already exist, a new one is created.
name
The displayed name for the category.
urlPath
The path that can be used to generate the URL of the category listing.
available
If the category is visible on the store. This can be set to false to soft delete the category in an upsert.
Some stores support hierarchical categories i.e. a category may have parent and child categories. The following fields can be used for hierarchical categories:
parentId
The identifier of the parent category.
fullName
The name of every category in the hierarchy.
When a new user comes to the app, you can use this method to get a new session. It will return you a customer-id that can save on the device and use for future requests. This would be ideal.
When a customer logs in, you can update the existing customer with the customer-reference. This would merge the online and mobile sessions. If not needed, I would omit this for now.
In order to use the GraphQL session mutation to fetch recommendations for your search page, the event, in this case, must be VIEWED_PRODUCT
and you should specify the product-identifier of the current product being viewed.
In order to use the GraphQL session mutation to fetch recommendations for your category page, the event, in this case, must be VIEWED_CATEGORY
and you should specify a fully qualified category path of the current category. For example, if you have a category called "Dresses" under the category "Women", the FQCN would be "/Women/Dresses".
In order to use the GraphQL session mutation to fetch recommendations for your search page, the event, in this case, must be SEARCHED_FOR
and you should specify the search term of the query.
In order to use the GraphQL session mutation to fetch recommendations for your cart or checkout page, the event, in this case, must be VIEWED_PAGE
and you should specify a fully qualified URL of the page as the target.
In order to use the GraphQL session mutation to fetch recommendations for your home or front page, the event, in this case, must be VIEWED_PAGE
and you should specify a fully qualified URL of the page as the target
Recommendation results can be attributed to events by setting a session event's ref
to the recommendation result's resultId
.
Here is an example of some recommendations for a front page. You can see recommendation result's resultId
is "frontpage-nosto-1"
.
If a customer selects to view the Cool Kicks product, you can generate the following request. Note that the event's ref
is set to "frontpage-nosto-1"
.
When making GraphQL queries from mobile applications, it's essential to define the user agent string in your HTTP headers. Ideally, the user agent should represent the mobile environment, including details such as the platform, device type, and application version. Avoid using terms like "bot" in the user agent string, as this might lead to unintended behavior or rejection of the query/session. Sending an empty user agent will also lead to be catch by the bot detection mechanism.
When a user places an order onsite or offsite, you must send the conversion tracking information to Nosto.
Tracking orders by customer id looks like the following:
To fetch the recommendations for the order-confirmation page, simply use the GraphQL field called forOrderPage
to fetch all the recommendations for the order-confirmation page.
Mutations can be used to update the email identities in Nosto. An "identity" is the personal information associated with an email address.
The upsertIdentity
mutation allows you to upsert the details of an identity. The given example updates the customer attributes for the email john.doe@nosto.com and requests the details of all the attributes of the identity.
If the identity for john.doe@nosto.com does not exist, a new identity will be created.
Note: If a specified attribute already exists on that identity, it will be overwritten.
There is currently no way to delete an identity.
Step by step guide for checking that our client script is tracking events on your site.
Navigate to your site in incognito mode.
Load the debug toolbar by appending nostodebug=true
to your store's URL e.g. https://example.com?nostodebug=true
Click the login link and navigate to the session view.
Navigate to a category page and verify that the View Category event is tracked with the following details:
Target matches the viewed category.
If the category doesn't appear in the session, these pages might help
Navigate to a product page and verify that the View Product event is tracked with the following details:
Target matches the viewed product ID.
If the product doesn't appear in the session, these pages might help:
Click on a product recommendation and verify that the View Product event is tracked with the following details:
Target matches the viewed product ID.
Ref matches the previously viewed recommendation slot ID.
If the product id and recommendation slot id don't appear in the session, these pages might help:
Add the product to cart and verify that the cart’s contents are correct. Ensure that the product details in the cart match the product that was previously viewed.
Product ID
Price & Currency
Quantity
If the cart doesn't correctly show in the session view, these pages might help:
Purchase the product and verify that the Buy Product event is tracked with the following details:
Ref matches the recommendation slot id
Target matches the product id
Wait 30 minutes for the session to expire and then verify that the order shows up in the orders page of the Nosto admin UI.
If the order doesn't correctly show in the session view, these pages might help:
If it’s not possible to perform a test order, the Nosto admin UI's orders page can be used to review that orders link to known products in the catalogue and that some items have click attribution towards the visible recommendations.
We’ve integrated with the User Timing API to be able to show some performance measurements of our client script. The supported measurements are:
nosto.get_dynamic_placements
Parse the DOM and find placements on the page. Performed before a recommendations request is sent.
nosto.load_recommendations
Send the recommendations request and handle the recommendation result. This encompasses measuring the recommendations request and nosto.inject_campaigns
.
nosto.inject_campaigns
Inject both dynamic and static campaigns into the DOM. This encompasses both nosto.inject_static_campaigns
and nosto.inject_dynamic_campaigns
.
nosto.inject_static_campaigns
Inject static campaigns into the DOM.
nosto.inject_dynamic_campaigns
Inject dynamic campaigns into the DOM.
nosto.evaluate_js
Extract and evaluate embedded JavaScript from recommendation templates.
Chrome's lighthouse tool can be opened by doing the following:
Right click and select Inspect.
Navigate to the Lighthouse tab.
Ensure the Performance category is enabled.
Click Generate Report
Once the report is generated, you can expand the “User Timing marks and measures” section under the Diagnostics section to see some basic information like how long after the page started to load the measurements start and how long each measurement took.
You can scroll back up and click the View Original Trace button to view a timeline of the measurements. You may need to expand the Timings section to view the client script’s recorded measurements. You can zoom in an out of this graph and swipe side to side to get a better view of things.
Start exploring Nosto's GraphQL API on your account. GraphiQL is an in-browser IDE for exploring GraphQL. You don't need any access for using the GraphiQL Explorer.
Toy around, use the API and when you'd like API access to the endpoint for use through a library such as Apollo, please contact support.
Use the embedded GraphiQL explorer below to run queries. The GraphiQL Explorer is accessible at https://my.nosto.com/\[account-id]/graphql
(please add your account ID).
Documentation is a first-class citizen of GraphQL, and GraphiQL leverages it. The right-hand pane exists for you to explore the possible queries, mutations, fields, their types (if they’re required), the works. Even if your server doesn’t implement human-composed descriptions, you will always be able to explore the graph of possibilities.
You don’t even have to read the documentation to discover our API. GraphiQL supports debugging as-you-type, giving hints and pointing out errors.
GraphiQL comes with a JSON viewer with all the niceties you’d expect: code folding, automatic indentation, copy support, and read-only so you won’t accidentally delete or edit.
Orders can be associated with a customer either by or by customer id. The customer id matches the Nosto cookie (this cookie is typically called 2c.cId
).
The attributes associated with an identity can be used to segment users. This works similarly to how the attributes can be leveraged .
The query methods allow you to fetch basic recommender data and does not require any sessions. Query operations are light and do not give you the benefit of personalization but can be used to fulfill simple use cases e.g. an in-store display that always shows the top 10 viewed products.
_The given example simply fetches products related to a given search term aliased as q_related
and also fetches the most viewed products within the last week.
Querying products gives access to Nosto's product catalogues current state. It can be useful for backend integration and verification purposes. It is not meant for online use purposes as it doesn't include any concepts related to user sessions or attribution, for those refer to GraphQL For Headless
The maximum number of products that can be paged over is capped at 10000. If you need to get around this limitation, we recommend adding more restrictive filters to narrow down the result set.
You can query identities using the GraphQL Identities endpoint. An "identity" is the personal information associated with an email address.
So long as you are able to specify the email address, you will be able to query the identity, its associated customer affinity and the personalized recommendations for that identity.
The attributes associated with an identity can be used to segment users. This works similarly to how the attributes can be leveraged when importing them via a CSV.
You can generic recommendations using the GraphQL orders endpoint. The recommendations offered here don't use sessions so they aren't personalized but still offer enough flexibility to support a multitude of use-cases.
The endpoint can be used to fetch toplist recommendations i.e. best-sellers. Toplists recommendations are either sorted by views or buys.
The endpoint can be used to fetch random recommendations i.e. previews. Random recommendations are a totally randomized selection of products and often used for testing purposes.
The endpoint can be used to fetch related recommendations i.e. cross-sellers. Cross-sell recommendations allow you fetch related products to a given set of products.
Example: If you were to use this to add recommendations to a product page, the productIds
parameter would be a single-item array containing the product identifiers of the product that is being viewed.
Example: If you were to use this to add recommendations to an order-follow email, the productIds
parameter would be an array containing the product identifiers of the products that were purchased.
The endpoint can be used to fetch recommendations related to a search term.
Example: If you were to use this to add recommendations to a search page, the term
parameter would be the entire search term as queries by the user.
Note: This endpoint cannot be used for building auto-complete style integrations.
In case some cases it is desired to filter products by their properties. include
and exclude
fields of primary
should be used to achieve this. The former will filter only the products that match the specified attribute, the later will filter out the products that match the attribute.
include
field expects a type of InputIncludeParams
, whose attributes are
exclude
field expect type InputFilterParams
whose attributes are:
Here is an example of a query including filters
GraphQL is a query language for the APIs for getting your data. It is an alternative for the REST APIs. It is not specific to a single platform and works for all type of clients including Android, iOS or the web. It stands between your server and client and helps you to query your data in a more optimized way.
If you would like to leverage Nosto's intelligence engine in your Android app, please see our example app and the docs.
Leveraging Nosto's intelligence engine on iOS is just as easy as on Android. While an example app is yet to be provided, please read the Apollo docs.
You can query orders using the GraphQL orders endpoint. So long as you are able to specify the order number or an external order reference, you will be able to query the order.
This endpoint is used for blacklisting email addresses from receiving Nosto's triggered emails such as cart-abandonment emails, order-follow emails, and we-miss-you emails.
Having the corresponding email address in our system prior to blacklisting or unblacklisting is not a prerequisite. If the specified email record does not exist in our system, it will be created.
This endpoint requires an Email token.
You can specify multiple email addresses separated by a newline.
You can specify multiple email addresses separated by a newline.
This endpoint is used for initiating a personal-data takeout request. All requests to this endpoint are asynchronous and simply enqueue the email address for takeout. It may take up to 24 hours for the takeout process to complete. If the email address is found, a notification email (informing you about the takeout request) will be sent once the process has completed.
This endpoint requires an Email token.
This endpoint is used for redacting all personal data associated with an email. All requests to these endpoints are asynchronous and simply enqueue the email address for redaction. It may take up to 24 hours for the redaction process to complete. If the email address is found, a notification email (informing you about the redaction) will be sent once the process has completed.
This endpoint requires an Email token.
Nosto offers a multitude of APIs for different use cases. The APIs are not entirely RESTful but provide lightweight endpoints that expose similar usability.
All the APIs reside at https://api.nosto.com
and must be accessed over HTTPS.
Note: If you happen to call the interface via HTTP using a valid API key, that API key will be invalidated immediately and a notice of the token revocation will be sent to the account owner.
Authenticating with the API is done by using . You authenticate by using your API key as the password and the username is left empty.
You can see your API keys in the Nosto Backend under account settings. API key is always tied to a single store in your account.
Note: Keep your API key secret and delete it immediately if you think someone untrusted might have had access to it.
To get access to our APIs, please log in to your Nosto account at and contact support via chat. When you request API access, please provide following information:
What is the API in question?
What is the purpose for the API use?
What is the volume of requests?
What is the request distribution, on-demand or periodic?
Nosto does not rate-limit the API usage but follows a fair-use policy. Nosto reserves the right to revoke API access for any abusive API usage patterns.
Search GraphQL API uses different API endpoint. For more information see:
Nosto's GraphQL APIs can be used for simplified implementations for headless frontends. While we recommend using our JS API for use in headless environments, there are scenarios where a GraphQL based implementation might be more fruitful.
🚨Implementing Nosto over GraphQL will not allow you to leverage the entire Nosto suite. When Nosto is implemented over tagging and/or Javascript APIs it can modify web-pages automatically with Javascript, which means many things can work out of the box. For example inserting recommendations dynamically onto a webpage, rendering of templates, tracking of user behaviour. GraphQL instead is only an API which can be called from anywhere, so it cannot directly run Javascript or modify web-pages, instead those need to be implemented by the caller of the API. The following features are not available through GraphQL API:
Facebook Ads: As the pixel events aren't dispatched.
Content Personalization: As the GraphQL API only handles the personalization and not onsite experiences.
Popups: As the GraphQL API only handle the personalization and not onsite experiences.
AB-testing & dynamic placements: Because the current GraphQL API works with recommendation identifiers directly and not through placements.
Each customer who visits a site is uniquely identified with a session identifier. When a new customer comes to the site, a GraphQL session mutation call must be made to initiate a session. The resultant session identifier must be persisted and reused for all consecutive calls.
💡The session-duration is 30 minutes from the last activity.
We recommend using the following flow to creating and resuming sessions.
Read the session-identifier from the cookie.
If the session-identifier doesn't exist, initiate a new session and store the resultant session identifier in a cookie.
Read the session identifier from the cookie, and leverage the mutations for the outlined page types.
In order to start a new session when a session-identifier doesn't exist, you'll need to use the newSession
mutation
The newSession
mutation will return a unique session-identifier that you must persist.
⚠️ How you persist the session-identifier is entirely dependant upon your implementation. For example, you can persist it into a cookie or even application storage.
If you already have a session-identifier, you can pass that using the updateSession
mutation.
The example below is a generic example of how you update a session and pass the appropriate event to Nosto but in practice, you'll be using one of the page-specific mutations as shown in the section "Implementing on pages".
In order to use Nosto the different pages, you'll need to make the appropriate mutations for the different page types.
Every page-specific mutation requires you to pass the event for the specific page. These events are used to pass signals to Nosto's intelligence engine. Each of the page-specific mutations also allows you to fetch the recommendations for the given page type.
When you mutate a session, it is imperative that you send the full cart contents.
If the current shopping cart is empty, this can be omitted.
If you want to add a new item to the cart, without any page changes you should pass a new parameter of skipEvents
this will prevent analytics to count new page view event while still adding product to the cart.
if the add to cart happens as a result of a click on a recommendation element, you must pass the attribution along with the event as the ref
parameter.
When you mutate a session, it is imperative that you send the details of the currently logged-in customer. If no customer if currently logged in, this can be omitted.
When navigating between pages, if the navigation happens as a result of a click on a recommendation element, you must pass the identifier as part of the route and on the next page load, read the attribution parameter and pass it along with the event as the ref
parameter.
⚠️ If you do not pass the attribution parameter, the recommendations statistics will be inaccurate but will not affect the quality of the recommendations.
All default the recommendation results are returned when the recommendations are enabled and the account is a live account. If you would like to preview the recommendations, all the recommendation fields accept a boolean isPreview
parameter.
⚠️ Any recommendation requests when the preview mode is enabled do not accrue towards the statistics or skew the product relations.
In order to use the GraphQL session mutation to fetch recommendations for your home or front page, the event, in this case, must be VIEWED_PAGE
and you should specify a fully qualified URL of the home page as the target.
The pages query for home page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forFrontPage
request, as shown below:
Note: slotIds
accepts an array of String parameters
The forFrontPage
field will return the result of all the recommendations that are configured for the front page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
In order to use the GraphQL session mutation to fetch recommendations for your category page, the event, in this case, must be VIEWED_CATEGORY
and you should specify a fully qualified category path of the current category. For example, if you have a category called "Dresses" under the category "Women", the FQCN would be "/Women/Dresses".
The pages query for category page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forCategoryPage
request, as shown below:
Note: slotIds
accepts an array of String parameters
The forCategoryPage
field will return the result of all the recommendations that are configured for the category page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
In order to use the GraphQL session mutation to fetch recommendations for your search page, the event, in this case, must be VIEWED_PRODUCT
and you should specify the product-identifier of the current product being viewed.
The pages query for product page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forProductPage
request, as shown below:
The forProductPage
field will return the result of all the recommendations that are configured for the product page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
In order to use the GraphQL session mutation to fetch recommendations for your search page, the event, in this case, must be SEARCHED_FOR
and you should specify the search term of the query.
The pages query for search page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forSearchPage
request, as shown below:
The forSearchPage
field will return the result of all the recommendations that are configured for the search page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
In order to use the GraphQL session mutation to fetch recommendations for your cart or checkout page, the event, in this case, must be VIEWED_PAGE
and you should specify a fully qualified URL of the cart page as the target.
The pages query for cart page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forCartPage
request, as shown below:
The forCartPage
field will return the result of all the recommendations that are configured for the front page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
In order to use the GraphQL session mutation to fetch recommendations for your cart or checkout page, you must use a different mutation as compared to the rest of the pages.
⚠️ The customer, in this case, is the details of the customer making the purchase.
The pages query for order page also supports filtering recommendation for a specific Slot ID using the slotIds
parameter in forOrderPage
request, as shown below:
The forOrderPage
field will return the result of all the recommendations that are configured for the order-confirmation page. When slotIds
filtering is used, the result will only contain the recommendations for the specified Slot Ids.
Other page type fields are:
forNotFoundPage
- 404 page
forLandingPage
- landing page
forGeneralLayoutPage
- general layout page
This documentation is only for the implementation of CM 1.0 and most likely this doc shouldn't be used anymore. If you'd like to implement CM 2.0, please check this . If you're not sure which version you'd like to implement, please contact your technical solutions manager or our support.
Nosto's category merchandising APIs are meant to be used for resorting your existing product listing pages. It has support for listing the products in the order defined within Nosto for different categories, including paging and filtering support. It doesn't support taking over the product listing pages fully as it doesn't include support for creating category specific filters and calculating their facet counts. The expected implementation leveraging these APIs would keep on using their current solution for building most of the product list pages, but swap the shown products with the information retrieved from this APIs results.
You can query using the query below:
Setting the addAttributionParameters
parameter to true
, causes attribution parameters to be automatically rendered in product URLs. For example, the url https://example.com/product
becomes https://example.com/product?nosto_source=cmp&nosto=5e5e09f060b232790cbbccbf
. These parameters allow our client script to track the performance of Category Merchandising results.
If you wish to handle attribution parameters manually, the addAttributionParameters
parameter can either be set to false
or can be omitted.
Product views resulting from clicking products of a category listing need to contain the required attribution parameters:
type
: VIEWED_PRODUCT
target
: (product id)
ref
: (resultId
from the category merchandising response)
refType
: CATEGORY_MERCHANDISING
For example, given the following category merchandising response:
If a customer clicks on Cool Kicks, the following GraphQL query should be sent to fetch the product's details and to attribute the product view to the category merchandising result:
Graphql calls using Category Merchandising methods are treated as a category view by default. This behavior can be changed by including skipVCEvent: true
into the graphql request. All product URLs on a category page must be appended with #nosto\_cmp
fragment. An example of such a product URL would be www.test-store.com/product1#nosto\_cmp
where #nosto\_cmp
is the added fragment.
The batchToken
can be used the next batch of results. This is useful if you only wish to fetch the first 10 products when there may be thousands of results. To fetch the next batch, use the batchToken
in the next query like in the example below:
If you wish to skip the first number of pages, you can use the skipPages
parameter instead of the batchToken
. A page size is calculated from the maxProducts
parameter.
You can get token values from page under your Nosto Account. Each set of endpoints are secured using different token types.
In order to be able to provide personalized results, we will need to look up a session either by id or by reference. You read more about managing sessions on our wiki page.
Results can be filtered by specifying the include and exclude parameters. You can explore more parameters in the
API_REC
A deprecated token for using the legacy recommendations API
API_PRODUCTS
A token for accessing the Products API
API_EMAIL
A token for managing customers using the Blacklist and GDPR APIs
API_APPS
A token for accessing the new GraphQL APIs
API_OMNICHANNEL
A token for accessing the new Omni-channel API
API_RATES
A token for updating rates using the Exchange Rates API
API_SETTINGS
A token for configuring your account using the Settings API
Authorization
Basic :NOSTO_API_TOKEN
While Nosto's crawler attempts to keep its copy of your catalog as fresh as possible, there are scenarios where we may not be able to update all the information as quickly as needed.
In these scenarios, we recommend that you implement our Discontinue API which allows you to push all your product identifiers to discontinue them and have the changed instantly reflect across our entire engine.
Here's an example of a Curl request.
You can request an API token (API_PRODUCTS) by getting in touch with our support personnel. Once the token has been granted, you will be able to find it listed in the authentication tokens section in the admin.
The Discontinue API takes an array of product metadata and has no hard limit on the number of items that you can specify and is only limited by the maximum size of the payload of 2 MB.
You can discontinue products as often as you need.
You should make an API call when any product is discontinued and removed from your catalog. If a product has simply gone out of stock, we recommend making an API to update the product with the correct availability.
While Nosto crawls your site and automatically discontinues products that are no longer available, it may lag behind when your site has a large catalog. In these environments, it is recommended to use the Discontinue API to immediately discontinue the product.
A single-page application (SPA) is a web application or web site that interacts with the user by dynamically rewriting the current page rather than loading entire new pages from a server. This approach avoids interruption of the user experience between successive pages, making the application behave more like a desktop application. In a SPA, either all necessary code – HTML, JavaScript, and CSS – is retrieved with a single page load,[1] or the appropriate resources are dynamically loaded and added to the page as necessary, usually in response to user actions. The page does not reload at any point in the process, nor does control transfer to another page, although the location hash or the HTML5 History API can be used to provide the perception and navigability of separate logical pages in the application.[2] Interaction with the single page application often involves dynamic communication with the web server behind the scenes.
If you have a website, that is built atop JavaScript frameworks, such as AngularJS, Ember.js, ExtJS, Knockout.js, Meteor.js, React or Vue.js, your site has likely adopted SPA principles.
Important: You cannot mix JS API and Session API. You need to use either or. If you are not sure which one to use, please contact Nosto's support.
Note: The examples in the documentation are written in ES5 and leverage advanced browser features such as Promises.
While Nosto's crawler attempts to keep its copy of your catalog as fresh as possible, there are scenarios where we may not be able to update all the information as quickly as needed.
In these scenarios, we recommend that you implement our lightweight Recrawl API which allows you programmatically instruct our crawler to reindex a given URL.
For example, if you add a discount of -10% to all the products in your "Shirts" category, you can use the Recrawl API to recrawl all the given URLs and update the prices.
Here's an example of a Curl request.
You can request an API token (API_PRODUCTS) by getting in touch with our support personnel. Once the token has been granted, you will be able to find it listed in the authentication tokens section in the admin.
The Recrawl API takes an array of product ids and URLs and has no hard limit on the number of items that you can specify.
You can recrawl as often as you need but bear in mind that every recrawl adds an extra page load to your server.
This endpoint is used for toggling the marketing permission for an email. The marketing permission for an email is normally gathered via the customer tagging.
This endpoint is only intended for use when the consent needs to be programmatically managed and should be a considered an advanced use case.
This endpoint requires an Email token.
When using multi-currency, this endpoint is used to update the exchange rates for your account. When new rates are sent via this endpoint, the changes will reflect instantly on your store as the product prices are multiplied with the provided rates in real-time.
Note: This endpoint should only be used when using multi-currency. Please refer to our multi-currency guide prior to using this endpoint. Incorrect usage of these endpoints will result in a total outage of your personalization setup.
This endpoint requires a Rates token.
You can request an API token (API_PRODUCTS) by getting in touch with our support personnel. Once the token has been granted, you will be able to find it listed in the authentication tokens section in the admin.
You can send exchange rates as often as you like but at the bare minimum, the exchange rates should be sent when they are changed.
While Nosto's crawler attempts to keep its copy of your catalog as fresh as possible, there are scenarios where we may not be able to update all the information as quickly as needed.
In these scenarios, we recommend that you implement our enhanced Products API which allows you push all your product metadata and have the changes instantly reflect across our entire engine.
For example, if you add a discount of -10% to all the products in your "Shirts" category, you can use the Products API to bulk update all the products.
Here's an example of a Curl request.
Categories must always be delimited by a slash. For example, Home/Accessories
or sale/summer/shirts/long-sleeve-shirts
is a valid category while Home > Accessories
is not.
You can request an API token (API_PRODUCTS) by getting in touch with our support personnel. Once the token has been granted, you will be able to find it listed in the authentication tokens section in the admin.
The Products API takes an array of product metadata and has no hard limit on the number of items that you can specify and is only limited by the maximum size of the payload of 2 MB.
You can update products as often as you need although, initially you'll need to send the entire catalog to populate the replica of your catalog on Nosto.
You should make an API call when any product information changes. If a non-critical field of the product e.g. description, has changed, you can delay the product update as descriptions are rarely visible to the end customer. When the price or availability of the product changes, you should make an API call right away as this will instantly reflect in the recommendations.
While the product API contains the full superset of the information in the tagging, it also allows you to pass sensitive information to us. Sensitive information is fields such as the supplier cost (margin) and the inventory level. These fields are only mutable via the API.
The following fields are required:
product_id
name
url
image_url
availability
price
price_currency_code
Onsite features such content and recommendations are injected into what we call "placements".
Nosto requires that you specify an array of placements and will respond with the response for those specified placements. There are two types of placements and it is possible to leverage either of them when implementing Nosto on an SPA:
These are defined as empty hidden elements in the DOM with the class nosto_element
. The identifier of the element denotes the placement identifier. An example placement is as follows:
The Div element remains hidden until Nosto injects content into it.
These are defined in the administration panel and are CSS and URL rules to define where content is to be injected. In order to allow these dynamic placements to be usable, you should follow the guide below for managing placements automatically.
When using the Session API, the placements are set through a function call setPlacements
which expects an array of strings. In order to support dynamic placements setup in the Nosto backend, we recommend that instead of setting the placements array contents directly from your application, you use the following API to get a list of placements for the page:
The function scans the current page (document object) for any valid placements at the time of execution and returns them in an array suitable for the setPlacements
-function. As long as it is called after the targeted elements have been rendered into the document, it will return both the static and the dynamic CSS and URL rules based placements on the page. Dynamic placements are picked up regardless of them being rendered or not. Static placements are always obtained through scanning the page. Freshly created Nosto accounts come with static placements only. ( In case you have programmatic placement codes that are not in the page document at all, you can add them to the array to combine both manual and automatic approaches. )
Here's an example call where placements are scanned automatically:
To continue with the example, let's assume the api.placements.getPlacements()
returned an array with 2 placements: ['frontpage-center-1', 'frontpage-banner']
and then let's assume that we would have set up in the backend a recommendation campaign for frontpage-center-1
and a content campaign for frontpage-banner
.
Here is an example of a sample response.
The response object will contain a campaigns field which has both content and recommendations under their own fields and within those the keys are the placement identifiers and the value will be an object containing the payload and parameters used for click attribution.
By default the API returns campaigns data in JSON notation. Product campaigns contain an array of recommended products and content campaigns contain an html field. The implementing application can decide how it does the rendering in the application, but Nosto does provide a utility function to help with injecting the html content campaigns into the right place: api.placements.injectCampaigns()
. The function expects an object where the field keys are the placements to be injected and values are either a string or an object with a string field named html
. The function will scan the document to find the active placements and insert the html to the right location. Any javascript blocks within the html content will be executed as well.
Here is an example of rendering campaign results.
This example assumes the implementing application has a utility function to transform products json into html to be inserted, alternatively there could also be a function that gets the product json and renders them itself directly.
In the event that you would like to offload the campaign rendering fully to Nosto, you can skip transforming the products json to html and instead use the recommendation templates in the Nosto backend to produce html. In that case you would set the response mode in the Session API to be 'HTML', then the response will not have a campaign
field and will instead contain a recommendations
field which has the HTML content of all campaigns, regardless if they are content or recommendation campaigns. You can then pass that field to a utility method api.placements.injectCampaigns
that will inject the HTML into the page.
Here's an example call
The injectCampaigns
method automatically handles the injection of both the recommendations and the content. If there is no response for a specified placement, the element (into which to be injected), remains as-is.
The cart content must updated whenever the cart contents change. The cart contents are the 1:1 representation of the user's cart. Also note that the cart contents is only send to Nosto when you perform an . If you want to send the cart contents to Nosto right away, you add .viewCart().update()
to your call.
You may also pass null
or undefined
to signify that there was no change in the cart. The default state of the cart in the session is empty.
The cart information is used by the Nosto to tailor the recommendations, dispatch abandoned cart emails and fire Facebook pixel events for retargeting purposes.
or when sending the contents to Nosto right away
Note: Passing null
or undefined
will prevent the cart contents from being mutated on Nosto. Passing an empty object {}
will reset the cart contents.
The customer information is primarily used for sending personalised triggered emails and for building multi-channel experiences.
or when sending the contents to Nosto right away
Note:
Passing null
or undefined
will prevent the customer information from being mutated on Nosto. Passing an empty object {}
will reset the customer information.
The new marketing-permission flag denotes whether the customer has consented to email marketing. If the marketing-permission field is omitted, we assume that the current customer has not given their consent and Nosto will refrain from sending out any personalized triggered emails.
The marketing permission is false by default but if a user has explicitly agreed to receive marketing then you can set it to true manually. In practice, this means reading and mapping the value from opt-in for marketing in your platform e.g. a consumer explicitly subscribed for marketing emails when checking out.
The marketing-permission should be included as a part of the customer tagging and should be rendered on all pages.
The customer-reference can be leveraged to unify sessions across channels such as between online and offline. It is a unique identifier provided by you that is used in conjunction with the Nosto cookie. The customer-reference can also be used to uniquely identify users in lieu of an email address.
The customer-reference should be a long, secure and a non-guessable identifier. For example, use your internal customer-id or the customer's loyalty program identifier and use a secure hash function like an HMAC-SHA256 to hash it.
You must use a valid domain for your website. If you are creating a test account and running your store locally, you must use valid TLD as using localhost
is not supported.
You cannot use the following domains as they are reserved by the IANA.
.test
.example
.localhost
.invalid
We recommend using a valid TLD that is aliased to localhost
for testing purposes. You will need to edit your operating-system dependent hosts file to add an alias for the domain you are using.
While Nosto crawls sites to replicate the product catalog, it is unable to do so on SPAs. In order to synchronise your product catalog with Nosto, you'll need to to keep the Nosto catalog in sync.
Note: This step must be completed prior to proceeding with the implementation. Without this step, it will be troublesome to preview and debug the recommendations.
To start tracking visits and content the Nosto script needs to be active on all pages within the store. Replace the account-id in the snippet below with your own account-id and place the code within the <head>
section of your DOM. You can find your account-id from the admin.
The JS comprises of three parts - the first is the "stub" (which allows API usage prior to the script being loaded), the second is the "autoload" configuration (which prevents Nosto from automatically initiating once loaded.) and finally the Nosto script is loaded.
Note: The script and the snippet should be added as high up in the <head>
portion of the page so the connection is initialised as soon as possible. As the script is flagged async
, the page load isn’t delayed.
Note: This needs to exist on every page.
When a visitor logs in customer information should be passed. If the customer isn't logged in, this can be omitted. Similar to setting the , customer data is only sent to Nosto when an is performed.
Here viewCart
is only provided as an example. But the actual tracking method to be invoked will depend on customer's current page. For more information on this, please refer
Alternatively to the script injection Nosto can also be used as a library dependency in your Javascript application via the following utility library
Action in the Session API context means fetching recommendations for a specific view. For example when a visitor navigates from the front page to a product view you would most likely fetch recommendations related to a product. This would be considered as an Action. Setting the cart contents however would not be considered as action.
It's also good to keep in mind that each Action is considered as a page view in Nosto's analytics. It's recommended to perform an action only once per route change to keep the analytics consistent and comparable to traditional "static" e-commerce stores.
Route change in the context of this documentation means, as it stands, when the navigational route (url) of the application is changed. In traditional web sites this would be a (full) page load.
Nosto uses a cookie to identify browsers between their visits to the site. The purpose and usage of this cookie is very similar to how web analytics tools, such as Google Analytics, work.
Each session is identified using a randomly generated 24-character secure string and persisted in 2c.cId
cookie.
For privacy reasons, if you have the need to disallow any third-party tracking cookies, this feature can be used to achieve that.
This feature will not remove previously set 2c.cId
cookies and will only affect sessions from the time of implementation onward.
``
You can opt-out of tracking by using the setCustomerIdentifierService
method.
Assuming that your platform has a method called platform.getSID()
that returns the current session identifier as offered by your platform - you would use:
To showcase, the flexibility offered by this API - the following example simply uses LocalStorage
(instead of cookies) to persist the session identifier.
Nosto already offers the Session API, for recording attribution. But it's limited to vp
events so far. In an attempt to expand this functionality to any event types, a new Session API method recordAttribution
has been introduced. This method can be utilized to update current visit with details of events for attribution.
Deprecated
The recordAttribution
usage with Session API is deprecated and no longer recommended. The API will continue to work without any issues but we recommend using the JS API version. For more info on JS API, please refer JS API/Record Attribution
The Session API method recordAttribution
accepts one event at a time, but users can chain multiple calls to recordAttribution
and add as many events as they want.
type
string
yes
type of event to which a placement (ref) should be attributed
target
string
yes
id of the element that's been loaded as a result of the event
ref
string
no
id of the element that hosted the link which triggered the event
refSrc
string
no
id of parent element of the link that triggered the event
Nosto supports following predefined event types
View Product (VP)
An event associated with viewing a single product
View Category (VC)
An event associated with event a single category of items
Internal Search (IS)
An event associated with results of search internal to a merchant's website
Add to cart (CP)
An event associated with adding a product or bundle to a cart
External Campaign (EC)
Custom Campaign (CC)
An event associated with campaigns, which are not part of nosto, that directed a user to a merchant website. These campaigns will not contain google's UTM parameters in ev1
request URL
External Search (ES)
An event associated with search outside of merchant's website (Google for e.g.) that brought the user to merchant's website
Give Coupon (GC)
An event associated with a coupon code campaign popup in which the customer has acted upon
Source (SRC)
An event associated with a customer action which needs to be attributed to one of Nosto's feature (api, email, rec, imgrec, cmp). Here the information is usually passed through a pre-configured source parameters name (nosto_source
, by default) in ev1
request URL
Cart Popup Recommendations (CPR)
An event associated with a recommendation, that's shown when a product is added to cart, in which a customer has acted upon
Page Load (PL)
An event associated with a page load merchant's website
Content Campaign (CON)
Event triggered when a customer performs an action inside a content campaign
Attributing a placement click to a vp
(View Product) event
In the above example,
vp
specifies the type of event and it corresponds to View Product
12345678
specifies the target and it corresponds to the ID of the product that's being viewed
frontpage-nosto-1
specifies the slot’s ID from the placement that hosted the product that’s being clicked
Attributing a placement click to a cc
(Custom Campaign) event
In the above example,
cc
specifies the type of event and it corresponds to Custom Campaign
12345678
specifies the target and it corresponds to the ID of the product that's being viewed
frontpage-nosto-1
specifies the slot’s ID from the placement that hosted the product that’s being clicked
Adding the fourth refSrc
parameter
In the above example,
vp
specifies the type of event and it corresponds to View Product
7513863258337
specifies the target and it corresponds to the ID of the product that's being viewed
productpage-nosto-3
specifies the slot’s ID from the placement that hosted the product that’s being clicked
7513872007393
specifies the reference source and it corresponds to the ID of the product displayed in current page (PDP), that contained the ref
element, (productpage-nosto-3
)
Here we are recording a View Product
event for product 7513863258337 which was clicked from the recommendation slot productpage-nosto-3
while on another product page 7513872007393
Attributing a click inside a content campaign to a con
(Content Campaign) event
In the above example,
con
specifies the type of event and it corresponds to Content Campaign
6ef452da787623f2
specifies the target and it corresponds to the ID of the content campaign inside which a customer performs an action
In similar way, we will be able to record attribution for all the event types listed under Event Types
section of this documentation.
In this article, you will learn how to implement multi-variants in Nosto. When the implementation is complete, you will be able to display different products at different prices to different customer groups.
Note: You can only change the pricing and the availabilities using this feature.
Note: You cannot use SKUs with this feature at the time of writing.
You will need to implement the multi-variate tagging if you have any such scenarios:
Your store has different prices for B2B and B2C customers
Your store has different prices for logged-in and logged-out customers
Your store has different prices for loyalty customers
Your store has different prices and availabilities for different locations
Prior to the multi-variate implementation, ensure that the Nosto tagging is correctly in place. Some of the tagging must be slightly amended to support multi-variants.
The product update API calls must be amended to denote the primary currency code of the product. Typically, most retailers have a primary currency which is the default currency of the inventory.
For example, a retailer who has different prices for normal and loyal customers would have GENERAL
as the default variation id and LOYAL
as an extra variation.
Some additional properties named variation_id
and variations
must be placed within the product object.
No. You cannot use SKUs with this feature at the time of writing.
The cart and order tagging can be left as-is but the prices must be in the customer's currently active currency. For example, a customer shopping in Swiss Francs (CHF) should have all the cart items tagged in Swiss Francs (CHF). Failure to do so will result in incorrect prices in any triggered emails such as abandoned cart or order followup.
Once you have amended the product metadata, you must change the session usage to also pass the active variation of the customer.
For example, on the site of a retailer, who has different prices for normal (GENERAL) and loyal (LOYAL) customers, if the customer is a logged in customer and is a known loyalty customer, the nosto_variation
element should show LOYAL
. If the customer logs out or new customer visits, and there is no way to identify him as a loyal customer, the nosto_variation
element should show GENERAL
.
Once the product metadata changes have been done, you need to configure and enable it from your admin panel under Settings > Other > Multi-Currency. Toggle the Use Multiple Currencies switch on and Use Exchange Rates switch off and set the variation ID of the primary currency via the input field and toggle on the exchange rates switch.
Note: Ensure that the Variation ID of the primary currency matches the value sent via the variation_id
element in the product metadata.
Note: Multi-variants cannot be used in conjunction with exchange-rates based multi-currency feature. You must keep the Use Exchange Rates switch off.
You will also need to configure the price formatting for your primary and secondary currencies.
Once you enabled multi-variants you can preview the product prices for different groups by navigating to Tools > Products and choosing a product.
You will see one or more dropdowns that contain the prices and the availability for that group.
When you have reviewed your set-up, you’re all set and ready to go live with our features. Nosto will automatically handle the different customer groups across its feature set.
When viewing a home-page, there's no context to be provided, so invoking the viewFrontPage
will suffice.
When viewing a product, you should send the product-id of the current product being viewed. Unlike the regular implementation, you do not need to pass the entirety of the product metadata.
Optional event that can be sent to signal that a specific product variant (SKU in Nosto terms) is being viewed. Typical use case for sending this event would be from product detail page when the user selects a product variant, such as some specific color and/or size. The recommendations can then be configured to update and give preference for products that have similar variants available. For example "Other products also available in the same size". Product variant views are added with the function viewProductSku
:
This example leverages dynamic placements and html rendering
When viewing a category, you should send the fully qualified name of the current category. This is not necessarily the same as the handle of the category used in the address of the category page.
When the category or collection id is available it can be provided via
It is needed for accurate attribution in certain Nosto products such as Category Merchandising.
You don’t need to ensure the case-sensitivity of the category being passed so long as the path is tagged in the same way as your products’ categories are.
On Shopify, the collection title should be used, so in the snippet above, use simply "Dresses" instead of the collection handle.
Nested categories must always be delimited by a slash. For example, /Home/Accessories
is a valid category while Home > Accessories
is not.
When viewing the results of a search, you must send the exact search-term as queried for.
Note: You don’t need to normalize or encode the search query in any way.
When viewing a checkout page, there's no context to be provided, so invoking the viewCart
will suffice.
On all thank-you and order-confirmation views, the order confirmation metadata must be passed.
The order confirmation metadata is used for sending personalised order-followup emails, personalise the recommendations e.g. order-related, for segmentation insights and conversion statistics.
When viewing a page / view that was not found, there's no context to be provided, so invoking the viewNotFound
will suffice.
When a page with a type - other than the ones listed here - is viewed, there's no context to be provided, so invoking the viewOther
will suffice.
The load
method returns a promise which can be consumed to get the raw recommendation data. The raw recommendation data is an object containing the recommendation data.
Recommendation results are returned in a promise by calling either load()
or update()
. The difference between these two methods is:
load()
causes the load count of the most recently tracked page view to be incremented.
update()
does not automatically increment the page load count.
In order to achieve an accurate reach statistic for recommendations, load()
should be called once per page view when fetching recommendations and all proceeding recommendation requests should use update()
.
Normally requesting product related recommendations happens in relation to viewing a product detail page, so a typical product related recommendation request looks like this:
The above will also add a product view event for the user. In some cases there are needs to request product related recommendations even when the user is not looking at a product. In these cases, to avoid reporting the user event, include a { trackEvents: false }
flag to the load
function, for example:
If for implementation specific reasons there are multiple calls for product related recommendations on the product page, only the first request should track the event and subsequent requests should have the { trackEvents: false }
flag include.
When a recommended product is viewed, the result_id
from the recommendation result should be used. Below is an example recommendation result (some fields have been omitted).
The snippet of code below attributes product1
to the result id nosto-frontpage-1-fallback
from the recommendation result above and fetches recommendations for nosto-productpage-1
.
If you wish Nosto to render the recommendations and returns HTML for the recommendations you can set the response mode to HTML by adding .setResponseMode('HTML')
into your call. A full example for 404 page would look like this
Please note that Nosto will not inject the returned HTML into the DOM even if the response mode is set to HTML. The logic for injecting the recommendations must be implemented in the application side.
Usually adding an Add to cart button directly into the recommendation which lists multiple products is fairly straightforward, the website just needs to have an appropriate javascript function to do the operation. Nosto provides ready-made functions for multiple platforms so check the Nosto documentation specific to your e-commerce platform or if needed look into your e-commerce platform's documentation and support on how to create such a function.
Once the Add to cart button is pressed it should call that function to add the products to the cart, but it should also additionally let Nosto know that the button was pressed so Nosto can track the sales from the recommendation. This can be done with the reportAddToCart
function as follows:
⚠️ The api call is only for informing Nosto about the attribution (that the product was added from the recommendation), setCart
function in the Session API should be used to tell Nosto the user’s cart contents.
The load
method returns a promise which can be consumed to get the raw placement data. The raw recommendation data is an object containing the placement data.
Customer affinities are taken into account by the recommendation engine and matched with the affinities defined on the products. The affinities are determined automatically, but the API allows for a more granular manual control when required.
In case addAffinity
is called multiple times, the provided values will all be merged together.
Note: If the same key is provided more than once, the latest encountered value is used, and the earlier keys are overridden.
It's possible to provide multiple affinities in a single call to addAffinity
.
If the current state of the request needs to be cleared, a second parameter can be provided to the addAffinity
call. In the example below, sku.size
key will be removed from the request.
Note: This only affects the current local state of the request. It will not remove user's affinities already saved on the backend.
You can disable Nosto for a given customer if they don't give consent for data processing or if legal reasons such as requires to disable Nosto for an individual.
This method disables the initialization of Nosto entirely, meaning that all associated Nosto features on your web store for that user are also disabled.
You will need to wrap the Nosto script in a conditional that activates only if the customer has accepted to activate Nosto. Below is an example that simply checks for the existence of a cookie called accepts_marketing
but you should change the conditional to match your consent management implementation.
Normally Nosto uses a cookie to identify browsers between their visits to the site. The purpose and usage of this cookie is very similar to how web analytics tools, such as Google Analytics, work.
You can use opting out of session tracking in case you want to enable Nosto's features in a limited manner where Nosto doesn't track browser sessions. When users opt out of session tracking, Nosto treats each request like it would be a new session that is then immediately discarded. In this mode, Nosto can still serve generic trend based recommendations, but any feature that relies on users actions over multiple requests will never activate.
Any information sent to Nosto with the requests activated by the implementation will still be processed normally by Nosto's service even when users have opted out of session tracking. Merchant should ensure necessary consent is obtained for this processing.
Nosto supports opting out of session tracking via the "Do Not Track" feature. If you leverage Nosto's "Do Not Track", Nosto will avoid setting a session identifier.
This feature does not disable cookies entirely. It only disables the 2c.cId
cookie that is used for identifying browsers between their visits to the site.
You can opt-out of tracking by using the setDoNotTrack
method. You must do so before making any requests to Nosto.
Having done so, you can also verify that you have opted out by using the isDoNotTrack()
method
In this article, you will learn how to implement multi-currency in Nosto. When the implementation is complete, you will be able to display product prices (in any feature) in different currencies.
Prior to the multi-currency implementation, ensure that your implementation is correct. Some of the API calls must be slightly amended to support multi-currency.
The calls must be amended to denote the primary currency code of the product. Typically, most retailers have a primary currency which is the default currency of the inventory.
For example, a US-based retailer who sells in Euros (EUR) and Sterling Pounds (GBP) would have US Dollar (USD) as the primary currency while Euro (EUR) and Sterling Pounds (GBP) would be secondary currencies whose exchange rates would need to be sent via an API.
An additional property named variation_id
must be placed within the product object.
Yes. Prices for all SKUs will automatically be converted using the same logic. As long as your SKUs are tagged, no additional changes are needed.
The cart and order tagging can be left as-is but the prices must be in the customer's currently active currency. For example, a customer shopping in Swiss Francs (CHF) should have all the cart items tagged in Swiss Francs (CHF). Failure to do so will result in incorrect prices in any triggered emails such as abandoned cart or order followup.
Once you have amended the product metadata, you must change the session usage to also pass the active currency of the customer.
For example, on the site of a US-based retailer who sells in Euros (EUR) and Sterling Pounds (GBP), if the customer changes the currency to Sterling Pounds (GBP), the setVariation
method must be passed GBP
. If the customer changes the currency to Euros (EUR), the setVariation
method must be passed EUR
.
In the example above, 0.77
is the exchange rate from US Dollars (USD) to British Pounds (GBP) and 0.91
is the exchange rate from US Dollars (USD) to Euros (EUR).
The valid_until
entry defines the expiration date. When the expiration date is reached, the exchange rates won't be applied anymore and prices will be hidden for all the secondary currencies to prevent displaying outdated prices.
When recommendations are served, then exchange rates are dynamically applied to the product prices to reflect the active currency.
Once the tagging changed have been done and the API implemented, you need to configure and enable it from your admin panel under Settings > Other > Multi-Currency. Toggle the Use Multiple Currencies and Use Exchange Rates switches on and set the variation ID of the primary currency via the input field and toggle on the exchange rates switch.
Note: Ensure that the Variation ID of the primary currency matches the value sent via the
variation_id
element in the product tagging.
You will also need to configure the price formatting for your primary and secondary currencies.
Once you enabled multi-currency and made an API call, you can review the exchange rates received by Nosto by navigating to Settings > Other > Multi-currency.
You can also preview the product prices for different currencies by navigating to Tools > Products and choosing a product.
You will see one or more drop-downs that contain the prices and price calculation for the currency.
When you have reviewed your set-up, Nosto updates product prices in real-time for all the currencies and displays the appropriate currency to the right target groups of users. You’re all set and ready to go live with our features.
An event associated with campaigns, which are not part of nosto, that directed a user to a merchant website. These campaigns will contain google's UTM parameters ( for more info.) in ev1
request URL
Important Even if you would not display any recommendations in your order-confirmation view you must still set placements (.setPlacements(...)
) and load (.load()
) the results. Setting the order works in a similar manner than and and an must be performed for the data to be sent to Nosto.
Popups are handled automatically and you do not need to control the rendering of the popups. As events are dispatched, popups will show and hide automatically. If you would like to have programmatic control over the popups, see .
In order to send the exchange rate multipliers to Nosto, you will need to use our . Below is a small snippet of what the payload looks like.
Nosto is initialized automatically once the script has loaded. Unlike the legacy script, you do not need to manually initialize Nosto.
In the event that you would like to initialize Nosto but not have it automatically load the recommendations, you can set setAutoLoad
to false.
Also see: Setting up for how to first include the script stub that allows API usage in this manner.
Note: You will need to manually load the recommendations when the autoloading is disabled. A recommendation request needs to be sent in order to track user events. So, if autoloading is disabled and you wish to track an order or cart changes, you need to send a recommendation request even if you don't wish to display recommendations on the page.
In most implementations, there isn't any need to use the Nosto JavaScript API and the regular tagging implementation approach will suffice.
Typically calling the API should be approached only after the normal tagging implementation has been done and now needs to be extended with something that doesn’t come out of the box. The JavaScript API is commonly used to support dynamic functionality i.e. without a page reload. For example, showing recommendations in a product quick view.
If you are working on a Single-Page App (SPA) or a Progressive Web Application (PWA) you most likely want to use Session API. Also, please note that you can not use both, Session API and JS API on a same page or application.
JavaScript API works only in on-site context. Using the API does not require authentication but requires that Nosto embed script is included.
Nosto embed script needs to be recent enough. The easiest way to check that you are using a recent version enough is to view your site’s HTML source and make sure it includes the text nostojs.init
. In case that is there you are using the version that supports the Nosto Javascript API.
If you are using Nosto with a async
script tag (AKA Direct Include), then you must add a javascript stub as an inline script block before you call the Nosto Javascript API (see the Javascript examples). You do not need to call nostojs.init()
when using Direct Include.
Using the stub ensures that your code will be executed correctly even if you call the Nosto JS API before the Nosto script has loaded.
This is done automatically by Nosto as long as you follow the Handling attribution- topic.
Alternatively you can define the recommendation (result_id
) after an action by adding .setRef(productId, result_id)
to your call. In practise you would only do this when performing the action for product view.
Example when productId 123 was clicked on a recommendation nosto-frontpage-1:
Tracking external campaigns such as Google Ads, Facebook Ads, etc. will work automatically as long as you perform an action on the landing page of your ad.
This documentation highlights the differences in the response rendered when using Parameterless Attribution with Session API
Parameterless attribution, when enabled, removes tracking parameters from the URL and tracks user interactions with Nosto recommendations/campaigns through an alternative approach. For more information on Parameterless Attribution, please refer the help article here
It's important to note that when using Session API with Parameterless Tracking enabled, the structure of response returned is different from the traditional Session API responses.
Below are the examples of responses with/without Parameterless Attribution
This section is only applicable when using HTML response mode in Session API calls. JSON response handling remains the same in both cases.
When handling HTML responses from Session API calls, it's recommended to use the below approach while extracting html content from the response, to support both cases discussed above.
In the above example, `htmlContent` gets the value from the html property within the placement object (productpage-nosto-2
), if available (when Parameterless Attribution is enabled).
Gets the HTML content directly from the placement object (productpage-nosto-2
) otherwise (when Parameterless Attribution is disabled).