API Documentation
Complete reference for all Convex functions in Soloist application
User Management
Functions for managing user accounts, profiles, and authentication
viewer
queryGet the current authenticated user (viewer)
Parameters
No parameters
Returns
User | nullExample
const user = useQuery(api.users.viewer);What This Does
This function checks who is currently logged into the app and returns their user information. If nobody is logged in, it returns null. It's commonly used to display user information in the UI or to check if someone is authenticated before showing certain features.
currentUser
queryGet the current authenticated user
Parameters
No parameters
Returns
User | nullExample
const user = useQuery(api.users.currentUser);What This Does
Similar to the viewer function, this retrieves information about whoever is currently signed in. It's useful when you need to access the logged-in user's details like their name, email, or profile picture anywhere in your application.
getProfile
queryGet user profile information for the authenticated user
Parameters
No parameters
Returns
UserExample
const profile = useQuery(api.users.getProfile);What This Does
This function fetches the complete profile information for the person who is currently logged in. Unlike viewer or currentUser, this will throw an error if no one is authenticated, making it suitable for protected pages where you know someone must be logged in.
getAllUsers
queryGet all users (admin function)
Parameters
No parameters
Returns
User[]Example
const users = useQuery(api.users.getAllUsers);What This Does
This retrieves a list of every user registered in the system. It's intended for administrative purposes, like viewing all users in an admin dashboard. In a production app, this should be restricted to admin users only with proper permission checks.
getUserByEmailPublic
queryCheck if user exists by email (public query)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
string | Required | User's email address |
Returns
User | nullExample
const user = useQuery(api.users.getUserByEmailPublic, { email: "user@example.com" });What This Does
This looks up a user by their email address and returns their public profile information if found. It's useful for checking whether someone has already signed up with a particular email or for finding users by email in features like invitations or mentions.
getUserSubscriptionStatus
queryGet user's subscription status
Parameters
No parameters
Returns
{ hasActiveSubscription: boolean, subscriptionType: string | null, subscription: Subscription }Example
const status = useQuery(api.users.getUserSubscriptionStatus);What This Does
This checks whether the current user has an active paid subscription. It returns detailed information about their subscription status, which is useful for determining whether to show premium features or prompt them to upgrade their plan.
getUser
queryGet user by ID (public function)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| id | string | Required | User ID |
Returns
User | nullExample
const user = useQuery(api.users.getUser, { id: "user_123" });What This Does
This retrieves a user's information using their unique ID. For security, it only allows users to access their own data - if you request someone else's ID, it returns null. This prevents users from viewing other people's private information.
exportUserData
queryExport all user data including profile, logs, attributes, and subscription
Parameters
No parameters
Returns
{ profile: User, dailyLogs: Log[], userAttributes: UserAttributes, subscription: Subscription, exportedAt: string, totalLogs: number }Example
const data = useQuery(api.users.exportUserData);What This Does
This gathers all of the current user's data from across the entire system - their profile, all their daily mood logs, custom attributes, and subscription info - and packages it into a single export. This is useful for GDPR compliance, allowing users to download all their data, or for creating backups.
upsertUser
mutationUpsert user (public function)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| name | string | Optional | User's name |
string | Optional | User's email | |
| image | string | Optional | User's profile image URL |
Returns
Id<'users'>Example
const userId = await upsertUser({ name: "John Doe", email: "john@example.com" });What This Does
This updates the authenticated user's profile information with any new values you provide. You can update their name, email, or profile picture. It only modifies the fields you include in the request, leaving other fields unchanged.
updateUserProfile
mutationUpdate user profile (public mutation for authenticated users)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| name | string | Optional | User's name |
| phone | string | Optional | User's phone number |
| image | string | Optional | User's profile image URL |
Returns
UserExample
const updated = await updateUserProfile({ name: "Jane Doe" });What This Does
This allows the current user to update their profile details like name, phone number, or profile picture. After making the changes, it returns the updated user object so you can see the new values. Only authenticated users can call this, and they can only update their own profile.
getUserByEmail
internalQueryGet user by email (internal function)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
string | Required | User's email address |
Returns
User | nullWhat This Does
This is an internal function used by the backend to look up users by email. It's marked as internal so it can only be called by other Convex functions, not directly from the client. This helps protect sensitive operations like authentication and user lookups.
updateProfile
internalMutationUpdate user profile
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| name | string | Optional | User's name |
string | Optional | User's email | |
| image | string | Optional | User's profile image URL |
| phone | string | Optional | User's phone number |
Returns
voidWhat This Does
This internal function handles the core logic of updating a user's profile information. It's used by other backend functions and removes any undefined values before saving, ensuring only the fields you want to change actually get updated in the database.
deleteAccount
internalMutationDelete user account and all associated data
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID to delete |
Returns
voidWhat This Does
This permanently removes a user's account and all their associated data from the system. It first deletes related records like subscriptions, then removes the user itself. This is a sensitive operation that's kept internal for security reasons.
completeUserDeletion
internalMutationCompletely delete a user and all associated data by email
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
string | Required | User's email address |
Returns
DeletionSummaryWhat This Does
This is a comprehensive deletion function that removes a user and absolutely everything associated with them - subscriptions, payments, logs, forecasts, feed entries, and more. It returns a summary of what was deleted, which is useful for debugging and confirming the deletion was complete.
Daily Logs
Functions for creating, reading, and managing daily mood logs
listDailyLogs
queryFetch all logs for a given user and year
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
| year | string | Required | Year in YYYY format (e.g., '2025') |
Returns
Log[]Example
const logs = useQuery(api.dailyLogs.listDailyLogs, { userId: "user_123", year: "2025" });What This Does
This retrieves all mood logs for a specific user during a particular year. For example, if you want to see all of someone's entries from 2025, this will fetch every log from January 1st through December 31st. It's useful for yearly review features or visualizing long-term patterns.
getDailyLog
queryFetch a single daily log for a given user and date
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
| date | string | Required | Date in YYYY-MM-DD format |
Returns
Log | nullExample
const log = useQuery(api.dailyLogs.getDailyLog, { userId: "user_123", date: "2025-01-15" });What This Does
This fetches a single mood log entry for a specific date. If the user has logged their mood on that day, you'll get their entry back. If they haven't logged anything for that date yet, it returns null. This is perfect for showing today's log or checking if a particular day has been filled in.
getLogsByDateRange
queryFetch all daily logs for a user between two ISO dates (inclusive)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
| startDate | string | Required | Start date in YYYY-MM-DD format |
| endDate | string | Required | End date in YYYY-MM-DD format |
Returns
Log[]Example
const logs = useQuery(api.dailyLogs.getLogsByDateRange, { userId: "user_123", startDate: "2025-01-01", endDate: "2025-01-31" });What This Does
This gets all logs between two dates, including both the start and end dates. For example, you could fetch all logs from the past week, month, or any custom date range. It's great for showing trends over specific time periods or creating custom reports.
getLogCount
queryGet the total number of logs for a user
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
Returns
numberExample
const count = useQuery(api.dailyLogs.getLogCount, { userId: "user_123" });What This Does
This simply counts how many total log entries a user has created. It's useful for displaying statistics like 'You've logged your mood 45 times!' or tracking user engagement over time.
listScores
queryList all dates and scores for a user
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
Returns
Array<{ date: string, score: number | null }>Example
const scores = useQuery(api.dailyLogs.listScores, { userId: "user_123" });What This Does
This returns a simplified list of just the dates and mood scores for all of a user's logs, leaving out the detailed answers and other information. It's perfect for creating charts and graphs of mood over time without loading unnecessary data.
listAllUserLogs
queryDebugging helper: Show all logs for a user
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
Returns
Log[]Example
const logs = useQuery(api.dailyLogs.listAllUserLogs, { userId: "user_123" });What This Does
This is a debugging tool that fetches every single log for a user with all details formatted in a readable way. It includes timestamps and converts them to human-readable dates. Use this when troubleshooting issues or inspecting the raw data structure.
getLogById
queryDebugging helper: Get log details by ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| logId | string | Required | Log document ID |
Returns
Log | nullExample
const log = useQuery(api.dailyLogs.getLogById, { logId: "log_abc123" });What This Does
This debugging function looks up a specific log using its unique database ID rather than by date and user. It's useful when you're investigating a particular log entry and have its ID, or when building admin tools that need to reference specific records.
dailyLog
mutationUpserts a daily log record. If a log with (userId, date) already exists, patch it; otherwise insert a new record
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
| date | string | Required | Date in YYYY-MM-DD format |
| answers | any | Required | Log answers data |
| score | number | Optional | Emotion score (0-100) |
Returns
LogExample
const log = await dailyLog({ userId: "user_123", date: "2025-01-15", answers: {...}, score: 85 });What This Does
This saves or updates a daily mood log. If the user already logged their mood for this date, it updates that existing entry. If not, it creates a new one. This smart behavior means users can always safely save their mood without worrying about creating duplicates.
Forecast & AI
AI-powered forecasting and mood prediction functions
testDatabaseConnection
queryTest database connection
Parameters
No parameters
Returns
{ success: boolean, message: string }Example
const test = useQuery(api.forecast.testDatabaseConnection);What This Does
This is a simple health check function that confirms the database is working properly. It returns a success message if everything is connected correctly. Useful for debugging or monitoring the system's health.
getLogsForUser
queryGet recent logs for a user up to a specific end date
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| endDate | string | Required | End date in YYYY-MM-DD format |
Returns
Log[]Example
const logs = useQuery(api.forecast.getLogsForUser, { userId: userId, endDate: "2025-01-31" });What This Does
This retrieves all logs up to a specific date, ordered with the most recent first. It's particularly useful for the forecasting system, which needs to analyze recent mood patterns to predict future moods.
getLogsForUserInRange
queryGet logs for a user in a date range (inclusive)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| startDate | string | Required | Start date in YYYY-MM-DD format |
| endDate | string | Required | End date in YYYY-MM-DD format |
Returns
Log[]Example
const logs = useQuery(api.forecast.getLogsForUserInRange, { userId, startDate: "2025-01-01", endDate: "2025-01-31" });What This Does
Similar to the dailyLogs version, but this one normalizes the dates to ensure they're in a consistent format (removing any time components). This is specifically designed for the forecast system which requires clean date formatting.
getSevenDayForecast
queryGet the 7-day forecast data (3 days before today, today, 3 days after today)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| startDate | string | Optional | Optional start date override |
| endDate | string | Optional | Optional end date override |
| today | string | Optional | Optional today date override |
Returns
ForecastDay[]Example
const forecast = useQuery(api.forecast.getSevenDayForecast, { userId });What This Does
This creates a 7-day view: your past 3 days (with actual mood data), today, and the next 3 days (with AI-predicted moods). It's like a weather forecast but for your emotional state. If forecasts haven't been generated yet, it shows placeholder text prompting you to generate them.
getForecastFeedback
queryGet feedback for forecast dates
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| forecastDates | string[] | Required | Array of forecast dates |
Returns
Record<string, 'up' | 'down'>Example
const feedback = useQuery(api.forecast.getForecastFeedback, { userId, forecastDates: ["2025-01-16", "2025-01-17"] });What This Does
This retrieves thumbs up/down feedback that users have given on forecast predictions. When users rate whether a forecast was accurate, this function lets you see those ratings. It's useful for displaying feedback indicators and for training the AI to improve predictions.
generateForecast
actionGenerate forecast for a user based on historical logs
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| startDate | string | Optional | Start date for log range |
| endDate | string | Optional | End date for log range |
Returns
{ success: boolean, error?: string, forecastDates?: string[] }Example
const result = await generateForecast({ userId });What This Does
This is the core forecasting action. It analyzes your recent mood logs (default is the last 4 days) and uses AI to predict your mood for the next 3 days. It checks that you have logs for all required days, sends the data to the AI, and saves the predictions. Returns success or an error message if something goes wrong (like missing log data).
generateRetrospectiveForecastAnalysis
actionGenerate retrospective forecasts for historical analysis
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| startDate | string | Optional | Start date for analysis |
| endDate | string | Optional | End date for analysis |
Returns
{ success: boolean, error?: string, analysis?: AnalysisResult }Example
const analysis = await generateRetrospectiveForecastAnalysis({ userId });What This Does
This is a testing tool that validates forecast accuracy. It goes back through your historical logs, pretends each day is 'today', generates a forecast for the next day, then compares that prediction to what actually happened. It creates an accuracy report showing how well the AI predictions match reality, helping improve the forecasting system.
submitForecastFeedback
mutationSubmit feedback for a forecast (thumbs up/down)
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| forecastDate | string | Required | Forecast date |
| feedback | 'up' | 'down' | Required | Feedback type |
Returns
{ updated?: boolean, created?: boolean }Example
const result = await submitForecastFeedback({ userId, forecastDate: "2025-01-16", feedback: "up" });What This Does
This lets users rate whether a forecast was accurate with a thumbs up (good prediction) or thumbs down (inaccurate). If they've already rated that date, it updates their rating. If not, it creates a new rating. This feedback helps track forecast accuracy over time.
Templates
Functions for managing custom log templates
getUserTemplates
queryGet all templates for a user
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
Returns
Template[]Example
const templates = useQuery(api.templates.getUserTemplates, { userId: "user_123" });What This Does
This retrieves all custom log templates that a user has created. Templates let users define their own questions for mood logging (like 'Did I exercise?' or 'How much did I sleep?'). This function returns them ordered by most recent first.
getTemplateById
queryGet a specific template by ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| templateId | Id<'templates'> | Required | Template document ID |
Returns
Template | nullExample
const template = useQuery(api.templates.getTemplateById, { templateId });What This Does
This fetches a single template using its unique ID. Useful when you want to load a specific template to edit it or use it for logging. Returns null if the template doesn't exist or was deleted.
saveTemplate
mutationSave a new template or update existing one
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| name | string | Required | Template name |
| userId | string | Required | User ID |
| questions | CustomQuestion[] | Required | Array of custom questions |
Returns
Id<'templates'>Example
const id = await saveTemplate({ name: "Morning Routine", userId, questions: [...] });What This Does
This saves a custom template with its questions. If a template with the same name already exists for this user, it updates that one instead of creating a duplicate. This smart behavior means users can modify their templates without losing the original ID or creating clutter.
deleteTemplate
mutationDelete a template
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| templateId | Id<'templates'> | Required | Template document ID |
| userId | string | Required | User ID (for permission check) |
Returns
booleanExample
await deleteTemplate({ templateId, userId });What This Does
This permanently removes a template. It includes a security check to ensure users can only delete their own templates, not someone else's. This prevents unauthorized deletions and keeps user data private.
Payments
Stripe payment processing and payment record management
getUserPayments
queryGet all payments for the authenticated user
Parameters
No parameters
Returns
Payment[]Example
const payments = useQuery(api.payments.getUserPayments);What This Does
This retrieves the complete payment history for the current user, ordered from newest to oldest. It shows all their transactions, including successful payments, pending ones, and any failed attempts. Useful for displaying a billing history page.
getPaymentById
queryGet payment details by ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| paymentId | Id<'payments'> | Required | Payment document ID |
Returns
Payment | nullExample
const payment = useQuery(api.payments.getPaymentById, { paymentId });What This Does
This fetches detailed information about a specific payment. It includes a security check - users can only view their own payment records, not someone else's. If you try to access another user's payment, it returns null.
createCheckoutSession
actionCreate a Stripe checkout session for the authenticated user
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| priceId | string | Required | Stripe price ID |
| paymentMode | string | Optional | Payment mode ('subscription' or 'payment') |
| embeddedCheckout | boolean | Optional | Whether to use embedded checkout |
Returns
{ clientSecret: string, sessionId: string }Example
const session = await createCheckoutSession({ priceId: "price_123" });What This Does
This creates a Stripe checkout session, which is like opening a secure payment window. It initializes the payment process, creates a pending payment record, and returns credentials needed to display the Stripe payment form. The user completes payment in Stripe's secure interface.
getBySessionId
internalQueryGet payment by Stripe session ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| sessionId | string | Required | Stripe session ID |
Returns
Payment | nullWhat This Does
This internal function looks up a payment record using Stripe's session ID. It's used by webhook handlers to find and update the correct payment when Stripe sends notifications about payment status changes.
create
internalMutationCreate a new payment record
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | Id<'users'> | Required | User ID |
| stripeSessionId | string | Required | Stripe session ID |
| priceId | string | Required | Stripe price ID |
| status | string | Required | Payment status |
| productName | string | Required | Product name |
| paymentMode | string | Required | Payment mode |
| createdAt | number | Required | Creation timestamp |
Returns
Id<'payments'>What This Does
This internal function creates the initial payment record when a checkout session starts. It stores all the essential details about the payment attempt, including what's being purchased and who's purchasing it. The status typically starts as 'pending' until the payment completes.
recordStripePayment
internalMutationRecord a payment from Stripe webhook
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| stripeSessionId | string | Required | Stripe session ID |
| userIdOrEmail | string | Required | User ID or email |
| priceId | string | Optional | Stripe price ID |
| productName | string | Required | Product name |
| paymentMode | string | Required | Payment mode |
| amount | number | Required | Payment amount |
| currency | string | Required | Currency code |
| customerId | string | Optional | Stripe customer ID |
| customerEmail | string | Optional | Customer email |
| subscriptionId | string | Optional | Stripe subscription ID |
| subscriptionStatus | string | Optional | Subscription status |
Returns
Id<'payments'>What This Does
This is called by Stripe webhooks when a payment completes. It intelligently finds the user (trying multiple lookup methods), prevents duplicate records, and saves all the payment details. This ensures the database accurately reflects what happened in Stripe.
updatePaymentStatus
internalMutationUpdate payment status after checkout completion
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| sessionId | string | Required | Stripe session ID |
| status | string | Required | New payment status |
| customerId | string | Optional | Stripe customer ID |
| subscriptionId | string | Optional | Stripe subscription ID |
Returns
Id<'payments'>What This Does
This updates an existing payment record after a checkout is completed. It finds the payment by session ID and updates its status (like changing from 'pending' to 'complete'), and can also store additional information like the customer ID or subscription ID that Stripe provides.
Subscriptions
User subscription management and status checking
hasActiveSubscription
queryCheck if current user has an active subscription
Parameters
No parameters
Returns
booleanExample
const isActive = useQuery(api.userSubscriptions.hasActiveSubscription);What This Does
This is a simple yes/no check: does the current user have an active paid subscription? It checks both that the subscription status is 'active' or 'trialing' AND that it hasn't expired. Use this to control access to premium features or prompt users to upgrade.
getCurrentSubscription
queryGet current user's subscription details
Parameters
No parameters
Returns
Subscription | nullExample
const subscription = useQuery(api.userSubscriptions.getCurrentSubscription);What This Does
This retrieves the full subscription record for the current user, including details like when it expires, what status it's in, and the Stripe subscription ID. Returns null if the user doesn't have a subscription. Useful for displaying detailed subscription information in account settings.
createOrUpdate
internalMutationCreate or update a user subscription
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | Auth user ID |
| subscriptionId | string | Required | Stripe subscription ID |
| status | string | Required | Subscription status |
| currentPeriodEnd | number | Optional | Current period end timestamp |
Returns
Id<'userSubscriptions'>What This Does
This internal function handles creating new subscriptions or updating existing ones. It includes smart user lookup logic to handle different ID formats from authentication systems. If a subscription already exists for the user, it updates it; otherwise it creates a new one.
createOrUpdateFromStripe
internalMutationCreate or update a subscription from Stripe webhook data
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userIdOrEmail | string | Required | User ID or email |
| subscriptionId | string | Required | Stripe subscription ID |
| status | string | Required | Subscription status |
| currentPeriodEnd | number | Optional | Current period end timestamp |
| customerEmail | string | Optional | Customer email |
Returns
Id<'userSubscriptions'>What This Does
This is called by Stripe webhooks when subscription events occur (new subscription, renewal, cancellation, etc.). It has robust user lookup logic that tries multiple methods to find the right user, handles different authentication formats, and properly updates or creates subscription records to keep the database in sync with Stripe.
cancelByStripeId
internalMutationCancel a subscription by Stripe subscription ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| stripeSubscriptionId | string | Required | Stripe subscription ID |
| currentPeriodEnd | number | Optional | Current period end timestamp |
Returns
Id<'userSubscriptions'>What This Does
This marks a subscription as canceled when Stripe notifies us of a cancellation. It finds the subscription by Stripe's ID and updates its status to 'canceled'. Often, canceled subscriptions remain active until the current billing period ends, which is tracked by the currentPeriodEnd timestamp.
updateSubscription
internalMutationUpdate subscription from Stripe webhook
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| userId | string | Required | User ID |
| subscriptionId | string | Required | Stripe subscription ID |
| status | string | Required | Subscription status |
| currentPeriodEnd | number | Required | Current period end timestamp |
| metadata | object | Required | Subscription metadata |
Returns
Id<'userSubscriptions'>What This Does
Another webhook handler that processes subscription updates from Stripe. It's similar to createOrUpdateFromStripe but takes the user ID directly. This handles events like subscription renewals, plan changes, or status updates, keeping our database synchronized with Stripe's records.
getUserIdBySubscriptionId
internalQueryGet a user ID by subscription ID
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| subscriptionId | string | Required | Stripe subscription ID |
Returns
Id<'users'> | undefinedWhat This Does
This looks up which user owns a particular Stripe subscription. It's useful in webhook handlers when Stripe sends us an event about a subscription, and we need to figure out which user in our database it belongs to.
Waitlist
Feature waitlist management functions
isOnWaitlist
queryCheck if current user is on waitlist for a specific feature
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| feature | string | Required | Feature name |
Returns
booleanExample
const onWaitlist = useQuery(api.waitlist.isOnWaitlist, { feature: "ai-coach" });What This Does
This checks whether the current user has already joined the waitlist for a specific feature. It's useful for showing different UI - if they're already on the waitlist, show 'You're on the list!' instead of a 'Join Waitlist' button.
getWaitlistStats
queryGet waitlist stats for a specific feature
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| feature | string | Required | Feature name |
Returns
{ totalCount: number, recentSignups: number }Example
const stats = useQuery(api.waitlist.getWaitlistStats, { feature: "ai-coach" });What This Does
This provides statistics about a feature's waitlist - how many total people have signed up, and how many joined in the last 7 days. Great for showing social proof ('Join 247 others waiting for this feature!') or tracking interest over time.
getAllWaitlistEntries
queryGet all waitlist entries (admin only)
Parameters
No parameters
Returns
WaitlistEntry[]Example
const entries = useQuery(api.waitlist.getAllWaitlistEntries);What This Does
This retrieves every waitlist entry across all features. It's protected - only users with admin role can access it. Use this in admin dashboards to see who's interested in what features and plan development priorities accordingly.
joinWaitlist
mutationJoin the waitlist for a specific feature
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| feature | string | Required | Feature name |
Returns
{ success: boolean, message: string, waitlistId: Id<'waitlist'> }Example
const result = await joinWaitlist({ feature: "ai-coach" });What This Does
This adds the current user to the waitlist for a specific upcoming feature. It saves their user info (name and email) and when they signed up. It prevents duplicate entries - if you're already on that waitlist, it throws an error instead of adding you again.
leaveWaitlist
mutationRemove user from waitlist
Parameters
| Name | Type | Required | Description |
|---|---|---|---|
| feature | string | Required | Feature name |
Returns
{ success: boolean, message: string }Example
await leaveWaitlist({ feature: "ai-coach" });What This Does
This removes the current user from a feature's waitlist. Maybe they changed their mind or aren't interested anymore. If they're not actually on the waitlist, it throws an error. This gives users control over their waitlist signups.