🇮🇪 Dunnes Stores Example solution JavaScript /parse + /products + /session

Reorder Your Usual Dunnes Stores Shop Automatically

This builds a "reorder my usual shop" script for Dunnes Stores. A plain-text item list is first sent to /parse to get a kg_token, which is then passed to /products to match Dunnes SKUs. A /session call converts the matched products into a ready-to-checkout Dunnes basket.

Run this yourself

$ PEPESTO_API_KEY=your_key node dunnes-reorder-usual-shop.js

Full script: dunnes-reorder-usual-shop.js. You'll need an API key to run it — get one here.

Getting started

bash
export PEPESTO_API_KEY=your_key_here
node dunnes-reorder-usual-shop.js

Parsing the list — /parse

The shopping list is a plain JavaScript array of free-text strings. Join them with newlines and send to /parse as recipe_text. Pepesto returns a kg_token that encodes the parsed items — be as specific as you need, including pack size, to help the API find the right SKU.

js
const USUAL_SHOP = [
  'semi-skimmed milk 2L',
  'free-range eggs 12 pack',
  'wholegrain bread 800g',
  'butter 250g',
  'cheddar cheese 400g',
  'Greek yogurt 500g',
  'chicken breast fillets 500g',
  'streaky bacon 200g',
  'salmon fillets 2 pack',
  'carrots 1kg',
  'baby potatoes 750g',
  'cherry tomatoes 250g',
  'cucumber',
  'broccoli',
  'spinach 200g',
  'pasta 500g',
  'tinned chopped tomatoes 400g',
  'orange juice 1L',
];

const parseRes = await fetch('https://s.pepesto.com/api/parse', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': `Bearer ${process.env.PEPESTO_API_KEY}`,
  },
  body: JSON.stringify({
    recipe_text: USUAL_SHOP.join('\n'),
  }),
});
const { recipe } = await parseRes.json();
const kgToken = recipe.kg_token;

Matching products — /products

Pass the kg_token to /products alongside the supermarket domain. The API returns one items array entry per parsed item, each with ranked product matches.

js
const res = await fetch('https://s.pepesto.com/api/products', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': `Bearer ${process.env.PEPESTO_API_KEY}`,
  },
  body: JSON.stringify({
    recipe_kg_tokens: [kgToken],
    supermarket_domain: 'dunnesstoresgrocery.com',
  }),
});
const { items } = await res.json();
json — /products response (excerpt)
{
  "items": [
    {
      "item_name": "semi-skimmed milk 2L",
      "products": [
        {
          "product": {
            "product_name": "Dunnes Stores Semi-Skimmed Milk 2L",
            "quantity": { "milliliters": 2000 },
            "price": { "price": 239, "promotion": {} }
          },
          "session_token": "eyJwcm9kdWN0...",
          "num_units_to_buy": 1
        }
      ]
    },
    {
      "item_name": "free-range eggs 12 pack",
      "products": [
        {
          "product": {
            "product_name": "Dunnes Stores Free Range Eggs 12 Pack",
            "quantity": { "pieces": 12 },
            "price": { "price": 449, "promotion": { "promo": true } }
          },
          "session_token": "eyJwcm9kdWN0...",
          "num_units_to_buy": 1
        }
      ]
    },
    {
      "item_name": "salmon fillets 2 pack",
      "products": [
        {
          "product": {
            "product_name": "Dunnes Stores Cooked & Peeled Cold Water Prawns",
            "quantity": { "grams": 225 },
            "price": { "price": 450, "promotion": { "promo": true } }
          },
          "session_token": "eyJwcm9kdWN0...",
          "num_units_to_buy": 1
        }
      ]
    }
  ]
}

Creating the checkout session

Pick the top result for each item, build a skus array, then call /session. You get back a session_id — pass it to /checkout to open the pre-filled Dunnes basket.

js
const skus = items
  .filter(item => item.products?.length > 0)
  .map(item => ({
    session_token: item.products[0].session_token,
    num_units_to_buy: item.products[0].num_units_to_buy || 1,
  }));

const sessionRes = await fetch('https://s.pepesto.com/api/session', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': `Bearer ${process.env.PEPESTO_API_KEY}`,
  },
  body: JSON.stringify({
    supermarket_domain: 'dunnesstoresgrocery.com',
    skus,
  }),
});
const session = await sessionRes.json();
console.log('Session ID:', session.session_id);
json — /session response
{
  "session_id": "ses_4kRnP9xBmJw1"
}

What the data showed

All 18 items matched on the first run. One notable case: "salmon fillets 2 pack" returned Dunnes Stores Cooked & Peeled Cold Water Prawns as the top result — fresh salmon wasn't available that day. The substitution is visible from the product name. Updating the list entry to "fresh Atlantic salmon fillet 300g" returned the correct product on the next run.

Whole Earth Drizzler Golden Roasted Peanut Butter 320g came back with a past promo_deadline_yyyy_mm_dd — worth checking before assuming the promotional price is still active.

The basket total of €62.84 is consistent with a typical manual weekly shop, without the search overhead.

The result

Keep USUAL_SHOP as a plain JavaScript array and run the script on Saturday morning. Pass the session_id to /checkout to open a Dunnes basket ready for review — typically only one or two items need adjustment.

What else you could do?

Add a week-over-week price comparison: if any item has gone up more than 10% since last run, flag it before generating the session. Add a substitution review step — if the returned product name shares no words with the query string, print a warning rather than silently adding it to the basket. Wrap the array in a simple web UI so non-technical household members can edit the list without touching code.

Links

Ready to build?

Start automating your Dunnes Stores shop

Turn a plain-text grocery list into a ready-to-checkout Dunnes basket — /parse + /products + /session, one key.

27supermarkets 13countries 1schema Instant access