Multi-tenant CRM with auth, consent management, Adobe AEP integration, and full-funnel entitlement for Webflow + Shopify.
Per-shop KV config isolation, tenant registry, auto-registration on install. Each Shopify store gets its own config, tokens, and sync schedule.
Email/password, Google OAuth, Shopify Customer Account (PKCE), JWT sessions, idle timeout, password reset, welcome emails, profile management.
GDPR/CCPA-compliant consent with TOS, cookie, marketing, newsletter, CCPA, and dynamic form types. Append-only audit trail with provenance.
Real-time sync across Shopify, Xano, Webflow CMS, GA4, and Adobe AEP. Cron every 15 min + webhook-driven single-user sync.
Streaming ingestion to AEP with SHA-256 hashed PII, XDM consent mapping, form bridge events, and product upsell commerce events.
Add data-crm-form="type" to any HTML form. Auto-creates tags, logs consent, fires GA4 events, and pushes to Adobe AEP.
Structured tags with categories (status, tier, segment, campaign, consent, marketing). Auto-inference, join table architecture, full-channel flow.
Customer redaction, data portability, shop redaction, self-service deletion, consent audit trail. All webhooks HMAC-verified.
CRM Auth Designer Extension with Config, Auth, Embeds, Plan, and Status tabs. Adobe AEP config, embed code generation, health checks.
| Field | Type | Description |
|---|---|---|
xano_base_url | string | Xano API base URL |
xano_api_key | secret | Xano API key |
shopify_store_domain | string | e.g., store.myshopify.com |
shopify_admin_token | secret | Shopify Admin API token (shpua_ prefix) |
shopify_refresh_token | secret | Shopify refresh token (shprt_ prefix, 90-day TTL) |
shopify_token_expires_at | number | Unix timestamp for token expiry |
webflow_cms_token | secret | Webflow CMS API token (via OAuth) |
webflow_collection_id | string | Webflow Customers collection ID |
webflow_site_id | string | Webflow site ID (from OAuth) |
ga4_measurement_id | string | GA4 Measurement ID (G-XXXXXXXXXX) |
ga4_api_secret | secret | GA4 Measurement Protocol secret |
auth_redirect_origin | string | CORS allowed origin (Webflow site URL) |
authMethods | object | Toggle email, Google, Shopify auth |
adobe_aep_enabled | boolean | Enable Adobe AEP streaming |
adobe_ims_org_id | string | Adobe IMS Org ID |
adobe_client_id | string | Adobe OAuth client ID |
adobe_client_secret | secret | Adobe OAuth client secret |
adobe_aep_dataset_id | string | AEP streaming dataset ID |
adobe_aep_sandbox | string | AEP sandbox name (default: prod) |
resend_api_key | secret | Resend transactional email API key |
| Key Pattern | Contents | Sensitivity |
|---|---|---|
tenant:{shop}:config | Per-tenant CrmSiteConfig | High |
tenants:index | JSON array of registered shops | Low |
platform:config | Shared platform credentials | High |
tag_table_ids | Xano table IDs for tags | Low |
sync:customers:last_run | ISO timestamp of last sync | Low |
adobe_token:{shop} | Cached Adobe IMS access token | High |
pkce:{state} | PKCE code_verifier (TTL) | Medium |
oauth_state:{uuid} | OAuth state + shop (10min TTL) | Medium |
reset:{token} | Password reset token (1h/24h TTL) | Medium |
| Variable | Source | Description |
|---|---|---|
XANO_BASE_URL | [vars] | Xano API endpoint |
AUTH_REDIRECT_ORIGIN | [vars] | CORS origin for auth redirects |
GOOGLE_CLIENT_ID | [vars] | Google OAuth client ID |
SHOPIFY_STORE_DOMAIN | [vars] | Default Shopify store domain |
SHOPIFY_SHOP_ID | [vars] | Shopify shop numeric ID |
SHOPIFY_CUSTOMER_ACCOUNT_CLIENT_ID | [vars] | Shopify Customer Account PKCE client |
RESEND_FROM_EMAIL | [vars] | From address for transactional email |
XANO_API_KEY | secret | Xano API key |
JWT_SECRET | secret | JWT signing secret |
GOOGLE_CLIENT_SECRET | secret | Google OAuth secret |
SHOPIFY_ADMIN_TOKEN | secret | Auto-set by OAuth install flow |
WEBFLOW_CMS_TOKEN | secret | Auto-set by Webflow OAuth |
RESEND_API_KEY | secret | Resend API key |
GA4_API_SECRET | secret | GA4 Measurement Protocol secret |
ADMIN_KEY | secret | Bearer token for admin endpoints |
Config is resolved per-tenant with the following precedence (highest first):
tenant:{shop}:config (per-tenant overrides)wrangler secret put valuesLegacy single-tenant mode falls back to the crm_config KV key when no tenant is specified.
| Feature | Shared ($69) | Private ($325) | Enterprise |
|---|---|---|---|
| Auth (email, Google, Shopify) | ✓ | ✓ | ✓ |
| Consent management | ✓ | ✓ | ✓ |
| Tag system | ✓ | ✓ | ✓ |
| Shopify sync | ✓ | ✓ | ✓ |
| Webflow CMS sync | ✓ | ✓ | ✓ |
| GA4 Measurement Protocol | ✓ | ✓ | ✓ |
| Form bridge | ✓ | ✓ | ✓ |
| GDPR/CCPA compliance | ✓ | ✓ | ✓ |
| Resend transactional email | ✓ | ✓ | ✓ |
| Adobe Experience Platform | — | ✓ | ✓ |
| Dedicated infrastructure | — | ✓ | ✓ |
| Custom domain | — | ✓ | ✓ |
| Salesforce / HubSpot / Klaviyo | — | — | ✓ |
| Attentive / Braze | — | — | ✓ |
| SLA & dedicated support | — | — | ✓ |
| Ingress | Tenant ID Source |
|---|---|
| Shopify embedded app | Session → shop domain |
| Shopify webhooks | X-Shopify-Shop-Domain header |
| Storefront embeds | ?shop= query param |
| Webflow extension | ?shop= query param |
| OAuth install flow | ?shop= query param |
| Cron/scheduled | Iterates tenants:index |
| Admin endpoints | ?shop= + Bearer token |
| # | Direction | Trigger |
|---|---|---|
| 1 | Shopify → Xano → Webflow → GA4 | Cron (*/15 * * * *) or webhook |
| 2 | Webflow → Xano → Shopify → GA4 | Webflow CMS item changed webhook |
| 3 | UCP → Xano → Shopify + Webflow → GA4 | POST /ucp/tags or POST /tags/user |
| 4 | Form Bridge → UCP → All | data-crm-form submission |
| 5 | Shopify → Xano → Resend | Customer create (welcome email) |
| 6 | Shopify → Worker (compliance) | POST /api/webhooks (GDPR) |
| 7 | Shopify → Xano → Adobe AEP | Customer update (if AEP enabled) |
Full specification: FUNCTIONAL-SPEC.md v1.2