Account Setup
Your organization (called a tenant internally) is the top-level container for every contact, pipeline, integration, and user in Olyron CRM. This guide walks through the org profile, branding, custom domains, and billing so your workspace is fully configured before you invite your team.
#Organization profile
Open Settings and choose Organization, or go directly to /dashboard/settings/organization. Every organization has a display name and a URL slug. The slug is the unique handle used in links and must be lowercase letters, numbers, and hyphens only (validated against ^[a-z0-9-]+$) — if the slug you pick is already taken by another tenant, the save is rejected.
- 1Set the organization nameEnter your agency or brand name. It cannot be blank — an empty name returns a 400 error.
- 2Choose a URL slugUse a short, unique handle (lowercase, numbers, hyphens). Uniqueness is enforced across all tenants.
- 3Save changesSaving sends a PUT to /api/organization. Every profile change is recorded to the audit log with the old and new values.
org_owner or agency_admin role. Members without one of these roles receive a 403 response.curl -X PUT https://app.olyron.com/api/organization \
-H "Content-Type: application/json" \
-d '{
"name": "Acme Benefits Group",
"slug": "acme-benefits"
}'#Branding: logo, favicon, and colors
Branding is stored inside the tenant record under tenants.settings.branding — there is no separate branding column. When you save, the branding object you send is merged (not replaced) into the existing settings, so you can update a single field without clearing the others.
logo_urlstring | null- Public URL of your uploaded logo.
favicon_urlstring | null- Public URL of your uploaded favicon.
primary_colorstring- Primary brand color as a hex value. Default #625fff.
secondary_colorstring- Secondary brand color. Default #7f22fe.
accent_colorstring- Accent color. Default #e12afb.
custom_domainstring | null- Normalized hostname for your branded workspace (see Custom domains below).
Uploading a logo or favicon
Logo and favicon files are uploaded straight from the browser to the Supabase Storage bucket named branding. Files are stored per tenant at {tenantId}/logo.{ext} and {tenantId}/favicon.{ext} with upsert enabled, so re-uploading overwrites the previous file at the same path. The upload returns a public URL that is written into the branding fields.
#Custom domains
There are two layers of custom-domain support. The simplest is the custom_domain branding field, which you set on the Organization page — the hostname is normalized before it is saved. The fuller mapping lives in the tenant_domains table, which backs hosted forms and landing pages and supports DNS verification.
Domains in tenant_domains are resolved through a provider selected by the DOMAIN_PROVIDER environment variable (or a per-row provider). Three providers exist: manual (CNAME/TXT only, no API calls), vercel, and cf_saas (Cloudflare for SaaS). The DNS record you need depends on the provider.
| Provider | Verification method | Record value |
|---|---|---|
| manual | CNAME | forms.olyron.com |
| vercel | CNAME | cname.vercel-dns.com |
| cf_saas | TXT | olyron-verify |
- 1Add the DNS recordAt your DNS host, create the record shown for your provider, pointing your hostname (e.g. app.youragency.com) at the target value.
- 2Trigger verificationCall POST /api/domains/:id/verify. Olyron polls the provider and updates the row's status.
- 3Wait for activeStatus moves through pending → verifying → active. On success verified_at is stamped; on failure the row records last_error and status becomes failed.
# List your tenant's custom domains
curl https://app.olyron.com/api/domains
# Poll the provider and update status for one domain
curl -X POST https://app.olyron.com/api/domains/DOMAIN_ID/verifyhostnamestring- The custom hostname you are mapping.
statusstring- One of pending, verifying, active, failed, or disabled.
providerstring- manual, vercel, or cf_saas.
verification_methodstring | null- cname or txt, depending on the provider.
verification_valuestring | null- The record value to point your DNS at.
verified_atstring | null- Timestamp set when the domain reaches active.
/dashboard/settings/domains) currently describes the model and links back to Organization. Apex-domain automation via Cloudflare for SaaS and Vercel is the V2 path; V1 relies on subdomains (for example tenant.forms.yourapp.com).#Plan and billing
Billing runs on Stripe. Each tenant carries a plan_tier (one of starter, professional, or agency) and, once billing is set up, a stripe_customer_id. Manage everything from Settings → Billing (/dashboard/settings/billing). Only the org_owner can start checkout or open the billing portal — other roles get a 403.
| Plan | Price / mo | User seats | Leads | Terminal req/day |
|---|---|---|---|---|
| Starter | $49 | 1 | 500 | 100 |
| Professional | $149 | 5 | 5,000 | 1,000 |
| Agency | $499 | Unlimited | Unlimited | 10,000 |
- 1Start checkout to upgradePOST /api/billing/create-checkout with a plan key. If the tenant has no Stripe customer yet, one is created and stored on stripe_customer_id. The response is a { url } to redirect the owner to Stripe Checkout.
- 2Manage an existing subscriptionPOST /api/billing/portal returns a Stripe Customer Portal { url } where the owner can change plans, update cards, and download receipts. Returns 404 if no billing account exists yet.
- 3Export billing recordsPOST /api/billing/export with an exportType of invoices, usage, revenue, or tax to download billing data (with the appropriate legal disclaimer).
curl -X POST https://app.olyron.com/api/billing/create-checkout \
-H "Content-Type: application/json" \
-d '{ "plan": "professional" }'
# -> { "url": "https://checkout.stripe.com/..." }#Deleting an organization
Deleting a tenant is permanent and cascades to all of its data. Only the org_owner can do it, and the request must be explicitly confirmed. After deletion the owner is signed out and the active-tenant cookie is cleared.
curl -X DELETE "https://app.olyron.com/api/organization?confirm=DELETE"#Endpoint reference
| Method & path | Purpose | Required role |
|---|---|---|
| GET /api/organization | Read the current org and its branding | Any tenant member |
| PUT /api/organization | Update name, slug, branding, settings | org_owner or agency_admin |
| DELETE /api/organization?confirm=DELETE | Permanently delete the org | org_owner |
| GET /api/domains | List custom domains for the tenant | Any tenant member |
| POST /api/domains/:id/verify | Poll the provider and update status | Any tenant member |
| POST /api/billing/create-checkout | Start a Stripe checkout session | org_owner |
| POST /api/billing/portal | Open the Stripe billing portal | org_owner |
| POST /api/billing/export | Export invoices, usage, revenue, or tax | Any tenant member |