DocumentationDocumentation
Talk2Sync Documentation
User Documentation
Connector APIs
  • English
  • Español
Talk2Sync Documentation
User Documentation
Connector APIs
  • English
  • Español
  • User Guide Portal & API Documentation
  • User-documentation

    • User Documentation
    • Guide

      • User Guide: Introduction
      • Core Concepts
    • Talk2sync

      • Connection Buttons
      • Color Coding System
      • Issues and Alerts
      • Command Filters
      • Deleted Information Still Appears: How to Remove It
      • Deletions
    • Conexiones

      • Connection Settings
    • Fields

      • Time Based Sync
      • Data Governance
      • Special and Extra Fields
    • Productos

      • Product Fields
      • Equivalences
      • Product Search
      • Link / Unlink Products
    • Ventas

      • Fields
      • Equivalences
      • Sales Search
      • No SKU (Missing SKU)
    • Reports

      • Product Export
      • Sales Report
    • Faq

      • Amazon

        • Amazon Barcode Requirements
        • Amazon Catalog Discrepancies and ASIN Mismatches
        • Amazon Manufacturer Requirements
        • New ASIN Creation Errors and Invalid Attribute Values
        • Talk2sync, SKUs, and Product Identifiers
        • Amazon Variation Templates
      • Mercadolibre

        • Mercado Libre Official Stores
        • Mercado Libre Locations and Geographic Attributes
        • Mercado Libre Pick-up in Store
        • Mercado Libre Extra Attributes
        • Mercado Libre Image Processing and Synchronization
        • Mercado Libre Seller Unable to List Error
      • Linio

        • Linio Brand Not Registered Error
        • Linio Physical Dimensions and Weight Requirements
  • Connector APIs

    • Connector APIs
    • Quick-start

      • Introduction & Requirements
      • Add Connection
      • Configure Connection
      • Generate Keys
      • Test Your Integration
    • Webhooks

      • Webhooks API
      • Catalog

        • Webhooks: List Products
        • Webhooks: List Product by ID
        • Webhooks: Add/Update Product
      • Sales

        • Webhooks: List Orders
        • List Order by ID
        • Add/Update Order
    • Reverse-connections

      • Reverse Connections
      • Implementation-states

        • Implementation
        • Query Implementation: Products and Orders
        • Store Implementation: Products and Orders
        • Sleep and Timeouts
      • Protocol

        • Protocol
        • Overview
        • Product Upload
        • Order Upload
        • Product Download
        • Order Download
      • Rest-calls

        • REST Calls
        • Fetching-changes

          • Fetching Changes REST Calls
          • Ask if Fetching
          • Catalog

            • Push Products Page
            • Set Finish Product Pushes
          • Sales

            • Push Orders Page
            • Set Finish Order Pushes
            • Set Finish All Pushes
        • Pulling-changes

          • Pulling Changes REST Calls
          • Ask if Pulling
          • Catalog

            • Get Next Product to Pull
            • Pull Products Page
            • Notify Product Storage Success
            • Notify Product Storage Failure
            • Set Finish Product Download
          • Sales

            • Get Next Order to Pull
            • Pull Orders Page
            • Notify Order Storage Success
            • Notify Order Storage Failure
            • Set Finish Order Download
            • Transact Finish Pull

Webhooks: List Product by ID

Overview

The List Product by ID webhook provides an optimized two-stage approach for retrieving products. This is useful for performance optimization when you have a large product catalog.

Instead of returning full product details with every request, you can return a lightweight list of product IDs and their last_updated timestamps. Talk2sync uses this information to determine which products have changed and only requests full details for those that need updating.

Two-Stage Retrieval Process

Stage 1: List Product IDs (Lightweight Index)

Request:

Talk2sync first requests a lightweight index of all your products:

Numeric Offset Pagination

GET https://www.example.com/your/endpoint/url?offset=0&sortorder=desc&jobid=123
T2SKey: {{API_KEY}}

Cursor-Based Pagination

GET https://www.example.com/your/endpoint/url?next=YXNkaWhhc3BvZGhpYXM&sortorder=desc&jobid=123
T2SKey: {{API_KEY}}

Response:

Return a lightweight list with only essential information:

{
  "paging": {
    "pageSize": 20,
    "itemsTotal": 2,
    "offset": 0
  },
  "products": [
    {
      "_id": "100004777",
      "sku": "100004777",
      "last_updated": 1517360038797
    },
    {
      "_id": "100004778",
      "sku": "100004778",
      "last_updated": 1517360038800
    }
  ]
}

