Skip to Content
ConceptsOTA Compatibility

OTA Compatibility

This page explains the rules for determining when OTA updates are safe and when a new store build is required.

The Core Rule

OTA updates can safely replace JavaScript code, but not native code.

If the native components of your app change, devices need a new binary from the app store.


What Can Be Updated via OTA

✅ JavaScript/TypeScript

All your app code:

// src/services/api.ts export async function fetchData() { // This can be updated via OTA return await fetch('/api/data'); }

✅ CSS/SCSS Styles

All styling:

/* app.css */ .button { /* Can be updated via OTA */ background-color: blue; }

✅ Assets

Images, fonts, and other assets in your source:

src/ ├── assets/ │ ├── images/ │ ├── fonts/ │ └── icons/

✅ Non-Native npm Packages

Pure JavaScript packages:

{ "dependencies": { "lodash": "4.17.21", // ✅ Safe to update "axios": "1.4.0", // ✅ Safe to update "date-fns": "2.30.0" // ✅ Safe to update } }

✅ Node Modules (JavaScript Parts)

JavaScript code from any package, even native plugins:

node_modules/ └── nativescript-camera/ ├── index.js // ✅ JS can update └── platforms/ └── ios/ // ❌ Native cannot

What Requires a Store Build

❌ NativeScript Platform Versions

{ "devDependencies": { "@nativescript/ios": "8.6.0", // Change = store build "@nativescript/android": "8.6.0" // Change = store build } }

❌ Native Plugin Versions

Any plugin with native code:

{ "dependencies": { "nativescript-camera": "4.5.0", // Change = store build "@nativescript/imagepicker": "1.0.0", // Change = store build "nativescript-geolocation": "8.0.0" // Change = store build } }

❌ App_Resources Contents

App_Resources/ ├── iOS/ │ ├── Info.plist // Change = store build │ ├── Assets.xcassets/ // Change = store build │ └── LaunchScreen.storyboard // Change = store build └── Android/ ├── AndroidManifest.xml // Change = store build └── res/ // Change = store build

❌ Custom Native Code

native-src/ ├── ios/ │ └── MyBridge.swift // Change = store build └── android/ └── MyBridge.java // Change = store build

Compatibility Checking Flow

1. Build Time

When you create a store build:

Project → Compute Fingerprint → Store with Build Record

2. Update Time

When you publish an OTA update:

Project → Compute Fingerprint → Store with Update Record

3. Check Time

When a device checks for updates:

Device Fingerprint ─┐ ├─→ Compare ─┐ Update Fingerprint ─┘ │ ┌─────────────────────────────────┐ │ Match? │ │ │ │ Yes → Download OTA │ │ No → requiresStoreUpdate: true │ └─────────────────────────────────┘

Client Behavior

Default Behavior

When requiresStoreUpdate is true:

  1. SDK receives the response
  2. Update is ignored
  3. App continues with current version
  4. Status: UPDATE_IGNORED

Override Behavior

With allowStoreUpdateOverride: true:

initNorrix({ updateUrl: 'https://norrix.net', allowStoreUpdateOverride: true, // ⚠️ Use with caution });
  1. SDK receives the response
  2. Update is downloaded despite incompatibility
  3. Update is applied
  4. Risk: App may crash if native code is missing

Warning: Only use this if you’re certain the native changes are backward-compatible.


Example Scenarios

Scenario 1: Bug Fix

Before: Version 1.0.0, Build 42 Change: Fix API endpoint in src/api.ts After: Version 1.0.1, Build 43 → ✅ OTA Compatible (JS only)

Scenario 2: Plugin Update

Before: nativescript-camera@4.5.0 Change: npm update nativescript-camera@5.0.0 After: nativescript-camera@5.0.0 → ❌ Store Build Required (native code changed)

Scenario 3: New Icon

Before: AppIcon.png (original) Change: Update App_Resources/iOS/Assets.xcassets After: AppIcon.png (new design) → ❌ Store Build Required (App_Resources changed)

Scenario 4: Mixed Changes

Changes: - Fix bug in src/utils.ts ✅ JS - Update @nativescript/core ❌ Native → ❌ Store Build Required (any native change triggers)

Best Practices

Plan Updates Carefully

  1. Patch releases (1.0.1): Usually OTA-compatible
  2. Minor releases (1.1.0): Check for dependency changes
  3. Major releases (2.0.0): Often require store builds

Check Before Publishing

Always verify compatibility:

norrix fingerprint compare --from <last-build-id>

Separate Concerns

  • Keep native changes in dedicated releases
  • Batch OTA-compatible changes together
  • Communicate store updates to users

Version Strategy

1.0.0 (Store) → 1.0.1 (OTA) → 1.0.2 (OTA) → 1.1.0 (Store)