← All docs

Identifying users

How visitors, users and sessions work, and when to call identify() and reset().

LaunchPulse tracks anonymous visitors out of the box. If your product has accounts, calling identify() connects those anonymous sessions to a real user in your database.

Visitor, user, actor

Three ids, and the difference matters when you read numbers in the dashboard.

IdWhat it is
visitor_idThe anonymous per-browser id. Assigned automatically on init()
user_idWhat you set via identify(). Empty until you call it
actoruser_id when present, otherwise visitor_id

The actor is the unit used for conversion, activation and “people” counts. That’s the point of identifying: without it, the same person on their laptop and their phone is two actors. With it, they’re one.

The dashboard’s Visitors metric counts distinct visitor_id — it is deliberately browser-level, so it stays comparable whether or not you identify.

identify()

lp.identify("user_8f21c");

Sets the user id, persists it in the _lp_vid cookie, and emits a $identify event.

Pass an internal user id, never PII. The SDK warns in the console if the value looks like an email address. Emails end up in your analytics store, in the events log, and in anything you export. A database id doesn’t.

// Good
lp.identify(user.id);

// Bad — warns, and puts an email in your analytics
lp.identify(user.email);

Call it as soon as you know who the person is: right after login, right after signup, and on every page load for an already-authenticated session. The value persists in the cookie, so re-calling it with the same id is harmless and keeps identity correct after the cookie expires or the user clears storage.

Call it before your first-value event, so that event can be attributed to a user. See Conversions and activation.

// React, after your session loads
useEffect(() => {
  if (session?.user) window.lp?.identify(session.user.id);
}, [session]);

reset()

lp.reset();

Clears the user id and rotates both the visitor id and the session id. Everything after the call is a fresh anonymous browser.

Call it on logout. Call it on any shared device — a kiosk, a support machine, a demo laptop — where the next person must not inherit the previous person’s identity.

Don’t call it on every page load or on a route change. Rotating the visitor id throws away 30 days of attribution history for that browser.

Identity lives in a first-party cookie named _lp_vid.

PropertyValue
Visitor id formatlpv_<base36 time><10 random chars>
Visitor lifetime30 days (cookie Max-Age)
Session inactivity timeout30 minutes
FlagsPath=/, SameSite=Lax, Secure on https, optional Domain

A visitor that returns within 30 days is the same visitor_id. After 30 days of no visits, they come back as a new visitor.

A session ends after 30 minutes of inactivity. The next event after that gap mints a new session id.

Subdomains

Without a Domain, the cookie is host-only — app.yourapp.com and www.yourapp.com would be separate visitors. Set cookieDomain to share identity across subdomains:

LaunchPulse.init("lp_pub_yourkey", { cookieDomain: ".yourapp.com" });

The collector normally supplies this automatically. The SDK ships no public-suffix list, so it can never mis-scope your cookie.

Attribution

Attribution is stored on the visitor, and it comes in two flavors.

First-touch is frozen for the visitor’s lifetime. Whatever brought someone in the first time stays attached to every event they ever send, for 30 days:

  • first_source
  • first_campaign
  • first_landing_page

Session attribution refreshes on each new session:

  • session_source
  • session_medium
  • session_campaign
  • session_landing_page

So if someone finds you through a Hacker News post, leaves, and comes back a week later via a Google search, first-touch still says Hacker News, and session attribution says Google. That’s what makes it possible to tell what actually acquires people versus what merely brings them back.

How source is classified

  1. UTM params win. utm_source becomes the source; utm_medium, or campaign if there’s no medium, becomes the medium.
  2. Otherwise the referrer host, stripped of www., and ignored when it matches your own host. Medium is organic for google, bing, duckduckgo, yahoo, ecosia and brave, and referral for everything else.
  3. Otherwise direct / direct.

Captured UTM parameters: utm_source, utm_medium, utm_campaign, utm_content, utm_term.

More on reading this in Sources and Domains and referrers.

Privacy

Your visitors’ IP addresses are used only to derive a country, then discarded. They are never stored. Combined with the “no PII in identify()” rule, that keeps your analytics free of personal data by default. See Security.

Identifying from your backend

Server-side events carry identity too — you set user_id in the payload rather than calling identify(). See Server-side events. Use the same id in both places, or you’ll end up with two actors for one person.

NextRevenue tracking

Talk to us

Questions about LaunchPulse, or want a walkthrough? Send a note and a real person replies.

Or email us at hello@launchpulse.dev