User Property
Concept
A value attached to one user and kept there, describing a current state such as plan or signup date, and overwritten whenever that state changes.
Why it exists
Pile up behavioral records alone and the range of answerable questions stays narrow. An event is one line recording who did what and when, and by itself it only supports counting how often something happened. You learn that documents were shared 42,000 times last month; you don't learn how much of that came from teams that pay.
So meetings stalled in a particular shape. Asked whether paying teams share more, the analyst says the current dashboard can't show it, then pulls an account list out of the billing database and matches it against the behavioral records by hand. That takes two days, and the same question next week takes two more.
What was missing was a value attached to the person. Behavior happens at a moment, while the plan someone is on or the size of their team is a standing characteristic. A user property puts that value in the same place as the behavioral records, so the split can be made in the room where the question was asked.
How it works
The value attaches to a user rather than an event, only the latest value survives a change, and the user identifier decides what it attaches to.
- It lives somewhere else. Events accumulate one line at a time, while a user property exists as one set per user. User A has a single plan field, and whatever that field says gets read alongside every record A has ever produced.
- Values get overwritten. Move an account from free to paid and the plan field reads paid, with nothing left saying it was ever free. This is the property that causes the most accidents. Split six months of data by plan and the past behavior of currently-paying accounts gets counted on the paid side.
- Values that belong to a moment go on the event instead, as an event property — the extra information stored alongside one event. Because it records the content of what happened then, it never changes later. If you need the plan as of a payment, the payment event has to carry the plan. Deciding this per value is the whole design job: anything you will later want to read "as it was then" belongs on the event.
- There are two points where it gets sent: one full set when the user logs in or signs up, and just the changed field whenever a state changes. Forget the update and the value doesn't disappear — it sits there as the old value, so the fact that it's wrong never surfaces.
- What it attaches to is decided by the user identifier, the stable value used to tie one person's records together. If that value wobbles, the properties land on the wrong person.
What gets stored usually falls into five kinds: contract state such as the plan, dates that mark a starting point such as the signup day, organizational facts such as team size or industry, the acquisition path showing which ad or search brought them in, and the role, such as admin versus ordinary member.
Where it shows up
The most frequent use is splitting numbers on a dashboard — the same feature-usage rate broken out by plan, by team size, by acquisition path. An overall usage rate of 18 percent tells you less than 34 percent for paying teams against 9 percent for free ones, and the second pair decides what happens next.
It's also how groups of similar users get defined. Teams that signed up in March, teams with more than twenty people: the condition fixes the group and you follow what share of it is still active months later. Of twenty-two teams that signed up in March, how many are still working four months on gets counted this way.
In-product messages and emails pick their audience from these values too. Show the plan-upgrade prompt only to free teams, send the setup guide only to accounts less than seven days old. When the values are stale, a team that upgraded yesterday gets the upgrade prompt one more time.
Experiments use them to narrow the population. If a change only affects enterprise customers, only users matching that condition go into the test. Customer success teams, meanwhile, use the same values to find accounts approaching renewal, sorting by signup date and plan rather than opening the billing system.
How it sounds at work
"I want to break this out by plan, but plan isn't coming in as a user property."
The question can't be answered with the current setup.
"That should be an event property, not a user property. We need the value as of that moment."
Flagging a value that must not be overwritten later.
"Property updates land a day late, so an account that converted yesterday still reads free."
The value isn't wrong; the update timing is.
Mia once got stuck trying to compare share-feature usage between paying and free teams. Theo instrumented four user properties that week — plan, team size, signup date, acquisition path — and from then on the same question was answered on screen in thirty seconds.
The historical data caught them out once more, though. Because the plan field holds a current value, splitting the previous six months by plan counted the free-era behavior of now-paying accounts as paid. Theo changed it so that the moment a plan changes is recorded as its own event, after which before and after could be separated.
What people get wrong
The most common assumption is that property values accumulate as a history each time they change. Everything else in the system stacks up one line at a time, so this looks like it should too. But a user property is a field holding the current state, and only the last value survives. Leave that assumption in place and rerunning an analysis from six months ago produces a different answer, costing days to explain. If the moment of change matters to the analysis, that moment has to be recorded as an event as well. Once the behavior is understood, which values belong on which side becomes a design-time question.
Believing more is better is nearly as common. Adding something now because it might be useful later is a natural call. But once there are forty properties, nobody knows which ones are still being updated. A field that stopped updating doesn't go blank; it holds an old value, so filtering on it in a dashboard returns a wrong answer with no warning at all. Keeping what's used and deleting what isn't stays safer, and a short list that everyone trusts beats a long one nobody checks.
Easily confused with
| Term | What it holds | How it differs from a user property |
|---|---|---|
| User identifier | The stable value that ties one person's records together | It points at who someone is, so it should never change. A user property holds their state and is overwritten when that state changes |
Where to go next
- Event tracking
see which part of the collection structure this sits in
- Event
see how the behavioral side gets recorded
Last updated 2026-09-16