Analytics — TelemetryDeck
Komplett spesifikasjon av analytics-oppsettet i TelemetryDeck for im-ios.
Arkitektur
heading.anchorLabel┌──────────────┐ ┌──────────────────┐ ┌─────────────────┐│ iOS App │────▶│ TelemetryDeck │────▶│ 6 Dashboards ││ Analytics.swift │ (anonymisert) │ │ 32 Insights │└──────────────┘ └──────────────────┘ └─────────────────┘- SDK: TelemetryDeck Swift SDK 2.11.0
- App ID:
CE8DB336-B6B9-4B6A-A725-915EE4B2E24F - GDPR: Ingen consent nødvendig — dobbel-hashing anonymisering på device
- Test Mode:
#if DEBUG→config.testMode = true - Kilde:
iosApp/Services/Analytics.swift
Signal-katalog
heading.anchorLabel23 signaltyper fordelt på 7 kategorier.
Retention
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
app.launched | — | App init (kaldstart) | 1/dag |
app.foreground | — | ScenePhase → .active | 1-3/dag |
Conversion Funnel
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
onboarding.completed | personalized: Bool | Onboarding ferdig | 1x totalt |
onboarding.skipped | — | Bruker hopper over | 1x totalt |
impulse.captured | classification: contraction/expansion, source: direct/checkin/parent | Impulse opprettet | 0-5/dag |
session.started | classification: contraction/expansion | Session opprettet | 0-3/dag |
session.stepCompleted | classification, step: 1-4 | Steg fullført (forrige steg) | 0-12/dag |
session.completed | classification, durationSeconds: Int | Session fullført | 0-3/dag |
session.abandoned | classification, lastStep: Int | Session forlatt | 0-3/dag |
checkin.completed | outcome: positive/contraction/expansion | Sjekk-inn vurdert | 0-3/dag |
checkin.converted | classification: contraction/expansion | Sjekk-inn → impulse | 0-2/dag |
Monetization
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
paywall.shown | trigger: quota | Paywall vises | 0-2/dag |
paywall.dismissed | trigger: quota | Paywall lukkes | 0-2/dag |
purchase.completed | tier: impulse/pro, fromTrial: Bool | Kjøp godkjent | 1x totalt |
purchase.failed | tier, errorType: verification_failed/etc | Kjøp feilet | Sjelden |
trial.started | — | Onboarding fullført | 1x totalt |
trial.expired | — | Trial utløpt uten kjøp | 1x totalt |
Engagement
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
insights.viewed | product: insight/areas/layers/transformations/flow | Insight-card synlig | 1-5/dag |
insight.feedback | product: narrative/areas/layers/transformations, signal: up/down | Thumbs up/down på innsiktskort | 0-4/dag |
journey.searched | — | Søk i Journey | 0-2/dag |
feedback.submitted | hasRating: Bool | Feedback sendt | Sjelden |
Errors
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
error.ai_workload | workloadType: guidance/summary/classification, step: Int? | AI-kall feilet | Sjelden |
error.classification_rejected | — | AI avviste impulse | Sjelden |
Navigation
heading.anchorLabel| Signal | Parametere | Trigger | Frekvens |
|---|---|---|---|
navigationPathChanged | Tab name: Home/Insights/Journey/Profile | Tab-bytte | 3-10/dag |
Signal-budsjett
heading.anchorLabel| Metrikk | Verdi |
|---|---|
| Estimert per aktiv bruker/dag | ~5-8 signaler |
| Estimert per aktiv bruker/mnd | ~150-240 signaler |
| Free tier (100K/mnd) | ~450 MAU |
| Paid tier (1M/mnd) | ~4 500 MAU |
Dashboard 1: Retention & Growth
heading.anchorLabel4 insights — forstå brukerbase og retensjon.
1.1 DAU (Daily Active Users)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | app.foreground |
| Counting | Count Users |
| Granularity | Day |
| Chart Type | Line Chart |
| Show Expanded | Ja |
1.2 WAU (Weekly Active Users)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | app.foreground |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Line Chart |
1.3 MAU (Monthly Active Users)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | app.foreground |
| Counting | Count Users |
| Granularity | Month |
| Chart Type | Line Chart |
1.4 New Users (First Launch)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | app.launched |
| Counting | Count Users |
| Granularity | Day |
| Chart Type | Bar Chart |
Dashboard 2: Conversion Funnel
heading.anchorLabel5 insights — konvertering fra onboarding til session completion.
2.1 Primary Conversion Funnel
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Funnel |
| Chart Type | Funnel |
| Show Expanded | Ja |
Steps:
| # | Step | Signal |
|---|---|---|
| 1 | App Launched | app.launched |
| 2 | Onboarding Complete | onboarding.completed |
| 3 | First Impulse | impulse.captured |
| 4 | Session Started | session.started |
| 5 | Session Completed | session.completed |
TQL
{ "queryType": "funnel", "dataSource": "telemetry-signals", "granularity": "all", "steps": [ {"name": "App Launched", "filter": {"type": "selector", "dimension": "type", "value": "app.launched"}}, {"name": "Onboarding Complete", "filter": {"type": "selector", "dimension": "type", "value": "onboarding.completed"}}, {"name": "First Impulse", "filter": {"type": "selector", "dimension": "type", "value": "impulse.captured"}}, {"name": "Session Started", "filter": {"type": "selector", "dimension": "type", "value": "session.started"}}, {"name": "Session Completed", "filter": {"type": "selector", "dimension": "type", "value": "session.completed"}} ]}2.2 Check-in → Impulse Funnel
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Funnel |
| Chart Type | Funnel |
Steps:
| # | Step | Signal |
|---|---|---|
| 1 | Check-in Done | checkin.completed |
| 2 | Converted | checkin.converted |
| 3 | Session Started | session.started |
| 4 | Session Completed | session.completed |
TQL
{ "queryType": "funnel", "dataSource": "telemetry-signals", "granularity": "all", "steps": [ {"name": "Check-in Done", "filter": {"type": "selector", "dimension": "type", "value": "checkin.completed"}}, {"name": "Converted", "filter": {"type": "selector", "dimension": "type", "value": "checkin.converted"}}, {"name": "Session Started", "filter": {"type": "selector", "dimension": "type", "value": "session.started"}}, {"name": "Session Completed", "filter": {"type": "selector", "dimension": "type", "value": "session.completed"}} ]}2.3 Onboarding: Complete vs Skip
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | (tom) |
| Filter | OR: onboarding.completed, onboarding.skipped |
| Counting | Count Signals |
| Top N Dimension | type |
| Chart Type | Donut |
2.4 Impulse Capture Sources
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | impulse.captured |
| Counting | Count Signals |
| Top N Dimension | source |
| Chart Type | Donut |
2.5 Check-in Outcomes
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | checkin.completed |
| Counting | Count Signals |
| Top N Dimension | outcome |
| Chart Type | Donut |
Dashboard 3: Monetization
heading.anchorLabel6 insights — trial-konvertering, revenue og churn.
3.1 Trial → Purchase Funnel
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Funnel |
| Chart Type | Funnel |
Steps:
| # | Step | Signal |
|---|---|---|
| 1 | Trial Started | trial.started |
| 2 | Paywall Shown | paywall.shown |
| 3 | Purchase Completed | purchase.completed |
TQL
{ "queryType": "funnel", "dataSource": "telemetry-signals", "granularity": "all", "steps": [ {"name": "Trial Started", "filter": {"type": "selector", "dimension": "type", "value": "trial.started"}}, {"name": "Paywall Shown", "filter": {"type": "selector", "dimension": "type", "value": "paywall.shown"}}, {"name": "Purchase Completed", "filter": {"type": "selector", "dimension": "type", "value": "purchase.completed"}} ]}3.2 Paywall: Shown → Converted
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Funnel |
| Chart Type | Funnel |
Steps:
| # | Step | Signal |
|---|---|---|
| 1 | Paywall Shown | paywall.shown |
| 2 | Purchase Completed | purchase.completed |
TQL
{ "queryType": "funnel", "dataSource": "telemetry-signals", "granularity": "all", "steps": [ {"name": "Paywall Shown", "filter": {"type": "selector", "dimension": "type", "value": "paywall.shown"}}, {"name": "Purchase Completed", "filter": {"type": "selector", "dimension": "type", "value": "purchase.completed"}} ]}3.3 Purchases Over Time
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | purchase.completed |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Bar Chart |
3.4 Purchases by Tier
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | purchase.completed |
| Counting | Count Signals |
| Top N Dimension | tier |
| Chart Type | Donut |
3.5 Trial Expirations (Churned)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | trial.expired |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Bar Chart |
3.6 Purchase Failures by Type
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | purchase.failed |
| Counting | Count Signals |
| Top N Dimension | errorType |
| Chart Type | Bar Chart |
Dashboard 4: Engagement
heading.anchorLabel6 insights — session-helse, insights-bruk, og aktivitetsmiks.
4.1 Session Step-by-Step Funnel
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Advanced Query (TQL) |
| Chart Type | Funnel |
| Show Expanded | Ja |
Steps:
| # | Step | Signal | Parameter-filter |
|---|---|---|---|
| 1 | Started | session.started | — |
| 2 | Step 1 | session.stepCompleted | step = 1 |
| 3 | Step 2 | session.stepCompleted | step = 2 |
| 4 | Step 3 | session.stepCompleted | step = 3 |
| 5 | Step 4 | session.stepCompleted | step = 4 |
| 6 | Completed | session.completed | — |
Krever compound filters per steg — bruk TQL:
{ "queryType": "funnel", "dataSource": "telemetry-signals", "granularity": "all", "steps": [ {"name": "Started", "filter": {"type": "selector", "dimension": "type", "value": "session.started"}}, {"name": "Step 1", "filter": {"type": "and", "fields": [ {"type": "selector", "dimension": "type", "value": "session.stepCompleted"}, {"type": "selector", "dimension": "step", "value": "1"} ]}}, {"name": "Step 2", "filter": {"type": "and", "fields": [ {"type": "selector", "dimension": "type", "value": "session.stepCompleted"}, {"type": "selector", "dimension": "step", "value": "2"} ]}}, {"name": "Step 3", "filter": {"type": "and", "fields": [ {"type": "selector", "dimension": "type", "value": "session.stepCompleted"}, {"type": "selector", "dimension": "step", "value": "3"} ]}}, {"name": "Step 4", "filter": {"type": "and", "fields": [ {"type": "selector", "dimension": "type", "value": "session.stepCompleted"}, {"type": "selector", "dimension": "step", "value": "4"} ]}}, {"name": "Completed", "filter": {"type": "selector", "dimension": "type", "value": "session.completed"}} ]}4.2 Completion: Contraction vs Expansion
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | session.completed |
| Counting | Count Signals |
| Top N Dimension | classification |
| Chart Type | Donut |
4.3 Session Drop-off: Last Step Before Abandon
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | session.abandoned |
| Counting | Count Signals |
| Top N Dimension | lastStep |
| Chart Type | Bar Chart |
4.4 Insights: Which Products Get Viewed
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | insights.viewed |
| Counting | Count Signals |
| Top N Dimension | product |
| Chart Type | Bar Chart |
4.5 Insights Views Over Time
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | insights.viewed |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Line Chart |
4.6 Daily Activity Mix
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | (tom) |
| Filter | OR: impulse.captured, session.started, checkin.completed |
| Counting | Count Signals |
| Granularity | Day |
| Top N Dimension | type |
| Chart Type | Bar Chart |
Dashboard 5: Errors & Friction
heading.anchorLabel3 insights — oppdage tekniske problemer som blokkerer brukere.
5.1 AI Errors Over Time
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | error.ai_workload |
| Counting | Count Signals |
| Granularity | Day |
| Chart Type | Bar Chart |
| Show Expanded | Ja |
5.2 AI Errors: Which Workloads Fail
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | error.ai_workload |
| Counting | Count Signals |
| Top N Dimension | workloadType |
| Chart Type | Donut |
5.3 Classification Rejections
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | error.classification_rejected |
| Counting | Count Signals |
| Granularity | Week |
| Chart Type | Bar Chart |
Dashboard 6: AI Product Quality
heading.anchorLabel7 insights — brukertilfredshet med AI-genererte dataprodukter (thumbs up/down).
Basert på
insight.feedback-signalet. Fires ved thumbs up/down på innsiktskort, IKKE ved reverseringer.
6.1 Insight Feedback Volume
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | insight.feedback |
| Counting | Count Signals |
| Granularity | Week |
| Chart Type | Bar Chart |
| Show Expanded | Ja |
Adoption-monitor. Forventet: 10-20% av insights-visninger gir feedback.
6.2 Feedback: Thumbs Up vs Down
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | insight.feedback |
| Counting | Count Signals |
| Top N Dimension | signal |
| Chart Type | Donut |
Overordnet temperatur. Forventet 60-80% up. Down > 50% = kvalitetsproblem.
6.3 Feedback Volume by Product
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | insight.feedback |
| Counting | Count Signals |
| Top N Dimension | product |
| Chart Type | Bar Chart |
Hvilke kort som får mest feedback. Kryss-referer med 4.4 (views) for reach vs engagement.
6.4 Thumbs Down by Product
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Values Breakdown (Top N) |
| Signal Type | insight.feedback |
| Filter | AND: signal type insight.feedback + selector signal = down |
| Counting | Count Signals |
| Top N Dimension | product |
| Chart Type | Bar Chart |
| Show Expanded | Ja |
Viktigste insight. Høy thumbs-down på
narrative= AI-prompt trenger tuning. Høy påareas/layers= presentasjon treffer ikke.
6.5 Thumbs Up Trend per Product
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | insight.feedback |
| Filter | AND: signal type insight.feedback + selector signal = up |
| Counting | Count Signals |
| Granularity | Week |
| Top N Dimension | product |
| Chart Type | Line Chart |
Trendlinje per produkt. Måler om AI-prompt-endringer forbedrer tilfredshet over tid.
6.6 Users Giving Feedback (unique)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | insight.feedback |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Line Chart |
Sammenlign med 4.5 (insights views, unique users). Mål: feedback users / viewed users > 15%.
6.7 Insights Views Over Time (Monitor)
heading.anchorLabel| Felt | Verdi |
|---|---|
| Query Type | Time Series |
| Signal Type | insights.viewed |
| Counting | Count Users |
| Granularity | Week |
| Chart Type | Line Chart |
Kill-switch. Duplikat av 4.5, plassert her for å overvåke om feedback-innføring reduserer engagement. Views-drop > 10% = vurder å fjerne mekanismen.
Kall-steder i koden
heading.anchorLabelHvor hvert signal fires fra i iOS-appen.
| Signal | Fil | Kontekst |
|---|---|---|
app.launched | Analytics.swift → initialize() | App init |
app.foreground | ImpulseApp.swift → handleScenePhaseChange(.active) | Forgrunn |
onboarding.completed | ImpulseApp.swift → onboarding onComplete | Onboarding ferdig |
onboarding.skipped | OnboardingView.swift → skip-knapp | Hopper over |
trial.started | ImpulseApp.swift → etter onboardingCompleted | Ny bruker |
impulse.captured | UnifiedImpulseEditorView.swift → lagring | Impulse opprettet |
session.started | UnifiedSessionView.swift → onSessionCreated | Session opprettet |
session.stepCompleted | UnifiedSessionView.swift → onStepAdvanced | Steg avansert |
session.completed | UnifiedSessionView.swift → onSessionCompleted | Session ferdig |
session.abandoned | UnifiedSessionView.swift → cleanupIfNeeded | Forlatt |
checkin.completed | CheckInEditorView.swift → AI assessment ferdig | Sjekk-inn OK |
checkin.converted | CheckInEditorView.swift → convert-knapp | Konvertert |
paywall.shown | ContentView.swift → paywall .onAppear | Paywall vist |
paywall.dismissed | ContentView.swift → dismiss callback | Paywall lukket |
purchase.completed | SubscriptionManager.swift → verified transaction | Kjøp OK |
purchase.failed | SubscriptionManager.swift → unverified | Kjøp feilet |
trial.expired | SubscriptionManager.swift → entitlement lost | Trial utløpt |
insights.viewed | InsightsView.swift → card .onAppear | Card synlig |
insight.feedback | InsightFeedback.swift → thumbs up/down | Brukervurdering |
journey.searched | JourneyView.swift → søkefelt endret | Søk utført |
feedback.submitted | FeedbackSheet.swift → submit OK | Feedback sendt |
error.ai_workload | UnifiedSessionView.swift → SSE error | AI feilet |
error.classification_rejected | ContentView.swift → rejection event | Avvist |
navigationPathChanged | ContentView.swift → tab endret | Tab-bytte |