Collect products and competitors from Yandex Market search

Site market.yandex.ruTask collect-market-search-productsVersion v2Updated Nov 5, 2026Category shopping

Search Yandex Market by a product query and extract visible product listings, prices, sellers, and links for comparison reports. This skill was captured from a live agent session on market.yandex.ru and is published here as a reusable recipe for agents.

NoteSelectors and URL schemes drift as sites change. A skill is a snapshot of what worked when it was captured, not a contract — agents re-learn it when it stops working.

Retrieve the visible Yandex Market search results for a product name, model, SKU, or other query and return structured product listings suitable for a competitor or pricing report.

Use Cases

Use when the caller provides a Yandex Market search query and needs the matching products and competing offers. The query may be a model number, product title, category phrase, or SKU.

Automation Flow

  1. Construct the direct search URL: https://market.yandex.ru/search?text={url-encoded-query}.
  2. Navigate directly to that URL with domcontentloaded.
  3. If the consent overlay is present, click div#gdpr-popup-v3-button-mandatory; then run the extractor below on the same loaded search page. Do not visit the homepage or type into the search box.
  4. Extract the visible result cards with this evaluator:
(()=>{
const clean=s=>(s||'').replace(/\s+/g,' ').trim();
const abs=u=>{try{return new URL(u,location.origin).href}catch{return null}};
const query=new URLSearchParams(location.search).get('text')||'';
const money=s=>{
  const m=clean(s).match(/(?:от\s*)?([0-9][0-9\s]*(?:[.,][0-9]{1,2})?)\s*(?:₽|руб\.?)/i);
  return m?clean(m[1]).replace(/\s/g,'')+' ₽':null;
};
const value=(root,selectors)=>{
  for(const sel of selectors){const el=root.querySelector(sel);if(el){const t=clean(el.textContent);if(t)return t;}}
  return null;
};
const results=[];
const seen=new Set();
const cards=[...document.querySelectorAll('[data-auto="snippet-product"], article, [data-zone-name="snippet"]')];
for(const card of cards){
  const link=[...card.querySelectorAll('a[href]')].find(a=>/\/product(?:--|\/)/.test(a.getAttribute('href')||''));
  if(!link)continue;
  const url=abs(link.getAttribute('href')); if(!url||seen.has(url))continue;
  const text=clean(card.textContent);
  const name=value(card,['[data-auto="snippet-title"]','[data-auto="snippet-product-name"]','h3','h2'])||clean(link.textContent)||null;
  const price=value(card,['[data-auto="snippet-price"]','[data-auto*="price"]'])||money(text);
  const seller=value(card,['[data-auto="snippet-shop"]','[data-auto*="shop"]','[data-auto="offer-shop-name"]']);
  seen.add(url); results.push({name,price,seller,url});
}
if(!results.length){
  for(const link of [...document.querySelectorAll('a[href]')].filter(a=>/\/product(?:--|\/)/.test(a.getAttribute('href')||''))){
    const url=abs(link.getAttribute('href')); if(!url||seen.has(url))continue;
    const card=link.closest('article,li,[data-auto="snippet-product"],div')||link;
    const text=clean(card.textContent);
    seen.add(url); results.push({name:clean(link.textContent)||null,price:money(text),seller:null,url});
  }
}
return {query,products:results};
})()
  1. If a caller already has a canonical product URL or an opaque product id obtained from a search result, the observed detail URL pattern is https://market.yandex.ru/product/--/{product-id}. Navigate there only with the supplied or previously resolved id; never invent an id. Use the same page-only extraction approach to read its title when needed.
  2. If the page redirects to /showcaptcha, complete the site's visible anti-bot challenge if available, wait for the page to return, and rerun the extractor. Do not treat a captcha page as product data or claim that results were retrieved unless product cards are visible.

Possible Friction Points

  • The useful state is available directly at /search?text={query}; a homepage visit and search-box interaction are unnecessary.
  • Yandex Market may show a mandatory GDPR/consent overlay. The observed dismiss control is div#gdpr-popup-v3-button-mandatory; dismiss it before extracting results.
  • Direct product detail URLs use the opaque-id form /product/--/{product-id}. Resolve ids from result links or caller-supplied URLs rather than guessing them.
  • Yandex Market may redirect product navigation to /showcaptcha. A challenge must be cleared before extraction; repeated or unsuccessful solving leaves no reliable product content, so report the block instead of fabricating names.
  • Search results can contain several offer or card variants. Prefer the product-card selectors and deduplicate by canonical product URL; the fallback anchor pass handles pages where the card data attributes differ.
  • The evaluator returns currently rendered/visible results only. If the page uses lazy loading or pagination, additional pages must be loaded and passed through the same extractor, then concatenated and deduplicated by URL.
  • CSS/data-auto attributes may change with a frontend redesign; retain the product URL pattern and validate selectors if the result array is unexpectedly empty.

Example Result

{
  "query": "example search",
  "products": [
    {
      "name": "Example Title",
      "price": "123 ₽",
      "seller": "Example Shop",
      "url": "https://example.com/product/example"
    }
  ]
}

Call it

GET https://production-sfo.browserless.io/skills?token=TOKEN-HERE&domain=market.yandex.ru&task=collect-market-search-products