Response Fields:

FieldTypeDescription
_idstringUnique product identifier (required)
skustringProduct SKU/code
last_updatedintegerUnix timestamp (milliseconds) of last modification

Stage 2: Retrieve Full Product Details (On Demand)

Request:

When Talk2sync determines a product needs updating, it requests the full product details using the product ID:

GET https://www.example.com/your/endpoint/url?id=100004777&jobid=123
T2SKey: {{API_KEY}}

Request Parameters:

ParameterTypeDescriptionRequired
idstringProduct ID to retrieve full details for✓ Yes
jobidintegerUnique identifier for this sync job✓ Yes
T2SKeyheaderYour security key✓ Yes

Response:

Return the complete product details:

{
  "_id": "100004777",
  "sku": "100004777",
  "last_updated": 1517360038797,
  "title": "EON618S JBL SUBWOOFER 18\" AMPLIFICADO",
  "url": "",
  "brand": "",
  "mpn": "",
  "model": "",
  "description": "JBL Premium Transducers",
  "variations": [
    {
      "availabilities": [
        {
          "tag": "default",
          "quantity": 50
        }
      ],
      "prices": [
        {
          "tag": "default",
          "currency": "USD",
          "number": 1060.51
        }
      ],
      "images": [
        {
          "url": "https://www.example.com/13080-thickbox_default/eon618s-jbl-subwoofer-18-amplificado-.jpg"
        }
      ],
      "videos": [
        {
          "url": ""
        }
      ],
      "barcode": "",
      "size": "",
      "color": "",
      "variationid": ""
    }
  ],
  "properties": [
    {
      "extraattributes": {
        "promociones": "",
        "status": "",
        "condicion_venta": "",
        "peso": "",
        "relacionados": "",
        "custom_01": "",
        "custom_02": "1",
        "custom_03": ""
      }
    }
  ]
}

Complete Field Reference

Lightweight Product Object (Stage 1)

FieldTypeDescription
_idstringUnique product identifier (required)
skustringProduct SKU/code
last_updatedintegerUnix timestamp (milliseconds) of last modification

Full Product Object (Stage 2)

FieldTypeDescription
_idstringUnique product identifier (required)
skustringProduct SKU/code
last_updatedintegerUnix timestamp (milliseconds) of last modification
titlestringProduct name/title
urlstringProduct URL in your store
brandstringProduct brand
mpnstringManufacturer Part Number
modelstringProduct model
descriptionstringDetailed product description
variationsarrayArray of product variations
propertiesarrayArray of custom properties/attributes

Variation Object (Stage 2 Only)

FieldTypeDescription
variationidstringUnique variation identifier
sizestringSize attribute
colorstringColor attribute
barcodestringBarcode/EAN code
availabilitiesarrayStock information by location
pricesarrayPricing information
imagesarrayProduct images
videosarrayProduct videos

Availability Object

FieldTypeDescription
tagstringLocation identifier (e.g., "default", "warehouse_1")
quantityintegerAvailable quantity

Price Object

FieldTypeDescription
tagstringPrice tier identifier (e.g., "default", "wholesale")
currencystringISO 4217 currency code (e.g., "USD", "MXN")
numbernumberPrice value

Implementation Example (Node.js/Express)

// Stage 1: List product IDs with last_updated timestamps
app.get('/api/products', (req, res) => {
  const { offset = 0, next, sortorder = 'desc', jobid } = req.query;
  const apiKey = req.headers['t2skey'];

  // Validate API key
  if (apiKey !== process.env.TALK2SYNC_KEY) {
    return res.status(401).json({ error: 'Unauthorized' });
  }

  try {
    // Fetch lightweight product data (IDs and timestamps only)
    const allProducts = fetchProductsLightweight(sortorder);
    
    const pageSize = 20;
    const startIndex = parseInt(offset) || 0;
    const paginatedProducts = allProducts.slice(startIndex, startIndex + pageSize);

    const response = {
      paging: {
        pageSize: paginatedProducts.length,
        itemsTotal: allProducts.length,
        offset: startIndex
      },
      products: paginatedProducts.map(product => ({
        _id: product.id,
        sku: product.sku,
        last_updated: new Date(product.updatedAt).getTime()
      }))
    };

    res.json(response);
  } catch (error) {
    console.error('Error fetching products:', error);
    res.status(500).json({ error: 'Internal Server Error' });
  }
});

