Match Users
Search Endpoints
Match Users
Match people by activity-derived interest facets
Match Users
Ranks other users against an asker’s interests, using activity-derived interest facets — clusters of what each user has actually engaged with over time, not a static profile. The endpoint returns a structured match breakdown (who, how strongly, and on which facets), optionally with sample content that illustrates each overlap.
Matching runs in two modes:
Breakdown fields
passive— match against the asker’s own interest facets. Answers “who is like me?” No free-text; the asker’s top facets are the query.directed— match against a free-textquerytopic. Answers “who is into biotech?” The query is embedded and ranked against candidate facets.
Requires a paid plan, the
ai-search bundle, the interest-matching bundle, and interestMatching.enabled set on the project. See the Interest Matching guide for setup.Authentication
The endpoint requires an authenticated user. A missing token is rejected with a bare401 before the controller runs; an invalid or expired token is rejected with 403 (refresh and retry). Both modes act on behalf of that user:
passiveranks candidates against the asker’s own facets — the authenticated user is the query.directedranks candidates against a free-textquery, still on behalf of the authenticated user.
401 auth/user-required if none is resolved.
Body Parameters
string
required
"passive" or "directed".string
The free-text topic to match against. Required in
directed mode; rejected in passive mode.number
default:"20"
Maximum number of matched users to return. Maximum
50.string
Restrict candidates to users active in this space.
boolean
default:"false"
Only applies with
spaceId. When true, candidates active anywhere in the space’s subtree are eligible. Ignored without spaceId.boolean
default:"false"
Gate 2 of the two-gate sample exposure. When
true and the project setting interestMatching.exposeSampleContent is on, each matched facet includes a few illustrative content snippets from the candidate. Requesting samples while the project setting is off returns 403 match/sample-content-disabled.boolean
default:"true"
Exclude the asker from the results.
Response
Returns the{ results: [...] } envelope (a deliberate divergence from search/*, which return bare arrays). Results are ordered by descending score.
score— the aggregate match score. Inpassivemode this is additive over the top matched facet-pairs (two moderate overlaps can outrank one very strong overlap); indirectedmode it is the single best facet’ssimilarity · weight(hotness).matchedFacets[].similarity— cosine similarity of the facet pair.matchedFacets[].askerFacet— the asker’s side of the pair. Present inpassivemode; omitted indirectedmode (there is no asker facet — the query is the anchor) and for the cold-start bio fallback.matchedFacets[].candidateFacet— the candidate’s facet: itsidand lazily-decayedhotness.matchedFacets[].sampleContent— present only when both sample gates are satisfied. Never contains moderation-removed, soft-deleted, or private-DM content.
Cold-start fallback
Inpassive mode, if the asker has no facet above the significance threshold, the endpoint falls back to the asker’s bio embedding (from UserEmbeddings) as a single pseudo-facet, so a brand-new user can still get matches. Cold-start matches omit askerFacet on the breakdown.
Candidate exclusions
Candidates are excluded when they are: the asker (unlessexcludeSelf: false), users with an active suspension (a future-dated suspension does not count as active), and — for a space-scoped match — users banned in that space.
Error Responses
User Required — 401
User Required — 401
Plan Required — 403
Plan Required — 403
Interest Matching Disabled — 403
Interest Matching Disabled — 403
Sample Content Disabled — 403
Sample Content Disabled — 403
Tables Not Available — 403
Tables Not Available — 403
The
interest-matching bundle is not installed.
