Skip to main content

Custom integration

If you're not on Shopify / WooCommerce yet, this is the recipe.

1. Listen for subscription events in your billing system

Hook your own billing webhooks (Stripe, Chargebee, anything) for subscription.created and subscription.renewed. On either event, upsert a Genvoris customer:

import fetch from 'node-fetch'

async function syncCustomer(stripeSub: any) {
const planMap = {
price_basic: 'pln_basic_id',
price_pro: 'pln_pro_id',
}
await fetch('https://genvoris.org/api/v1/customers', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.GENVORIS_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
externalId: stripeSub.customer, // Stripe cust id
email: stripeSub.customer_email,
planId: planMap[stripeSub.items.data[0].price.id],
metadata: { stripe_subscription_id: stripeSub.id },
}),
})
}

2. Cancel / pause appropriately

// On subscription.deleted
await fetch(`https://genvoris.org/api/v1/customers/${ourCustomerId}`, {
method: 'DELETE',
headers: { 'Authorization': `Bearer ${process.env.GENVORIS_API_KEY}` },
})

// On subscription.paused
await fetch(`https://genvoris.org/api/v1/customers/${ourCustomerId}`, {
method: 'PATCH',
headers: {
'Authorization': `Bearer ${process.env.GENVORIS_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({ status: 'PAUSED' }),
})

3. Mint a session on each product page render

Server-side render a session token for the logged-in customer:

// Express handler for /product/:slug
app.get('/product/:slug', async (req, res) => {
const customerId = await db.getGenvorisCustomerId(req.user.id)
const r = await fetch(`https://genvoris.org/api/v1/customers/${customerId}/sessions`, {
method: 'POST',
headers: { 'Authorization': `Bearer ${process.env.GENVORIS_API_KEY}` },
})
const { token } = await r.json()
res.render('product', { tryonToken: token })
})

4. Drop the widget into the template

<script
src="https://api.genvoris.org/widget.js"
defer
data-api-key="<%= process.env.GENVORIS_PUBLIC_KEY %>"
data-end-customer-token="<%= tryonToken %>"
></script>

5. Handle the end_customer_quota paywall

The widget emits a genvoris:quota DOM event when the user hits 402. Listen for it and show your own upgrade modal:

window.addEventListener('genvoris:quota', (e) => {
const { reason, used, limit } = e.detail
showUpgradeModal({ reason, used, limit })
})

That's the entire integration.