// Stage 2: Retrieve full product details by ID
app.get('/api/products', (req, res) => {
  const { id, jobid } = req.query;
  const apiKey = req.headers['t2skey'];

  // Validate API key
  if (apiKey !== process.env.TALK2SYNC_KEY) {
    return res.status(401).json({ error: 'Unauthorized' });
  }

  try {
    // If ID parameter is present, return full product details
    if (id) {
      const product = fetchProductById(id);
      
      if (!product) {
        return res.status(404).json({ error: 'Product not found' });
      }

      const response = {
        _id: product.id,
        sku: product.sku,
        last_updated: new Date(product.updatedAt).getTime(),
        title: product.name,
        url: product.url,
        brand: product.brand,
        mpn: product.mpn,
        model: product.model,
        description: product.description,
        variations: product.variations.map(v => ({
          variationid: v.id,
          size: v.size || "",
          color: v.color || "",
          barcode: v.barcode || "",
          availabilities: v.stocks.map(s => ({
            tag: s.location || "default",
            quantity: s.quantity
          })),
          prices: v.prices.map(p => ({
            tag: p.tier || "default",
            currency: p.currency || "USD",
            number: p.value
          })),
          images: v.images.map(img => ({ url: img })),
          videos: v.videos.map(vid => ({ url: vid }))
        })),
        properties: [{
          extraattributes: product.customFields || {}
        }]
      };

      res.json(response);
    }
  } catch (error) {
    console.error('Error fetching product:', error);
    res.status(500).json({ error: 'Internal Server Error' });
  }
});

How Talk2sync Uses This Approach

  1. First Request: Talk2sync calls your endpoint without an id parameter to get the lightweight index
  2. Comparison: Talk2sync compares the last_updated timestamp with what it has stored
  3. Selective Requests: For products with newer last_updated values, Talk2sync makes individual requests with the id parameter
  4. Bandwidth Optimization: Only products that have actually changed trigger full data requests

Performance Benefits

AspectBenefit
BandwidthReduced by only fetching full details for changed products
Sync SpeedMuch faster initial index comparison
Database LoadLower load from fewer full product fetches
ScalabilityHandles large catalogs efficiently

When to Use This Approach

✓ Use when:

  • Your catalog has 10,000+ products
  • Products are updated infrequently
  • You want to minimize bandwidth usage
  • Response time is critical

✗ Avoid when:

  • Your catalog is small (< 1,000 products)
  • Most products change frequently
  • Bandwidth is not a concern
  • Simplicity is more important than optimization

Response Status Codes

StatusMeaningAction
200 OKData retrieved successfullyTalk2sync processes the response
400 Bad RequestInvalid parametersCheck your request parameters
401 UnauthorizedInvalid or missing API keyVerify your security key
404 Not FoundProduct ID does not existCheck the product ID
500 Internal Server ErrorServer errorCheck your server logs

Pagination Guidelines

Stage 1: List Endpoints

Use the same pagination strategies as List Products:

  • Numeric Offset: For small to medium datasets
  • Cursor-Based: For large or frequently changing datasets

Stage 2: Single Product Request

No pagination needed—this endpoint always returns a single complete product.


Best Practices

✓ Do:

  • Return lightweight data in Stage 1 (IDs and timestamps only)
  • Keep last_updated timestamps accurate and up-to-date
  • Validate the API key on every request
  • Return 404 if a requested product ID doesn't exist
  • Cache full product details when possible

✗ Don't:

  • Return full product details in Stage 1 (defeats the purpose)
  • Return incomplete data in Stage 2
  • Include sensitive information in responses
  • Ignore the sorting parameter in Stage 1

Comparison: List Products vs List Product by ID

FeatureList ProductsList Product by ID
Use CaseSmall catalogs, simple integrationsLarge catalogs, performance optimization
Stage 1 ResponseFull product detailsLightweight (ID + timestamp)
Stage 2 ResponseN/AFull product details (on demand)
Bandwidth UsageHigh (all details always sent)Low (only changed products fetched)
ComplexitySimpleMore complex (two endpoints)
Best For< 1,000 products10,000+ products

Related Webhooks

  • List Products
  • Add/Update Product

Related Documentation

  • Quick Start: Generate Keys
  • Webhooks Overview
Last Updated: 8/28/26, 12:58 AM
Prev
Webhooks: List Products
Next
Webhooks: Add/Update Product