Overview
Woopra's data layer allows you to enrich your analytics with user properties, account information, and custom attributes. Proper data layer setup enables powerful segmentation, personalization, and user journey analysis.
User Identification
Basic User Identification
Identify users with their core properties:
woopra.identify({
email: 'user@example.com',
name: 'John Doe',
company: 'Acme Inc',
plan: 'enterprise'
});
Complete User Profile
Include comprehensive user data for deeper insights:
woopra.identify({
// Required identifiers
email: 'user@example.com',
id: 'user_12345',
// Personal information
name: 'John Doe',
firstName: 'John',
lastName: 'Doe',
phone: '+1-555-0123',
// Company information
company: 'Acme Inc',
companySize: '50-200',
industry: 'Technology',
// Account details
plan: 'enterprise',
mrr: 299,
signupDate: '2024-01-15',
trialEndsAt: '2024-02-15',
// Custom properties
referralSource: 'google_ads',
campaignId: 'summer_2024',
isVip: true,
lifetimeValue: 3588
});
Visitor Properties
Setting Individual Properties
Set properties one at a time:
woopra.identify('email', 'user@example.com')
.identify('name', 'John Doe')
.identify('plan', 'pro')
.push();
Updating User Properties
Update properties as users progress through your app:
// User upgrades plan
woopra.identify({
plan: 'enterprise',
upgradedAt: Date.now(),
previousPlan: 'pro'
});
// User completes onboarding
woopra.identify({
onboardingCompleted: true,
onboardingCompletedAt: Date.now(),
onboardingStepsCompleted: 5
});
// User reaches milestone
woopra.identify({
projectsCreated: 10,
teamMembers: 5,
storageUsed: 2.5, // GB
lastActiveAt: Date.now()
});
Property Types and Naming
Supported Data Types
Woopra supports various property types:
woopra.identify({
// Strings
email: 'user@example.com',
plan: 'enterprise',
status: 'active',
// Numbers
age: 32,
mrr: 299.99,
loginCount: 47,
// Booleans
isActive: true,
hasCompletedOnboarding: false,
isEmailVerified: true,
// Dates (use timestamps or ISO strings)
createdAt: Date.now(),
lastLoginAt: '2024-01-15T10:30:00Z',
// Arrays (as comma-separated strings)
interests: 'analytics,marketing,sales',
features: 'export,api,integrations'
});
Property Naming Conventions
Use consistent, descriptive property names:
// Good - consistent camelCase
woopra.identify({
firstName: 'John',
lastName: 'Doe',
signupDate: '2024-01-15',
isEmailVerified: true
});
// Avoid - inconsistent naming
woopra.identify({
first_name: 'John',
LastName: 'Doe',
signup_date: '2024-01-15',
email_verified: true
});
Account-Level Properties
B2B Account Tracking
Track both user and account (company) properties:
woopra.identify({
// User properties
email: 'john@acme.com',
name: 'John Doe',
role: 'Admin',
userId: 'user_12345',
// Account properties
accountId: 'acct_789',
accountName: 'Acme Inc',
accountPlan: 'Enterprise',
accountMrr: 999,
accountSeats: 25,
accountIndustry: 'Technology',
accountCreatedAt: '2023-06-01'
});
Multi-Tenant Applications
Handle users across multiple accounts:
// User switches between accounts
function switchAccount(accountId) {
const account = getAccountData(accountId);
woopra.identify({
currentAccountId: accountId,
currentAccountName: account.name,
currentAccountPlan: account.plan,
accountSwitchedAt: Date.now()
});
woopra.track('account_switched', {
from_account: previousAccountId,
to_account: accountId
});
}
Conditional Properties
Dynamic Property Setting
Set properties based on user state or behavior:
// Identify based on user type
if (user.isLoggedIn) {
woopra.identify({
email: user.email,
name: user.name,
userId: user.id,
userType: 'authenticated',
sessionCount: user.sessionCount
});
} else {
woopra.identify({
userType: 'anonymous',
sessionCount: 1
});
}
// Identify based on subscription status
const subscriptionStatus = user.subscription.active ? 'active' : 'inactive';
woopra.identify({
subscriptionStatus: subscriptionStatus,
subscriptionTier: user.subscription.tier,
billingCycle: user.subscription.billingCycle
});
Calculated Properties
Include computed values:
// Calculate engagement metrics
const daysSinceSignup = Math.floor((Date.now() - user.signupDate) / (1000 * 60 * 60 * 24));
const avgSessionDuration = user.totalSessionTime / user.sessionCount;
woopra.identify({
daysSinceSignup: daysSinceSignup,
averageSessionDuration: Math.round(avgSessionDuration),
engagementScore: calculateEngagementScore(user),
lifetimeValue: user.totalRevenue,
churnRisk: user.lastLoginDays > 30 ? 'high' : 'low'
});
Best Practices
Identify Early and Often
Identify users as soon as possible:
// On page load (if user is logged in)
document.addEventListener('DOMContentLoaded', function() {
if (currentUser) {
woopra.identify({
email: currentUser.email,
name: currentUser.name,
id: currentUser.id
});
woopra.track();
}
});
// After login
function handleLogin(userData) {
woopra.identify({
email: userData.email,
name: userData.name,
id: userData.id,
loginAt: Date.now()
});
woopra.track('login');
}
Keep Properties Updated
Update properties when they change:
// User updates profile
function updateProfile(newData) {
// Update in your database
saveUserProfile(newData);
// Update in Woopra
woopra.identify({
name: newData.name,
phone: newData.phone,
profileUpdatedAt: Date.now()
});
woopra.track('profile_updated', {
fields_changed: Object.keys(newData).join(',')
});
}
Use Consistent Identifiers
Always use the same identifier for a user:
// Good - consistent ID across sessions and devices
woopra.identify({
id: user.id, // Your internal user ID
email: user.email // Backup identifier
});
// Avoid - different IDs in different contexts
// Session 1: woopra.identify({ id: user.sessionId });
// Session 2: woopra.identify({ id: user.email });
Common Use Cases
E-commerce User Data
woopra.identify({
email: 'customer@example.com',
customerId: 'CUST_12345',
// Purchase history
totalOrders: 23,
totalSpent: 2847.50,
averageOrderValue: 123.80,
lastPurchaseDate: '2024-01-10',
// Preferences
favoriteCategory: 'Electronics',
newsletterSubscribed: true,
smsOptIn: false,
// Loyalty
loyaltyTier: 'Gold',
loyaltyPoints: 4500,
referralCount: 3
});
SaaS User Data
woopra.identify({
email: 'user@startup.com',
userId: 'user_789',
// Subscription
plan: 'professional',
mrr: 99,
billingCycle: 'monthly',
nextBillingDate: '2024-02-01',
trialUser: false,
// Usage metrics
projectsCreated: 12,
apiCallsThisMonth: 45000,
storageUsed: 8.5, // GB
teamSize: 8,
lastActiveDate: '2024-01-15',
// Feature adoption
featuresUsed: 'api,export,integrations,webhooks',
advancedFeaturesEnabled: true,
integrationsConnected: 4
});
Content Platform User Data
woopra.identify({
email: 'reader@example.com',
userId: 'user_456',
// Engagement
articlesRead: 127,
commentsPosted: 15,
articlesBookmarked: 23,
shareCount: 8,
lastVisitDate: '2024-01-14',
// Preferences
topicsFollowed: 'technology,business,science',
authorsFollowed: 'author_1,author_5,author_12',
emailFrequency: 'weekly',
// Subscription
subscriptionType: 'premium',
memberSince: '2023-03-15',
autoRenewal: true
});
Server-Side Identification
Identify Users from Backend
Send user properties from your server:
import requests
def identify_woopra_user(user_data):
"""Identify user in Woopra from server-side"""
url = "https://www.woopra.com/track/identify/"
# Build visitor properties (prefixed with cv_)
params = {
'host': 'example.com',
'cv_email': user_data['email'],
'cv_name': user_data['name'],
'cv_id': user_data['id'],
'cv_plan': user_data['plan'],
'cv_mrr': user_data['mrr'],
'cv_signupDate': user_data['signup_date']
}
response = requests.post(url, data=params)
return response.status_code == 200
# Usage
identify_woopra_user({
'email': 'user@example.com',
'name': 'John Doe',
'id': 'user_12345',
'plan': 'enterprise',
'mrr': 299,
'signup_date': '2024-01-15'
})
Sync User Data Periodically
Keep Woopra updated with latest user data:
def sync_user_to_woopra(user_id):
"""Sync user data from database to Woopra"""
# Get latest user data from database
user = get_user_from_db(user_id)
# Calculate metrics
lifetime_value = calculate_lifetime_value(user)
engagement_score = calculate_engagement_score(user)
# Send to Woopra
identify_woopra_user({
'email': user.email,
'id': user.id,
'name': user.name,
'plan': user.subscription.plan,
'mrr': user.subscription.mrr,
'lifetime_value': lifetime_value,
'engagement_score': engagement_score,
'last_synced': datetime.now().isoformat()
})
Troubleshooting
Properties Not Appearing
If properties aren't showing in Woopra:
// Enable debug mode to see what's being sent
woopra.config({ debug: true });
woopra.identify({
email: 'test@example.com',
testProperty: 'value'
});
// Check browser console for debug output
Property Values Not Updating
Ensure you're calling identify() with updated values:
// This updates the property
woopra.identify({ plan: 'enterprise' });
// Track an event to ensure data is sent
woopra.track('plan_upgraded');
Reserved Property Names
Avoid using Woopra's reserved property names:
// Avoid these property names
// - cookie
// - host
// - timeout
// - idle_timeout
// Use custom names instead
woopra.identify({
customCookie: 'value', // Instead of 'cookie'
hostName: 'example', // Instead of 'host'
});