Identifying a user tells Gleap who is on the other side of the conversation. Without it, every visitor is anonymous, which limits what Kai can answer and what you can target.
Run this wherever your app knows who the user is — usually right after login and on page load for an already-signed-in session.
Gleap.identify("user-123", {
name: "Franz Huber",
email: "[email protected]",
plan: "Pro",
createdAt: new Date("2024-03-01"),
company: {
id: "acme-inc",
name: "ACME Inc."
},
customData: {
projectId: "project-123",
seats: 12
}
});The first argument is your own user ID. Use the same value your database uses, and keep it stable — it's how Gleap recognises someone across sessions and devices.
Alongside the ID, Gleap recognises a set of standard fields: name, email, phone, avatar, plan, value, createdAt and sla.
Anything else goes in customData as key-value pairs. Custom fields work the same way as standard ones: they show in the sidebar, they can be used in audience filters, and Kai can read them. Two limits apply: values must be primitives (strings, numbers, or booleans), and you can send at most 35 custom keys per call.
Send what you'd want an agent to see before replying. A plan name and a signup date answer more questions than a long list of internal flags.
Pass a company object to group contacts under the organisation they belong to. That's what lets you see everyone from one customer together, and what company-level SLAs are based on.
company: {
id: "acme-inc", // required
name: "ACME Inc." // optional
}Three things are worth knowing about this.
The id is required. Without it, the whole company is ignored — a name on its own would show a company the contact isn't actually linked to. Use a stable identifier from your own system, not the display name.
Only id and name are used. Company-level attributes like plan or seat count don't belong here — put them in customData on the user, or set them on the company record itself through the server-side Companies API. Note that company.name acts as a fallback label: it won't overwrite a name already set authoritatively via the Companies API.
The nested company object needs SDK 16.3.0 or later. On earlier versions, pass the flat companyId and companyName properties instead. Those remain fully supported, so older integrations don't need to migrate.
To change attributes without re-identifying, use Gleap.updateContact() with just the fields that changed.
Call Gleap.clearIdentity() when someone logs out. On shared or public computers, skipping this leaves the next person signed in as the previous one.
If you need to check the current state, Gleap.isUserIdentified() returns whether someone is identified, and Gleap.getIdentity() returns the current user identity.
By default, anyone who can read your client-side code could call identify with someone else's user ID and see their conversations. Identity verification closes that.
Generate an HMAC-SHA256 of the user ID on your server, signed with your project's secret key, and pass it as the third argument:
// On your server
const crypto = require("crypto");
const userHash = crypto
.createHmac("sha256", process.env.GLEAP_SECRET)
.update(String(user.id))
.digest("hex");
// In your app
Gleap.identify("user-123", { name: "Franz Huber" }, userHash);Once you enforce identity verification in your project settings, calls without a valid hash are rejected. Roll it out by sending the hash first and enabling enforcement afterwards, so you don't lock out users mid-session. Example code for other server languages is in the developer documentation.
Kai can answer questions about the person's own account instead of in general. Agents see who they're talking to and their history. Outbound messages can be targeted by plan, company, signup date, or any custom field. Conversations follow the person across devices instead of starting fresh each time.