Skip to main content

Overview

The defineDiscount() function defines a discount or coupon code that customers can apply at checkout. It’s an identity function that provides type inference and autocomplete while returning the input as-is.

Function Signature

function defineDiscount<T extends DiscountDef>(config: T): T

Type Parameters

T
T extends DiscountDef
The discount configuration type. Must extend DiscountDef.

Parameters

config
DiscountDef
required
The discount configuration object.

Returns

config
T
The same configuration object passed in, with full type inference preserved.

Usage

Percentage Discount - One Time

import { defineDiscount } from "@revstack/core";

export const welcome = defineDiscount({
  code: "WELCOME20",
  name: "New Customer Welcome - 20% Off First Month",
  type: "percent",
  value: 20,
  duration: "once",
  max_redemptions: 1000,
  expires_at: "2024-12-31T23:59:59Z",
});

Percentage Discount - Forever

import { defineDiscount } from "@revstack/core";

export const nonprofit = defineDiscount({
  code: "NONPROFIT50",
  name: "Nonprofit/Education - 50% Off Forever",
  type: "percent",
  value: 50,
  duration: "forever",
  // No expiration for nonprofit discounts
});

Percentage Discount - Repeating

import { defineDiscount } from "@revstack/core";

export const launch = defineDiscount({
  code: "LAUNCH50",
  name: "Launch Special - 50% Off for 3 Months",
  type: "percent",
  value: 50,
  duration: "repeating",
  duration_in_months: 3,
  max_redemptions: 100,
  expires_at: "2024-06-30T23:59:59Z",
});

Fixed Amount Discount

import { defineDiscount } from "@revstack/core";

export const tenOff = defineDiscount({
  code: "SAVE10",
  name: "$10 Off First Month",
  type: "amount",
  value: 1000, // $10.00 in cents
  duration: "once",
  max_redemptions: 500,
});

Plan-Specific Discount

import { defineDiscount } from "@revstack/core";

export const enterpriseTrial = defineDiscount({
  code: "ENTERPRISE_TRIAL",
  name: "Enterprise Trial - 30% Off for 6 Months",
  type: "percent",
  value: 30,
  duration: "repeating",
  duration_in_months: 6,
  applies_to_plans: ["enterprise"], // Only for enterprise plan
});

Black Friday Campaign

import { defineDiscount } from "@revstack/core";

export const blackFriday = defineDiscount({
  code: "BLACKFRIDAY_2024",
  name: "Black Friday 2024 - 40% Off Yearly Plans",
  type: "percent",
  value: 40,
  duration: "once",
  applies_to_plans: ["pro", "business"], // Only yearly intervals
  max_redemptions: 250,
  expires_at: "2024-11-30T23:59:59Z",
});

Partner/Referral Discount

import { defineDiscount } from "@revstack/core";

export const partner = defineDiscount({
  code: "PARTNER_ACME",
  name: "Acme Corp Partnership - 25% Off Forever",
  type: "percent",
  value: 25,
  duration: "forever",
  // No max_redemptions for partner codes
});

Complete Configuration

import { defineConfig, defineDiscount } from "@revstack/core";

export default defineConfig({
  features: { /* ... */ },
  plans: { /* ... */ },
  coupons: [
    defineDiscount({
      code: "WELCOME20",
      name: "Welcome - 20% Off",
      type: "percent",
      value: 20,
      duration: "once",
      max_redemptions: 1000,
    }),
    defineDiscount({
      code: "LAUNCH50",
      name: "Launch Special - 50% Off 3 Months",
      type: "percent",
      value: 50,
      duration: "repeating",
      duration_in_months: 3,
      expires_at: "2024-12-31T23:59:59Z",
    }),
    defineDiscount({
      code: "SAVE10",
      name: "$10 Off",
      type: "amount",
      value: 1000,
      duration: "once",
    }),
  ],
});

Discount Types

Percentage Discount

Reduces the price by a percentage:
{
  type: "percent",
  value: 25, // 25% off
}

// $100/month plan → $75/month with discount

Amount Discount

Reduces the price by a fixed amount:
{
  type: "amount",
  value: 1000, // $10.00 off (in cents)
}

// $100/month plan → $90/month with discount

Duration Options

Once

Applied to the first invoice only:
{ duration: "once" }

// Month 1: $80 (with 20% discount)
// Month 2+: $100 (regular price)

Forever

Applied to every invoice indefinitely:
{ duration: "forever" }

// Every month: $80 (with 20% discount)

Repeating

Applied for a specific number of billing cycles:
{
  duration: "repeating",
  duration_in_months: 3,
}

// Months 1-3: $80 (with 20% discount)
// Month 4+: $100 (regular price)

Best Practices

Naming Conventions

  • Use uppercase for code (e.g., “LAUNCH50”, “SAVE10”)
  • Use descriptive names that include the offer (e.g., “Launch Special - 50% Off”)

Expiration

  • Always set expires_at for promotional campaigns
  • Omit expires_at for permanent partner/nonprofit codes

Redemption Limits

  • Set max_redemptions for limited-time promotions
  • Omit max_redemptions for evergreen codes

Plan Restrictions

  • Use applies_to_plans for plan-specific offers
  • Omit to allow discount on all plans

Source

Location: packages/core/src/define.ts:88-90

Build docs developers (and LLMs) love