Unable to sync data between pages using session storage in Wix

Question

How can I ensure session storage data is reliably synchronized across pages in Wix, especially when navigating rapidly between pages?


Product

Wix Editor (with session storage and navigation).


What are you trying to achieve?

I am trying to pass product-specific data (like SKU) from a product listing page to an individual product details page. The SKU is stored in session storage on the product page and retrieved on the individual product page. The goal is to reliably sync the SKU, even when users navigate quickly between pages.


What have you already tried?

  1. Used wix-storage-frontend to store and retrieve the SKU in session storage.
  2. Added delays before navigation to allow session storage to update.
  3. Implemented a retry mechanism on the receiving page to fetch the SKU from session storage.
  4. Tested with query parameters as a fallback method when session storage fails.
  5. Validated using console logs that the SKU is stored and cleared correctly.

Despite these efforts, session storage sometimes retains an outdated value or fails to persist the updated SKU before navigation completes.


Additional Information

  • Logs show that the SKU from session storage works correctly during the first navigation but often fails on subsequent navigations.
  • Delays (e.g., 800ms) were added before navigating to ensure the data is updated in session storage, but this only resolves the issue intermittently.
  • Query parameters have been added as a fallback, but synchronization issues persist when session storage is involved.
  • Would like guidance on best practices or potential alternatives for reliable data synchronization between pages in Wix.

product page code

import { session } from "wix-storage-frontend";
import wixLocationFrontend from "wix-location-frontend";

$w.onReady(() => {
    $w("#Section1Repeater1").onItemReady(($item, itemData) => {
        $item("#Section1RepeaterItem1Button1").onClick(async () => {
            const productId = itemData.sku; // Get SKU of the selected product

            // Check if there's an existing SKU in session storage
            const existingSKU = session.getItem("selectedSKU");
            if (existingSKU) {
                console.log("Existing SKU found in session storage:", existingSKU);
                session.removeItem("selectedSKU"); // Clear the existing SKU
                console.log("Cleared existing SKU from session storage.");
            } else {
                console.log("No existing SKU in session storage.");
            }

            // Save the new SKU to session storage
            session.setItem("selectedSKU", productId);
            console.log("New SKU stored in session storage:", productId);

            // Add a delay to ensure storage write
            await new Promise(resolve => setTimeout(resolve, 800)); // 800ms delay
            const storedSKU = session.getItem("selectedSKU");

            if (storedSKU === productId) {
                console.log("Verified SKU in session storage before navigation:", storedSKU);

                // Navigate to the Individual Product Page
                const navigationURL = `/indiv-product?sku=${productId}`;
                console.log("Navigating to URL:", navigationURL);
                wixLocationFrontend.to(navigationURL);
            } else {
                console.error("Stored SKU does not match the intended product ID. Navigation aborted.");
            }
        });
    });
});

indiv product page

import wixData from "wix-data";
import wixLocationFrontend from "wix-location-frontend";
import { session } from "wix-storage-frontend";

$w.onReady(async () => {
    // Retrieve SKU from query parameters
    const query = wixLocationFrontend.query;
    let productSKU = query.sku;

    if (productSKU) {
        console.log("SKU retrieved from query parameters:", productSKU);
    } else {
        console.warn("No SKU in query parameters. Attempting to retrieve from session storage...");
        productSKU = await retryRetrieveSKU(5, 500); // Retry 5 times with 500ms delay
    }

    if (!productSKU) {
        console.error("No SKU found in query parameters or session storage after retries. Redirecting...");
        wixLocationFrontend.to("/product-page");
        return;
    }

    console.log("Using SKU:", productSKU);

    // Wait for dataset to be ready before filtering
    $w("#dataset1").onReady(() => {
        $w("#dataset1").setFilter(wixData.filter().eq("sku", productSKU))
            .then(() => {
                const currentItem = $w("#dataset1").getCurrentItem();

                if (currentItem) {
                    console.log("Current Item:", currentItem);

                    // Initialize features for the product
                    displayMapForItem(currentItem);
                    setupDynamicCalculator(currentItem);
                    setupAddToQuotationButton(currentItem);

                    // Clear SKU from session storage after successful use
                    if (session.getItem("selectedSKU") === productSKU) {
                        session.removeItem("selectedSKU");
                        console.log("Cleared SKU from session storage.");
                    } else {
                        console.warn("Session storage SKU does not match current SKU. Clearing anyway...");
                        session.removeItem("selectedSKU");
                    }
                } else {
                    console.error("No product found for the given SKU.");
                }
            })
            .catch(error => {
                console.error("Error filtering dataset:", error);
            });
    });
});

/**
 * Retry retrieving SKU from session storage.
 * @param {number} retries - Number of retries allowed.
 * @param {number} delay - Delay between retries in milliseconds.
 * @returns {Promise<string|null>} - SKU value or null if not found.
 */
async function retryRetrieveSKU(retries, delay) {
    let sku = null;
    for (let attempt = 1; attempt <= retries; attempt++) {
        sku = session.getItem("selectedSKU");
        if (sku) {
            console.log(`Retry ${attempt}: Retrieved SKU from session storage: ${sku}`);
            return sku;
        }
        console.log(`Retry ${attempt}: No SKU found. Retrying in ${delay}ms...`);
        await new Promise(resolve => setTimeout(resolve, delay));
    }
    console.error("Failed to retrieve SKU from session storage after retries.");
    return null;
}
1 Like

Why not. just use dynamic pages/presets ?

Add Dynamic Pages with Presets | Help Center | Wix.com.

You can even just add a dynamic page linked to the same cms as an existing repeater and link (button) click action in the repeater to go the the dynamic page.

The nice thing about this is you will not manually need to sync details. It is all done for you since the both link to the same CMS.

Although the one thing you may need to code is the back button on the dynamic page

Hi I had a lot of issues using session storage between pages. Definitely not consistent.
Console log entries showed the value was changed after setItem() was called in one page, yet the next page retrieving it with getItem() had an incorrect value.

This occurs when you force a page change with wixLocation.to() even if you call setItem() to local storage beforehand. 2 solutions.

  1. Use setTimeout() to wait 50 milliseconds before calling wixLocation.to to change page. That might allow the setItem() to finish before page switch shuts everything running down.
    e.g.
    session.setItem(“sku”, sku);
    setTimeout(() => { console.log(“allow pause”); wixLocation.to(‘/newPage’ }, 50 );

Seems you tried that even at 800 ms timeout which is annoying if that didn’t work!

  1. Pass the SKU or whatever else on the URL query line before switching page. e.g.
    wixLocation.to(‘/newPage/?sku=’+sku);
    Once in the new page you can look up the URL variables using wixLocation.query e.g.

    const query = wixLocation.query;
    console.log("URL parameters = ", query);
    if (query) {
    sku = = query[‘sku’];
    console.log(“SKU retrieved =”, sku);
    etc…

I opted for 2) as it fitted for what I needed & I think that’s your workaround. I asked Wix and got Zero in terms of a solution to this problem. session.setItem works fine if not called immediately before a page switch. If the page switch is immediately following setItem the results will be inconsistent as to what gets stored.

hope that helps.

Your product code is excessive snd the logic is off.

You need to reduce it.

It should be as simple as: on item ready, on click set the session then navigate.

You don’t need to clear the existing session variable. Simply by setting the new variable it will override the old one.