InsightHireHelp Center

Billing

Stripe subscriptions, plan tiers, usage limits, payment methods, and invoices.

Settings → Billing (/dashboard/settings/billing) is restricted to Organization Admins. It connects your tenant to Stripe for subscription management, usage tracking, and invoice history.

Subscription plans

Public self-serve plans (via trpc.billing.listPublicPlans):

PlanTypical priceCandidates / monthHighlights
TRIALFree50 (static cap)Time-limited evaluation
STARTER$499/mo50 (DB) / 100 (static fallback)Core video screening, basic analytics
PROFESSIONAL$1,499/mo200ATS integrations, advanced analytics, priority support
ENTERPRISE$3,999/moUnlimited (-1)White-label, custom workflows, dedicated CSM
ENTERPRISE_PLUSCustomUnlimitedSales-assigned; same limits as Enterprise

Prices and candidate limits live in subscription_plans (seeded from plan-config.ts defaults). Platform admins can override limits per plan from InsightHire Admin.

Feature highlights by plan

Starter includes: video pre-screening, automated scoring, custom questions, basic analytics, email support.

Starter excludes: ATS integrations, white-label branding.

Professional adds: ATS integrations (Greenhouse, etc.), team collaboration, advanced analytics, priority support, dedicated onboarding.

Enterprise adds: white-label branding, unlimited screenings, custom integrations, dedicated success manager, 24/7 support, SLA, SOC 2, custom MSAs.

Usage limits

getMergedPlanLimits combines DB candidatesLimit with static caps:

DimensionTRIALSTARTERPROFESSIONALENTERPRISE
Candidates / month50100*500*Unlimited
Team members35UnlimitedUnlimited
Video minutes / month1003001,500Unlimited
Storage (GB)51050Unlimited

*Candidate cap follows subscription_plans.candidatesLimit when DB row exists (Starter 50, Professional 200 in marketing defaults).

The Usage dashboard component on the billing page shows current-period consumption vs limits. Approaching limits triggers in-app banners (trial-banner component links back to billing).

Enforcement

When limits are exceeded:

  • New candidate screenings may block or warn depending on plan enforcement hooks
  • Trial expiration redirects to /dashboard/settings/billing?expired=true
  • ATS integration access checks plan tier (enforceATSAccess)

Stripe integration flows

Billing uses Stripe Checkout, Customer Portal, SetupIntents, and in-app PaymentIntents.

Upgrade paths

flowchart TD
  A[Admin clicks Upgrade] --> B{Existing Stripe sub?}
  B -->|Yes| C[updateSubscriptionPlan — proration]
  B -->|No| D{Saved payment method?}
  D -->|Yes| E[subscribeWithSavedPaymentMethod]
  E --> F{Requires 3DS?}
  F -->|Yes| G[confirmCardPayment + finalizeInAppSubscription]
  F -->|No| H[Subscription active]
  D -->|No| I[createCheckoutSession → redirect]

Payment methods

  • Add cardcreateSetupIntent opens Stripe Elements modal (AddCardModal)
  • Default cardsetDefaultPaymentMethod
  • Remove cardremovePaymentMethod (blocked if last method on active sub)

Billing portal

Manage subscription opens Stripe Customer Portal (createBillingPortalSession) for:

  • Cancel at period end
  • Update payment method (alternative to in-app card UI)
  • View Stripe-hosted invoices

Invoices

listInvoices returns recent Stripe invoices with expandable line items on the billing page. PDF links open Stripe-hosted documents.

Query parameters

ParamMeaning
?success=trueCheckout returned successfully — refetch subscription
?canceled=trueCheckout abandoned
?expired=trueTrial expired banner

Environment requirements

VariablePurpose
STRIPE_PUBLISHABLE_KEYWeb Stripe.js
STRIPE_SECRET_KEYAPI Stripe SDK
STRIPE_PRICE_*_MONTHLYPrice IDs for Checkout
Stripe webhooksSync subscription status → org record

Missing publishable key shows an alert when adding cards.

Org record fields

Subscription state on organizations:

  • subscriptionPlanTRIAL, STARTER, PROFESSIONAL, ENTERPRISE, ENTERPRISE_PLUS
  • subscriptionStatus — active, trialing, past_due, canceled, etc.
  • Stripe customer and subscription IDs (internal)

Webhooks keep these in sync after Checkout or portal changes.

Platform admin overrides

InsightHire platform admins can:

  • Set plan without Stripe (sales-assigned Enterprise)
  • Override candidatesLimit on subscription_plans rows
  • Extend trial from org detail in admin

Customer self-serve changes still flow through Stripe when a customer record exists.

Troubleshooting

SymptomAction
Upgrade button does nothingCheck Stripe keys; browser console for API errors
Past dueUpdate payment method; check Stripe dashboard
Usage seems wrongUsage dashboard refreshes post-webhook — wait ~30s
ATS blocked on ProfessionalConfirm subscriptionPlan synced; Greenhouse requires Professional+
Proration surpriseExpected on mid-cycle plan change — see Stripe invoice