Connect your stack
Optiview works with tools your team already uses
Optiview understands visitor behavior. Your GTM, Adobe, CMS, or app decides what visitors see — calmer modules, fewer interruptions, better continuity.
What teams do with Optiview
| Tool | Typical experience change |
|---|---|
| GTM | Suppress interruptions when visitors are uncertain |
| Adobe Target | Show calmer experiences when friction increases |
| React | Adapt modules before login |
| Segment | Pass anonymous context downstream |
| AEM | Swap content based on visitor state |
Optiview observes and suggests. It does not render banners, replace your CMS, or require a new component library.
Example moments → experiences
Plain-language intent first. Expand any row for copy-ready implementation snippets.
Payment feels unclear on mobile
GTM- When
- Visitor is rechecking financing and pace is slowing.
- Experience could
- Show simpler payment ranges and hold back aggressive pop-ups.
Show implementation →
Payment feels unclear on mobile
GTMGTM snippet
// Custom Event: si_personalization_signal
// Branch on canonical IDs — NOT labels in panels
if ({{DLV - si.context.traffic_source_type}} === 'paid_search'
&& {{DLV - si.commercial_signals.blocker_ids}}.includes('financing_or_payment_uncertainty')) {
showFinancingReassuranceModule();
}
if ({{DLV - si.session_dynamics.decision_pace}} === 'slow') delayInterruption();Serious comparison before deciding
React- When
- Visitor keeps returning to the same finalists.
- Experience could
- Keep shortlist visible and highlight key differences only.
Show implementation →
Serious comparison before deciding
ReactReact snippet
const cs = envelope?.si?.commercial_signals;
if (cs?.recommended_next_actions?.some(a => a.action_id === "support_comparison")) {
return <ComparisonTray />;
}Overwhelmed on mobile
GTM- When
- Evening mobile visit with slowing pace.
- Experience could
- Delay interruptions; keep navigation calm.
Show implementation →
Overwhelmed on mobile
GTMGTM snippet
// si.session_dynamics.decision_pace === 'slow'
// si.context.device_class === 'mobile'
// → delayInterruption() or hide sticky CTAFor builders — implementation examples
For engineers: the tag pushes si_personalization_signal with stable *_id fields to branch on — not human labels from the Live panel.
Example dataLayer payload
window.dataLayer.push({
"event": "si_personalization_signal",
"si": {
"context": {
"traffic_source_type": "paid_search",
"device_class": "mobile",
"visit_recency_bucket": "returning_30d"
},
"session_dynamics": {
"decision_pace": "slow",
"engagement_trend": "deepening"
},
"commercial_signals": {
"status": "active",
"commercial_state_id": "hesitating",
"blocker_ids": [
"financing_or_payment_uncertainty"
],
"recommended_next_actions": [
{
"action_id": "promote_financing_clarity"
}
]
}
}
});Server / webhook
Server / webhook
POST /your/collector
{
"event": "si_personalization_signal",
"si": {
"commercial_signals": {
"status": "active",
"commercial_state_id": "hesitating",
"blocker_ids": ["financing_or_payment_uncertainty"],
"recommended_next_actions": [{ "action_id": "promote_financing_clarity" }]
}
}
}Browser event listener
Browser event listener
window.addEventListener("si:personalization-signal", (e) => {
const cs = e.detail?.si?.commercial_signals;
if (cs?.status !== "active") return;
const actionId = cs.recommended_next_actions?.[0]?.action_id;
if (cs.commercial_state_id === "hesitating" && actionId === "promote_financing_clarity") {
// render your financing module
}
});Adobe Target
Adobe Target
// Profile parameters — use flat IDs from pushCommercialSignalsToTargetProfile
// si_commercial_state_id, si_blocker_ids (comma-separated), si_top_action_id
if ({{DLV - si.commercial_signals.commercial_state_id}} === 'hesitating') suppressPopup();