Your recommendation engine cannot surface a new product. Four things that fix it

About this series. We are building a recommendation engine from scratch on Google's own store data — the public GA4 export of the Google Merchandise Store — and publishing what comes out, including what does not work. Part 1 built the data foundation; part 2 put five models against each other and a 30-line SQL query won. This is part 3: what that winner does with a product it has never seen.

A recommender built on “people who viewed this also viewed that” is a table of product pairs. A product nobody has viewed has no pairs, and therefore no row. Asked what to recommend alongside it, the model does not return a worse list. It returns nothing.

39 of 418products on sale in the test window had no view history at all
0%hit rate for the behavioural model on those products — it had nothing to show
32%hit rate when the same sessions were served by a content-based model
Chart comparing a collaborative and a content-based recommender by how much history the product had: 0% versus 32% for products with no history, 51% versus 33% for products with 100 or more sessions.
Test sessions grouped by how much history the shop had on the product the shopper opened. The two models cross over.

Why this is worth a retailer's attention

Not because the failure is dramatic — because it is silent. A product that is never recommended does not generate a complaint, a support ticket or an alert. It appears in the sales report as a weak line rather than an invisible one, which is the worst possible disguise: the usual response to a weak line is to delist it.

It also compounds. Products with history get recommended, which generates more history, which earns more recommendations. Products without it stay without it. Nobody decides this; it is simply what a model trained on past behaviour does when nothing corrects for it.

History behind the product the shopper openedBehavioural modelContent model
No view history at all — 39 products0% (empty list)32%
Fewer than 20 sessions4%4%
20–99 sessions31%21%
100 or more sessions51%33%

The crossover is the useful part. On well-established products the behavioural model wins by eighteen points and deserves to. On products with no history it is not in the race. These are not a better and a worse model; they cover different parts of the catalogue.

Four things to do about it

1. Count it before you fix it

One query against your recommendation logs: how many of the products you had on sale last month were never once shown in a recommendation slot? That number is your cold-start exposure. In most shops nobody has ever looked at it, and it is the only way to know whether the rest of this article is worth your time — if the answer is under 2%, it is not.

2. Never render an empty slot

There is a ladder here, and most shops stop too early on it.

Bestsellers

A reasonable floor, and far better than an empty block — five minutes of work, and the products are at least known to convert. The cost is entrenchment: what already sells becomes the only thing anyone is ever shown, and the long tail never gets a turn.

Top sellers in the same category

Measured on our test sessions, this scored 32% where the behavioural model scored zero. Better, and still blunt: the category “Apparel” held 121 products, so “same category” is a weak statement of similarity.

Borrow the statistics of genuinely similar products

The one worth building. Embed each product's title, description and attributes with a language model, find the nearest existing products by meaning, and let the new line inherit their recommendation lists. A new navy zip hoodie has no history of its own — but the shop already knows that people who viewed the other zip hoodie went on to view the heavyweight pullover and the charcoal sherpa. The new product borrows that from the moment it is listed, with no interaction data at all.

The difference between the second rung and the third is the difference between “something else from the same shelf” and “what people who liked this kind of thing actually went on to look at”. The inputs for the third already exist in your product catalogue; no new tracking is required.

3. Give every new product a guaranteed share of impressions

The step people skip, and the one that keeps the others honest. Inherited statistics are an educated guess; a product's own are better. But a product cannot earn its own history if it is never shown, so the decision has to be deliberate: some fixed share of recommendation slots goes to products below your history threshold, for a fixed window.

This costs a little conversion rate up front, and it is worth being clear-eyed that it does. You are buying data. The alternative is a catalogue permanently sorted by arrival date.

4. Graduate products, and put coverage on the dashboard

Switch each product to its own behavioural data once it crosses the history threshold. In our data the crossover sat somewhere between 20 and 100 sessions; yours will differ, and it is worth measuring rather than assuming. Then track share of catalogue ever recommended beside click-through rate. Accuracy alone will never tell you that four fifths of your range is unreachable — that is precisely the blind spot that lets a bestseller fallback look like a success.

Under the hood — for the technically curious

The evaluation is the same next-item test as part 2 — trained to 10 January, scored on sessions from 11 to 31 January that the models had never seen — split by how many training sessions had viewed the product the shopper opened:

SELECT
  CASE
    WHEN IFNULL(i.n, 0) = 0 THEN 'never viewed in training'
    WHEN i.n < 20  THEN '1-19 sessions'
    WHEN i.n < 100 THEN '20-99 sessions'
    ELSE '100+ sessions'
  END AS history_bucket,
  COUNT(*)                                      AS test_sessions,
  ROUND(COUNTIF(co_blank) / COUNT(*) * 100, 1)  AS pct_no_recommendation,
  ROUND(COUNTIF(co_hit)   / COUNT(*) * 100, 1)  AS viewed_together_hit_pct,
  ROUND(COUNTIF(cat_hit)  / COUNT(*) * 100, 1)  AS same_category_hit_pct
FROM scored
LEFT JOIN item_n i ON i.item_key = scored.input_item
GROUP BY history_bucket

Two honest limits. The two cold buckets hold only 34 and 25 test sessions, so treat those hit rates as indicative rather than precise; the empty-list result is structural and does not depend on sample size at all. And the inheritance approach on the third rung is the experiment we are running next, not a measured result — when there are numbers, they will be published here whichever way they fall.

Data and licence

bigquery-public-data.ga4_obfuscated_sample_ecommerce — the obfuscated GA4 export of the Google Merchandise Store, 1 November 2020 to 31 January 2021, published by Google through the Cloud Public Datasets Program. Crawler sessions excluded throughout, for the reasons set out in part 1.

Next in the series: we tested the inheritance idea — it recovered an eighth of the gap, and not for the reason we expected. Related: Customer value becomes predictable after 90 days, part 2 of our customer-lifetime-value series. All articles.

Start Your Data Transformation Journey

Discover practical, scalable solutions tailored to your business priorities.