Loopnote API Documentation
This document provides a comprehensive overview of all backend API endpoints available in the Loopnote platform, grouped logically by resource.
1. Widget & Public Endpoints
These endpoints power the public-facing feedback widget embedded on customer websites.
GET /api/widget-settings
Description: Serves configuration settings and statically assigns A/B test variants to anonymous visitors based on their session token.
- Authentication: None
- Query Parameters:
site_id(String, Required): The unique ID of the site.token(String, Optional): An anonymous user token used to provide deterministic (sticky) A/B test assignments.
- Success Response (200):
{ "plan": "agency", "settings": { "position": "bottom-right", "accent_color": "#18181b", "question_text": "How was your experience?", "_ab_test_id": "test_123", "_ab_variant": "A" } } - Error Responses:
400:{"error": "site_id required"}404:{"error": "Invalid site_id"}500:{"error": "Internal server error"}
POST /api/feedback
Description: Collects user feedback submitted via the widget and asynchronously dispatches payloads to active external integrations (Zapier, Slack, WhatsApp).
- Authentication: None
- Rate Limiting: Free tier sites are securely capped at 100 responses per calendar month. Further requests return a 429.
- Request Body:
{ "site_id": "uuid", "rating": 5, "message": "Great website!", "page_url": "/pricing", "trigger_fired": "exit_intent", "time_on_page_at_trigger": 45, "device_type": "desktop", "visit_count": 2, "is_returning_visitor": true, "anon_user_token": "token_abc", "ab_test_id": "test_123", "variant_seen": "A" } - Success Response (201):
{ "success": true } - Error Responses:
400:{"error": "site_id is required"}or{"error": "rating must be 1–5"}404:{"error": "Invalid site_id"}429:{"error": "Monthly response limit reached. Upgrade to Pro Builder."}
GET /api/has-reply
Description: Checks if an anonymous user has received any replies to their previous feedback in order to show notification badges in the widget.
- Authentication: None
- Query Parameters:
site_id(String, Required)token(String, Required): The visitor's anonymous tracking token.
- Success Response (200):
{ "hasReply": true, "threads": [ { "feedback_id": "fb_123", "original_rating": 3, "original_message": "Needs dark mode", "original_date": "2026-04-14T...Z", "thread_locked": false, "messages": [ { "id": "rep_1", "sender": "owner", "text": "We just added it!", "created_at": "..." } ] } ] }
POST /api/contact
Description: Submits a contact or support form request from the public website via integration to FormSubmit.
- Authentication: None
- Request Body:
{ "name": "John Doe", "email": "john@example.com", "message": "I have a question about pricing." } - Success Response (200):
{"success": true} - Error Responses:
400(Missing fields),500(Failed to send).
2. Developer API (v1)
These endpoints are exposed externally for customer access via programmatic API Keys.
GET /api/v1/feedback
Description: Retrieves paginated and date-filtered feedback submissions for a specific site.
- Authentication: API Key (
Bearer {key_prefix}_{key}) - Query Parameters:
site_id(String, Required)limit(Number, Optional): Max 100, default 50.page(Number, Optional): Default 1.from(Date String, Optional): Filter start date.to(Date String, Optional): Filter end date.
- Success Response (200):
{ "data": [{ "id": "...", "trigger_type": "...", "response_text": "...", "rating": 5, "created_at": "..." }], "pagination": { "page": 1, "limit": 50, "total": 120, "has_more": true } } - Error Responses:
400:{"error": "site_id query parameter is required"}401:{"error": "Invalid API Key"}403:{"error": "Site not found or access denied"}
GET /api/v1/sites
Description: Fetches a list of all sites belonging to the authenticated account's user.
- Authentication: API Key (
Bearer {key}) - Success Response (200):
{ "data": [{ "id": "...", "name": "My Site", "domain": "example.com", "plan": "pro" }] }
GET /api/v1/summary
Description: Fetches the most recently generated AI qualitative summary for a given site.
- Authentication: API Key (
Bearer {key}) - Query Parameters:
site_id(String, Required) - Success Response (200):
{ "data": { "id": "...", "summary": { "overall_sentiment": "positive", "top_issues": [...] }, "created_at": "..." } }
3. Dashboard Analytics & Management
Used by the Dashboard to generate intelligence, manage feedback, and handle replies.
POST /api/ai-summary
Description: Analyzes up to 30 days of recent feedback using Google Gemini to generate a structured JSON qualitative insights report.
- Authentication: Supabase Bearer Token
- Request Body:
{"site_id": "uuid"} - Success Response (200):
{ "success": true, "summary": { "overall_sentiment": "positive", "satisfaction_score": 8, "top_positives": ["UI", "Speed"], "action_items": ["Fix mobile menu"], "critical_insights": [...] } } - Error Responses:
401(Unauthorized),403(Forbidden),429(AI API quota exceeded).
POST /api/page-ai-summary
Description: Generates a highly specific UX analysis report based entirely on feedback targeted at a specific URL route.
- Authentication: Supabase Bearer Token
- Request Body:
{"site_id": "uuid", "url_path": "/pricing"} - Success Response (200):
{"success": true, "summary": { "page_sentiment": "negative", "core_problem": "..." }}
GET /api/revenue-report
Description: Computes an estimated revenue leak report across the account by analyzing drop-off triggers against average order value and traffic data.
- Authentication: None strictly enforced by token (Relies on data availability), but inherently restricted to Agency tier plans.
- Query Parameters:
site_id(String, Required) - Success Response (200):
{ "site_id": "uuid", "total_estimated_monthly_loss": 1250.00, "trend": "worsening", "top_issues": [ { "trigger_type": "pricing_exit", "estimated_monthly_loss": 500, "recommendation": "Add comparison FAQ..." } ] }
DELETE /api/delete-feedback
Description: Hard-deletes a specific feedback entry.
- Authentication: Supabase Bearer Token (Verifies site ownership)
- Request Body:
{"feedback_id": "uuid"} - Success Response (200):
{"success": true}
POST /api/replies
Description: Sends a reply to an existing feedback thread. Differentiates between 'owner' (dashboard) and 'user' (widget).
- Authentication: Supabase Bearer Token (if sender = 'owner'); Widget anonymous token (if sender = 'user').
- Request Body:
{ "feedback_id": "uuid", "reply_text": "Thanks! We will look into it.", "sender": "owner", "token": "optional_if_user" } - Success Response (201):
{"success": true, "reply": { ... }} - Error Responses:
401,403,409(User already sent follow-up).
GET /api/replies
Description: Fetches all replies corresponding to a specific feedback ID.
- Authentication: Supabase Bearer Token (Owner side only)
- Query Parameters:
feedback_id(String, Required)
4. A/B Testing Management
Endpoints for configuring, reading, and interacting with A/B Tests.
GET /api/ab-tests
Description: Retrieves all A/B tests associated with a site.
- Query Parameters:
site_id
POST /api/ab-tests
Description: Initiates a new A/B Test definition ensuring no overlapping tests are running for the same dimension.
- Request Body:
{"site_id": "uuid", "dimension": "question_text", "variants": [{ "id": "A", "value": "Test 1" }]}
POST /api/ab-tests/track-view
Description: Increments the view count for a designated A/B test variant when a widget physically renders it.
- Request Body:
{"ab_test_id": "uuid", "variant_id": "A"}
GET /api/ab-tests/[id]
Description: Calculates the live statistical performance (conversion rate) of a test by comparing views mathematically against feedback received.
- Path Parameter:
id(A/B test ID)
PATCH /api/ab-tests/[id]
Description: Manipulates the lifecycle of a test (pause, resume, or finish and permanently apply winner to widget settings).
- Request Body:
{"action": "apply_winner", "winner_variant_id": "A"}
DELETE /api/ab-tests/[id]
Description: Permanently deletes an A/B test.
5. Account, Security & Agency Features
Endpoints meant strictly for tier upgrades, Developer API limits, and Sub-accounts.
GET / POST /api/api-keys
Description: Lists or provisions programmatic API keys (SHA-256 hashed on storage). Returns raw key only once on creation.
- Authentication: Supabase Bearer Token + Agency Tier Validation.
- POST Body:
{"key_name": "Zapier Integration"}
DELETE /api/api-keys/[id]
Description: Securely revokes an API key (Soft delete flag is_active = false).
GET / POST /api/client-accounts
Description: Lists or provisions white-labeled client sub-accounts managed under an Agency user.
- Authentication: Supabase Token + Agency Tier Validation.
PATCH /api/client-accounts/[id]
Description: Updates client account profiles or links/unlinks a specific Site to the designated sub-account.
- Request Body:
{"action": "assign_site", "site_id": "uuid"}
DELETE /api/client-accounts/[id]
Description: Deletes a client sub-account from the Agency's control.
POST /api/integrations
Description: Upserts integrations (Slack webhook, Zapier webhook, WhatsApp Meta Credentials) into the site settings JSON payload.
- Authentication: Supabase Token + Agency Tier Validation.
POST /api/integrations/whatsapp/test
Description: Validates WhatsApp Meta Cloud API configuration by sending a hardcoded test template message to the recipient's phone number.
6. Payments (Razorpay)
POST /api/razorpay/create-order
Description: Safely maps a requested pricing tier into secure billing values and proxies an Order creation call to Razorpay.
- Authentication: None (Internal user_id passed)
- Request Body:
{"plan": "pro", "billing_cycle": "annual", "currency": "INR", "user_id": "uuid"} - Success Response:
{"order_id": "order_abc", "amount": 2199900, "currency": "INR"}
POST /api/razorpay/verify-payment
Description: The strict verification loop that ensures Razorpay HMAC SHA256 signatures match prior to finalizing database Upserts into the subscriptions table.
- Authentication: Signature Validation
- Request Body:
{"razorpay_order_id": "...", "razorpay_signature": "...", "plan": "...", "amount": ...}
7. Admin Operations
Secured routes executing system-wide operations on behalf of Loopnote Founders.
POST /api/admin/action
Description: Enables execution of overriding manual actions (e.g. bypassing payment gateway to grant a manual upgrade).
- Body Options:
{"action": "manual_upgrade", "payload": { "user_id": "...", "plan": "agency" }}
POST /api/admin/alert
Description: Triggers an alert entry to the DB and fires an immediate email notification via Resend notifying founders of critical tier drops/errors.
- Request Body:
{"alert_type": "Payment_Failure", "user_id": "...", "message": "..."}
PATCH /api/admin/alert
Description: Resolves an admin alert.
POST /api/support
Description: Relays logged-in user feedback securely to founder tracking emails via Resend.
- Authentication: Supabase Bearer Token