## Summary Closes #36. Helpers / consent gating already exist from [#42](#42). This PR adds **call sites** + docs: - `identifyAccount` + `AnalyticsSession` (identify on session; `Logout` when auth ends) - Auth: Sign In / Sign Up / AuthCallback (SSO) success & fail - Billing: Checkout started, Payment Success / Canceled - Chat: Conversation Created, Message Sent (metadata only — no prompt text) - ToS Acknowledged - `BILLING_PORTAL_OPENED` reserved until Account portal (#33) - Catalog: [`llm-fe/ANALYTICS.md`](llm-fe/ANALYTICS.md) No `chat_backend` changes required. ## Test plan - [ ] Grant consent on beta → sign in → Tianji shows Login Success + identify - [ ] Decline consent → same actions produce no custom events (page views still ok) - [ ] Sign up + checkout + cancel/success return URLs fire expected events - [ ] New chat + send message → Conversation Created / Message Sent without prompt text - [ ] Acknowledge ToS → ToS Acknowledged - [ ] `npm run test:ci -- --testPathPattern='analytics.test|SignIn.test|SignUp.test|AuthCallback.test'`Reviewed-on: #45
This commit was merged in pull request #45.
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import { hasAnalyticsConsent, isAnalyticsEnvironment } from './analyticsConsent';
|
||||
import type { Account } from '../data';
|
||||
|
||||
type QueuedCall =
|
||||
| { type: 'track'; eventName: string; data?: Record<string, unknown> }
|
||||
@@ -6,7 +7,21 @@ type QueuedCall =
|
||||
|
||||
const queue: QueuedCall[] = [];
|
||||
|
||||
/** Named events for product analytics. Page views stay on automatic tracker.js. */
|
||||
/**
|
||||
* Named product events for Tianji (consent-gated). Page views stay on tracker.js.
|
||||
*
|
||||
* | Event | When |
|
||||
* |-------|------|
|
||||
* | Login Success / Failed | Password or SSO sign-in |
|
||||
* | Sign Up Started / Success / Failed | Self-serve registration |
|
||||
* | Logout | Sign out |
|
||||
* | Checkout Started | Stripe Checkout session created |
|
||||
* | Payment Success / Canceled | Billing return URLs |
|
||||
* | Conversation Created | New chat id assigned over WS |
|
||||
* | Message Sent | User submits prompt (no content) |
|
||||
* | ToS Acknowledged | POST acknowledge_tos succeeds |
|
||||
* | Billing Portal Opened | When #33 portal CTA ships |
|
||||
*/
|
||||
export const AnalyticsEvents = {
|
||||
LOGIN_SUCCESS: 'Login Success',
|
||||
LOGIN_FAILED: 'Login Failed',
|
||||
@@ -75,3 +90,17 @@ export const identifyUser = (userInfo: Record<string, unknown>): void => {
|
||||
|
||||
queue.push({ type: 'identify', userInfo: { ...userInfo } });
|
||||
};
|
||||
|
||||
/** Identify with stable non-sensitive traits only (no names / prompts). */
|
||||
export const identifyAccount = (account: Account): void => {
|
||||
const traits: Record<string, unknown> = {
|
||||
userId: account.email,
|
||||
};
|
||||
if (account.company?.id != null) {
|
||||
traits.companyId = account.company.id;
|
||||
}
|
||||
if (account.is_company_manager) {
|
||||
traits.isCompanyManager = true;
|
||||
}
|
||||
identifyUser(traits);
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user