Skip to main content

PLP Badges

Badges displayed on Product Listing Pages (PLPs) are managed through the static-assets repository and rendered via SearchSpring's search results.

Implementationโ€‹

Badge Generationโ€‹

Badges are generated in the sharedPlugin function within src/shared/shared/plugins/shared.js. The plugin runs during the afterStore hook and processes each search result to determine which badge to display.

// Badge is attached to each result
result.custom.badge = {
id: 'new',
label: 'New Arrival',
class: 'icon-tag new-arrival-tag',
bgColor: undefined,
color: undefined
};

Badge Renderingโ€‹

Badges are rendered in src/shared/result/Result.jsx:

{result.custom.badge && (
<div className={`grid gap-1 ${result.custom.badge.class}`}>
<span
style={{
backgroundColor: result.custom.badge.bgColor,
color: result.custom.badge.color
}}
>
{result.custom.badge.label}
</span>
</div>
)}

Badge Display Limitsโ€‹

Badge TypeMax CountLocationBehavior
Text Badge1Below product detailsFirst matching condition wins
Image Badge1Top-left of product imageShips Now or Personalize (same position)
Total21 text + 1 image badge

Text Badges (Priority System)โ€‹

Only one Text Badge displays per product. The first matching condition wins:

PriorityBadgeConditionLabel Example
1EOY Saletags includes 'badge:eoy25clearance'"Extra 30% off with code CHEERS"
2Limited Time Pricess_tags includes 'limitedtimeprice'"Limited Time Price"
3Out of StockNo availability AND no waitlist"Out of Stock"
4WaitlistWaitlist available, no current stock"Waitlist"
5Lightning Dealtags includes 'badge:lightningdeal'"Extra 30% off with VIRALDEAL"
6Promo Tagsss_promo_tags has valueDynamic from promo config
7Discontinuedss_discontinued == 1"Discontinues on MM/DD/YYYY"
8New Luxe Collectiontags_badge includes 'new luxe collection'"New Luxe Collection"
9Best Sellerss_bestseller == 1"Best Seller"
10New Arrivalss_new_arrival == 1"New Arrival"

Image Badgesโ€‹

Image Badges display independently of the Text Badge priority system and are overlaid on the product image (top-left corner). Since both badges share the same position, only one displays at a time.

Ships Now Image Badgeโ€‹

Displays when products have all sizes ready to ship immediately.

Conditions:

  • product_type is 'Bridesmaid Dress'
  • Either:
    • ss_sizes_ready_to_ship is truthy, OR
    • ss_tags includes 'sstempshipsnowallsizesplpbadge'
  • If ss_variants_filtered exists and is empty, badge is hidden

Styling: Gray background (#e8e2e5), positioned on product image

Personalize Image Badgeโ€‹

Displays when a product can be personalized.

Condition: ss_tags includes 'personalizable'

Styling: Gray background (#e8e2e5), positioned on product image

Promo Tag Configurationโ€‹

Promo tags support custom styling per promotion:

const promoTagClassesConfig = {
BMSMGR: 'suite-looks-tag flex items-center text-darkMauve',
BMSMWP: 'tieoneon-tag flex items-center text-darkSeaGlass',
FRIENDSANDFAMILY23: 'icon-tag faf-tag bg-[#d0b8b6]',
IWD23Promo: 'icon-tag iwd-tag bg-[#d0b8b6]',
PERFECTPAIR: 'perfect-pair-tag flex items-center text-brand-errorText',
$49VELVETDRESSES: 'velvet-tag flex items-center text-darkSeaGlass',
};

To add a new promo tag:

  1. Add entry to promoTagClassesConfig with the promo code as key
  2. Define CSS classes for styling
  3. Ensure ss_promo_tags is populated in SearchSpring

Stylingโ€‹

CSS Filesโ€‹

FilePurpose
src/_config/styles/themes/_custom.scssPLP badge styles
src/recommendations/email/styles/_custom.scssEmail badge styles

Text Badge Classesโ€‹

// Base icon tag (used by many Text Badges)
.icon-tag {
border-radius: 9px;
display: flex;
}

// Discontinued badge
.discontinued-tag {
background: #e5b3ac;
}

// Limited time price badge
.limitedprice-tag {
background: #4b5681;
color: #fff;
}

Image Badge Classesโ€‹

// Ships now / Personalize badges (overlaid on image)
// Note: .personliseBadge is the actual class name (typo in codebase)
.ships-now, .personliseBadge {
background: #e8e2e5;
color: #484140;
font-size: 10px;
border-radius: 0 20px 20px 0;
max-width: 75px;
position: absolute;
top: 0;
left: 0;

@media (max-width: 768px) {
font-size: 8px;
max-width: 65px;
}
}

Adding a New Text Badgeโ€‹

  1. Add logic in src/shared/shared/plugins/shared.js:

    // Add condition check in the priority chain
    if (result.attributes.ss_tags?.includes('badge:newbadge')) {
    result.custom.badge = {
    id: 'newbadge',
    label: 'New Badge Label',
    class: 'icon-tag new-badge-tag',
    };
    }
  2. Add styles in src/_config/styles/themes/_custom.scss:

    .new-badge-tag {
    background: #yourcolor;
    color: #textcolor;
    }
  3. Configure SearchSpring to populate the triggering attribute (e.g., ss_tags)

Discontinued Date Displayโ€‹

When a product has a discontinuation date, the Text Badge displays the date:

if (discontinuationDate) {
const date = new Date(discontinuationDate);
badge.label = `Discontinues on ${date.toLocaleDateString('en-US')}`;
}

Badge Data Structureโ€‹

Badges are attached to each search result with the following structure:

interface Badge {
id: string; // Unique identifier (e.g., 'lightningdeal', 'discontinued')
label: string; // Display text
class: string; // CSS classes (Tailwind + custom)
bgColor?: string; // Optional inline background color
color?: string; // Optional inline text color
}

Data Sources (SearchSpring)โ€‹

AttributeTypePurpose
tagsArrayRaw Shopify product tags (e.g., 'badge:eoy25clearance', 'badge:lightningdeal')
ss_tagsArraySearchSpring-processed tags (e.g., 'personalizable', 'limitedtimeprice')
ss_promo_tagsJSONPromo tag information
ss_availableBooleanStock availability
ss_waitlistBooleanWaitlist availability
ss_discontinuedNumberDiscontinued status (1 = discontinued)
ss_bestsellerNumberBest seller flag
ss_new_arrivalNumberNew arrival flag
ss_sizes_ready_to_shipBooleanShips now status
tags_badgeStringCustom badge tags
  • static-assets/src/shared/shared/plugins/shared.js - Badge generation logic
  • static-assets/src/shared/result/Result.jsx - PLP rendering
  • static-assets/src/recommendations/email/Email.jsx - Email rendering
  • static-assets/src/_config/styles/themes/_custom.scss - PLP styles