Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.vibefollow.com/llms.txt

Use this file to discover all available pages before exploring further.

Nine lifecycle events have first-class TypeScript helpers. Prefer them over events.track() — you get autocomplete and protection against name typos.
The constant STANDARD_EVENT_NAMES is exported from @vibefollow/sdk if you need to enumerate the canonical set programmatically.

The nine helpers

signedUp

user_signed_up — account created.

trialStarted

trial_started — trial activated.

featureUsed

feature_used — meaningful action in product.

onboardingStep

onboarding_step — step started or completed.

subscriptionChanged

subscription_changed — any plan/interval change.

subscriptionCancelled

subscription_cancelled — cancel requested, still has access.

paymentFailed

payment_failed — billing decline.

trialExpiring

trial_expiring — trial about to end.

userInvited

user_invited — teammate invited.

Reference table

HelperEvent nameCommon properties
users.signedUpuser_signed_upplan, source
users.trialStartedtrial_startedtrialDays
users.featureUsedfeature_usedfeature (required), count
users.onboardingSteponboarding_stepstep (required), completed
users.subscriptionChangedsubscription_changedfrom, to (required), interval, mrr
users.subscriptionCancelledsubscription_cancelledreason, effectiveAt
users.paymentFailedpayment_failedreason
users.trialExpiringtrial_expiringdaysLeft (required)
users.userInviteduser_invitedinvitedEmail (required)

signedUp

Fires when a user creates their account. Drives the signup audience and the “welcome” trigger rule.
await vf.users.signedUp('usr_42', {
  plan: 'trial',
  source: 'organic',
});

trialStarted

Fires when a trial activates. Often the same moment as signup; emit both if so.
await vf.users.trialStarted('usr_42', { trialDays: 14 });

featureUsed

Fires when the user does something interesting in your product. The feature string is the audience key — pick stable identifiers (dashboard_export, not Dashboard Export!).
await vf.users.featureUsed('usr_42', {
  feature: 'dashboard_export',
  count: 1,
});

onboardingStep

Fires when a user completes (or starts) an onboarding step. Powers the “onboarding stalled” trigger that nudges users who got partway through.
await vf.users.onboardingStep('usr_42', {
  step: 'connect_integration',
  completed: true,
});

subscriptionChanged

Fires on any plan change — trial → pro, pro → enterprise, monthly → yearly. The interval field is denormalised onto the user row so audience filters like “all yearly subscribers” can be answered without scanning event JSON. mrr should be in cents (9900 = $99/mo).
await vf.users.subscriptionChanged('usr_42', {
  from: 'trial',
  to: 'pro',
  interval: 'yearly',
  mrr: 9900,
});

subscriptionCancelled

Fires when the user clicks Cancel but still has access. Distinct from churned (truly gone after the grace period — emit a follow-up subscription_changed with to: 'churned' when access actually ends).
await vf.users.subscriptionCancelled('usr_42', {
  reason: 'too_expensive',
  effectiveAt: '2026-06-01T00:00:00Z',
});

paymentFailed

Fires on any billing decline. Powers the “card declined” recovery flow.
await vf.users.paymentFailed('usr_42', { reason: 'card_declined' });

trialExpiring

Fires when a trial is about to end. daysLeft lets your billing system control the cadence (7, 3, 1).
await vf.users.trialExpiring('usr_42', { daysLeft: 3 });

userInvited

Fires when a user invites a teammate. Powers the team-expansion nudges.
await vf.users.userInvited('usr_42', {
  invitedEmail: 'colleague@acme.io',
});

What if my event isn’t on this list?

Use events.track(). Custom event names are accepted as-is and become first-class citizens in audience filters. See Custom events.