Troubleshooting¶
A diagnostic guide for the most common Airlock failure modes, ordered by where they tend to bite first. If you're stuck, the fastest path to a diagnosis is almost always an Adobe Assurance session — it lets you watch the event flow live, see exactly what Airlock dispatched, and compare against what Analytics received.
Where to look first¶
| Symptom | Look at | Common causes |
|---|---|---|
| App doesn't connect to Assurance | Deep link / device logs | Wrong scheme in Info.plist / AndroidManifest.xml, missing Assurance registration |
No Airlock — (registered) event in Assurance |
App-launch logs | Airlock extension not in registerExtensions(...) call |
| Rule A doesn't fire | Assurance event list, Launch rule condition | Condition mismatch, app not sending the expected event |
Rule A fires but no Airlock Processed Track follows |
Assurance, Airlock log level = debug |
Rule script returned null/undefined (event suppressed), or script threw |
Airlock Processed Track appears but Analytics hit is missing |
Rule B configuration | No Rule B configured to fire on the enriched event |
| Analytics hit lands but contextdata is wrong | Assurance "Network Requests" pane | Wrong key name, type coercion (Boolean → "1"/"0"), reserved-key collision |
App-side problems¶
"I don't see any Airlock activity"¶
- Check the extension is registered. In
registerExtensions(...),Airlock.self(iOS) orAirlock.EXTENSION(Android) must be in the list before the configuration callback runs. - Check the log level. In Launch → Airlock configuration → set Log Level to
debugfor the dev environment; rebuild the property; reload in the app. - Look at the device console. iOS: Xcode console with the filter
Airlock. Android: Logcat withadb logcat | grep Airlock. You should seeAirlock — (registered)and per-event lines.
"Lifecycle events look wrong"¶
Make sure MobileCore.lifecycleStart(...) is called once after registerExtensions completes, and that MobileCore.lifecyclePause() is called from your app's background hook. Skipping these breaks session-scoped accumulators.
Rule problems¶
"My Rule A condition isn't matching"¶
- Inspect the actual event payload in Assurance — open the
generic.track / request.contentevent and copy the JSON. Compare it character-for-character with your rule condition. - Common gotcha: the app sends
contextdata.categorybut the rule checkscategory. Adobe's condition builder defaults to top-level keys. - Filter for whether the event reaches Airlock at all: search Assurance for
"Airlock Processed Track". If there's none, Rule A didn't fire (problem upstream of Airlock); if there is one, the script ran.
"Script returned undefined" / event suppressed by accident¶
Rule scripts that don't return anything (or return null/undefined) suppress the event. Common mistakes:
When Log Level = debug, suppressions log Airlock: script returned null/undefined; suppressing dispatch.
"Script threw an error"¶
Airlock fails open on script errors — the original event is dispatched with contextdata.airlock.status = "error" and contextdata.airlock.error = <message>. The event is not dropped. In Assurance, filter for airlock.status = error to find these.
"My JSON test payload won't parse"¶
If you're using the iOS test harness Payload sheet, paste the JSON and check the quotes look like " not " ". iOS Smart Punctuation can silently substitute curly quotes; the test harness disables this for the payload editor (as of MR !71) but it can still happen elsewhere — e.g. if you paste from a Word doc or web page.
Configuration problems¶
"Macro value is undefined in my script"¶
- Check the macro name matches exactly — case-sensitive, no whitespace.
sharedState.airlock.userTierwon't find a macro namedUserTier. - Macros run once at config-load with whatever shared state existed at that moment. If your macro depends on Identity ECID, Identity may not have published its state yet — use a derived metric instead.
- Watch the Launch property for typos in the macro body — a JS syntax error makes the entire macro resolve to
undefined.
"Lookup table always returns empty"¶
- The wildcard row
*must be the last row in definition order. Rows are matched top-down. - Source path is dot-notation:
contextdata.category, not[contextdata][category]. - The matched value is always coerced to String. Boolean values from
contextdataarrive as"1"/"0"(matching Adobe's NSNumber bridging on iOS); plan your match keys accordingly.
"Accumulator never increments"¶
- If the accumulator has no
incrementFilter, it counts every event matching the rule. If you set a decrement filter only, increment defaults to every event — usually not what you want. Set anincrementFilterexplicitly. - Persistence:
sessionresets at lifecycle start;userpersists across launches. If you reinstall the app, both reset. - See Reset Accumulators for the zero-and-republish workflow.
"Derived metric value is missing from the Analytics hit"¶
- Confirm the metric name isn't on the reserved list — those are silently rejected.
- Check the metric's filter actually matches your event. A filter-mismatched metric retains its previous value (or empty on first event); it doesn't disappear, but it also doesn't recompute.
Performance¶
"App feels slower since adding Airlock"¶
The runaway-script protection kicks in at:
- iOS: 2 seconds wall-clock per script
- Android: 100,000 Rhino instructions per script
If a script hits the limit, Airlock logs a warning and fails open. Tightly-looped scripts (especially regex or recursion) hit the Android limit fast — Rhino is interpreted, ~100× slower than V8.
For an honest perf check: in debug log level, every script evaluation logs its duration. If you see anything > 50ms regularly, that script is a candidate for refactoring or moving the computation into a macro (config-load, not per-event).
Getting help¶
- Reproduce in the test harness app first (
testapps/iOS/testapps/Android). The harness has Assurance pre-wired so it's the fastest way to isolate whether the bug is in your app or in Airlock. - Capture an Assurance session URL and the device log excerpt.
- File an issue with: platform, Airlock version (
Airlock.extensionVersion/Airlock.EXTENSION_VERSION), Adobe SDK versions, rule config, and the Assurance link.