GrowthRailDocs

Installation

The SDK is distributed as a binary Swift package from GrowthRail/growthrail-ios-sdk. There is no CocoaPods artifact.

Install with Xcode

  1. Choose File → Add Package Dependencies.
  2. Enter https://github.com/GrowthRail/growthrail-ios-sdk.git.
  3. Select a released version (prefer an exact version for production).
  4. Add the GrowthRail product for full UI, or GrowthRailCore for a headless integration.

Install from Package.swift

Package.swift
dependencies: [
  .package(
    name: "GrowthRail",
    url: "https://github.com/GrowthRail/growthrail-ios-sdk.git",
    from: "0.1.8"
  ),
],
targets: [
  .target(
    name: "YourTarget",
    dependencies: [
      .product(name: "GrowthRail", package: "GrowthRail"),
      // Or: .product(name: "GrowthRailCore", package: "GrowthRail"),
    ]
  ),
]
Requirements: Xcode 15+, Swift 5.9+, iOS 15+. Current public binary release is 0.1.8. SwiftPM verifies XCFramework checksums automatically.
ProductUse when
GrowthRailFull SDK including SwiftUI/UIKit host UI. Re-exports Core APIs via import GrowthRail.
GrowthRailCoreAttribution and referral APIs only — you render your own UI and observe GrowthRail.shared.state.

Configuration

Call GrowthRail.configure once at app startup (for example in App.init() or application(_:didFinishLaunchingWithOptions:)). Use a publishable mobile key; never ship a server secret in the app binary.

App.swift
import GrowthRail
import SwiftUI

@main
struct ExampleApp: App {
  init() {
    GrowthRail.configure(
      GrowthRailConfiguration(
        projectSecretKey: "sk_your_publishable_mobile_key",
        appearance: .dark,
        theme: GrowthRailTheme(primaryColor: "#2563eb"),
        debug: true
      )
    )
  }

  var body: some Scene {
    WindowGroup {
      ContentView()
        .growthRailHost()
        .onOpenURL { _ = GrowthRail.shared.handle(url: $0) }
    }
  }
}

Configuration Options

OptionTypeDefaultDescription
projectSecretKeystringRequired Publishable mobile key (sk_...).
apiURLURLproduction APIOverride for staging or local API testing.
appearance.light | .dark?systemPreferred appearance for automatic UI.
theme.primaryColorstring?campaign / #2563ebHex primary color for trigger and dashboard chrome.
disableTriggerButtonboolfalseNever show the automatic floating/edge trigger.
userIdstring?nilIf set, identifies the user automatically after bootstrap.
debugboolfalseVerbose logging. Disable in production.
cookieDomain and autoPageTrack exist for React Native source compatibility and have no effect on iOS.

Automatic UI

With the GrowthRail product, attach the host once at the root. The host renders the server-configured trigger, new-user banner, and referral dashboard.

SwiftUI

swift
ContentView()
  .growthRailHost()
  // Or: .growthRailHost(sdk: GrowthRail.shared)

UIKit

swift
final class HomeViewController: UIViewController {
  private let growthRailHost = GrowthRailUIKitHost()

  override func viewDidLoad() {
    super.viewDidLoad()
    growthRailHost.attach(to: self)
  }

  deinit {
    growthRailHost.detach()
  }
}

Backend campaign settings drive layout at runtime:

FieldValuesBehavior
trigger.displayModefloating | edge | noneCircle inset trigger, flush edge tab, or hidden. Also respect disableTriggerButton.
trigger.positionbottom-right, bottom-left, top-right, top-leftCorner placement for the trigger.
modal.componentTypemodal | drawerCentered card over a dimmed backdrop, or system bottom sheet with detents.
banner.positioncenter-top, center-bottom, left-*, right-*New-user promotional banner placement after attributed install/open.

User Management

Call initAppUser after authentication with a stable app user ID (for example a RevenueCat app user ID or your database ID — never an email). Any attribution captured from an incoming link is bound automatically.

swift
Task {
  do {
    let user = try await GrowthRail.shared.initAppUser(userID)
    let referralLink = await GrowthRail.shared.getReferralLink()
    let attributionToken = await GrowthRail.shared.getAttributionToken()
  } catch {
    // Present or log the integration error
  }
}

GrowthRail.shared.state is an ObservableObject with isInitialized, isUserReady, currentUser, isLoading, error, referral fields, trigger visibility, banner state, and dashboard state.

Common APIs

NeedAPI
Identify usertry await GrowthRail.shared.initAppUser(userID) or identify(userID)
Open / close dashboardshowReferralDashboard(options:), hideReferralDashboard()
Incoming attributiongetReferralTrackingId(), getAttributionToken(), getCapturedReferralCode()
Current referral datagetReferralLink(), getReferralCode()
Track a non-standard sourcetry await trackReferral(code, rewardEventName:)
Dismiss bannerdismissBanner()
Custom UIObserve GrowthRail.shared.state; optionally embed ReferralDashboard / TriggerButton

Dashboard options override

Pass ReferrerModalOptions to override title, description, presentation, appearance, or primary color for a single open:

swift
GrowthRail.shared.showReferralDashboard(
  options: ReferrerModalOptions(
    title: "Invite Friends",
    description: "Share your link and earn rewards.",
    componentType: .drawer,
    appearance: .dark,
    theme: GrowthRailTheme(primaryColor: "#2563eb")
  )
)

Deep Linking

Register a custom URL scheme or Universal Link, then forward URLs to GrowthRail. The handler returns true only when the URL contains a non-empty referralCode query parameter.

SwiftUI

swift
.onOpenURL { url in
  _ = GrowthRail.shared.handle(url: url)
}

UIKit / AppDelegate

swift
func application(
  _ app: UIApplication,
  open url: URL,
  options: [UIApplication.OpenURLOptionsKey: Any] = [:]
) -> Bool {
  GrowthRail.shared.handle(url: url)
}

func application(
  _ application: UIApplication,
  continue userActivity: NSUserActivity,
  restorationHandler: @escaping ([UIUserActivityRestoring]?) -> Void
) -> Bool {
  guard let url = userActivity.webpageURL else { return false }
  return GrowthRail.shared.handle(url: url)
}

Deferred attribution uses privacy-preserving fingerprint matching on first launch and does not collect IDFA. The SDK persists the referrer code and tracking ID, then forwards the tracking ID when the user is initialized.

Simulator tip: xcrun simctl openurl booted 'your-app://open?referralCode=TEST123'

Complete Example

App.swift
import GrowthRail
import SwiftUI

@main
struct ExampleApp: App {
  init() {
    GrowthRail.configure(
      GrowthRailConfiguration(
        projectSecretKey: "sk_your_publishable_mobile_key",
        debug: true
      )
    )
  }

  var body: some Scene {
    WindowGroup {
      ContentView()
        .growthRailHost()
        .onOpenURL { _ = GrowthRail.shared.handle(url: $0) }
        .task {
          _ = try? await GrowthRail.shared.initAppUser("user_123")
        }
    }
  }
}

struct ContentView: View {
  var body: some View {
    Button("Invite Friends") {
      GrowthRail.shared.showReferralDashboard()
    }
  }
}

Differences from React Native

FeatureReact NativeiOS (Swift)
Distributionnpm (@growth-rail/react-native)SwiftPM binary XCFrameworks
Entry pointGrowthRailProvider + hooksGrowthRail.configure + .growthRailHost()
StorageAsyncStorageApp Group / UserDefaults-backed storage
UIReact Native componentsSwiftUI overlay / UIKit host
Modal vs drawerCustom animated viewsCentered card vs system bottom sheet

Troubleshooting