Конфигурация iOS SDK

Инициализируйте SDK один раз при старте приложения. Установка и минимальное приложение; точные сигнатуры собраны в справочнике API.

Инициализация

Параметры:

  • apiKey — API key проекта.
  • section — идентификатор секции проекта.
  • gravityEventCallback — опциональный callback для событий SDK и действий пользователя внутри кампаний.
  • productViewBuilder — шаблон карточки товара, который приложение передает SDK. Обязателен для отображения товарных рекомендаций.
  • productFilter — клиентский фильтр слотов товаров. SDK применяет его при декодировании Products.slots, поэтому отфильтрованные товары не попадут в готовые product-based блоки и manual response.
  • uiSettings — опциональные настройки UI SDK, например кастомный шрифт через UISettings(fontName:).
  • logLevel — уровень логирования внутреннего SDK-логгера. По умолчанию .error.

Что важно учесть:

  • initialize(...) рекомендуется выполнить до первого обращения к GravitySDK.instance;
  • gravityEventCallback используется для обработки действий пользователя внутри кампаний и tracking-событий поддерживаемых сценариев;
  • если в приложении отображаются товарные рекомендации, передайте productViewBuilder уже на этапе инициализации.

Кастомный шрифт и элементы UI

Зарегистрируйте шрифт в приложении и передайте его PostScript name:

GravitySDK.initialize(
    apiKey: "YOUR_API_KEY",
    section: "YOUR_SECTION_ID",
    uiSettings: UISettings(fontName: "MyFont-Regular")
)

Если UIFont не сможет загрузить шрифт, SDK использует системный и пишет error-лог. Встроенный рендерер поддерживает текст, изображения, кнопки, spacer, товарные контейнеры, items-container и webview с URL в src. Действие openStep переключает контент по номеру step в кампании; отдельного callback-события для него нет.

Логирование SDK

iOS SDK поддерживает параметр logLevel в initialize(...). Он управляет только внутренними логами SDK и не влияет на gravityEventCallback, отправку событий или логи приложения.

GravitySDK.initialize(
    apiKey: "YOUR_API_KEY",
    section: "YOUR_SECTION_ID",
    gravityEventCallback: { event in
        print(event)
    },
    logLevel: .debug
)

Доступные уровни:

  • .debug — включает HTTP request/response debug-логи и ошибки SDK;
  • .info — включает info и error сообщения SDK;
  • .error — оставляет только ошибки SDK;
  • .none — полностью отключает внутренний вывод SDK.

Логи пишутся через os_log с префиксом GravitySDK.

Если нужно передавать внутренние логи SDK в приложение, используйте setLogListener(...).

Пример:

GravitySDK.instance.setLogListener { level, message in
    print("[GravitySDK][\(level)] \(message)")
}

Обработчик получает только те сообщения, которые проходят текущий logLevel. Он вызывается на потоке, где сформирован лог; для обновления UI переключайтесь на главный поток.

.none отключает локальный вывод и log listener. Отправка внутренних ошибок в sdk-sentry.gravityfield.ai/error выполняется отдельно и не отключается этим уровнем. В .debug выводятся полные запросы и ответы, включая заголовок Authorization.

Глобальные настройки

Метод задает runtime-настройки для последующих запросов trackView(...), triggerEvent(...) и getContentBySelector(...).

Пример:

GravitySDK.instance.setOptions(
    options: Options(
        isReturnCounter: false,
        isReturnUserInfo: true,
        isReturnAnalyticsMetadata: false,
        isImplicitPageview: false,
        isImplicitImpression: true
    ),
    contentSettings: ContentSettings(
        skusOnly: false,
        fields: ["id", "name", "price"]
    ),
    proxyUrl: nil
)

Что настраивается через Options:

  • isReturnCounter — добавляет счетчики в response, если они нужны приложению;
  • isReturnUserInfo — включает возврат user в response;
  • isReturnAnalyticsMetadata — включает возврат аналитических метаданных;
  • isImplicitPageview — управляет неявной отправкой pageview на backend;
  • isImplicitImpression — управляет неявной отправкой impression для поддерживаемых сценариев.

Что настраивается через ContentSettings:

  • skusOnly — возвращает только SKU вместо полного товарного объекта там, где это поддерживает backend-сценарий;
  • fields — ограничивает набор полей, возвращаемых по товарам.

По умолчанию первые четыре флага Options равны false, isImplicitImpression — true. isBuildEngagementUrl всегда равен true; параметра для его изменения в публичном инициализаторе нет.

setOptions(...) заменяет настройки целиком: nil сбрасывает соответствующий объект к значениям по умолчанию. proxyUrl задаёт полный базовый URL API, например https://proxy.example.com/v2, без завершающего /. SDK добавляет к нему /visit, /event или /choose. Tracking URL из ответа и адрес отправки ошибок этим параметром не заменяются.

gravityEventCallback

gravityEventCallback передается в initialize(...) опционально. Если приложению нужно обрабатывать действия пользователя внутри кампаний, передайте callback при инициализации SDK.

В SDK определены модели TrackingEvent, включая:

  • ContentLoadEvent
  • ContentImpressionEvent
  • ContentVisibleImpressionEvent
  • ContentCloseEvent
  • CopyEvent
  • CancelEvent
  • FollowUrlEvent
  • FollowDeeplinkEvent
  • RequestPushEvent
  • ProductImpressionEvent
  • ProductClickEvent

SDK передает эти события в gravityEventCallback и выполняет вызов на главном потоке.

Практический вывод:

  • ContentLoadEvent может приходить после getContentBySelector(...), а также после внутренней загрузки контента для auto-rendered in-app кампаний;
  • используйте gravityEventCallback для обработки URL, deeplink и других действий пользователя внутри кампаний;
  • SDK сам не выполняет переходы по FollowUrlEvent и FollowDeeplinkEvent, это ответственность приложения;
  • manual engagement через sendContentEngagement(...) / sendProductEngagement(...) не генерирует callback-событие автоматически;
  • ProductClickEvent может приходить из встроенного rendering flow SDK, но не из ручного вызова sendProductEngagement(...).

Передача статуса Push-уведомлений

Если таргетинг кампаний зависит от статуса push-разрешения, передавайте его в SDK через setNotificationPermissionStatus(status:).

GravitySDK.instance.setNotificationPermissionStatus(status: .granted)

Отдельно учитывайте поведение requestPush внутри in-app кампаний:

  • iOS SDK сам вызывает UNUserNotificationCenter.requestAuthorization(...);
  • при отказе SDK может открыть системные настройки приложения;
  • SDK дополнительно передает RequestPushEvent в gravityEventCallback.

Блокировка показа in-app кампаний

Используйте presentation lock, когда приложение показывает собственную модалку, bottom sheet, onboarding, checkout или другой приоритетный слой интерфейса, который не должен перекрываться кампанией Gravity.

func showCheckoutSheet() {
    GravitySDK.instance.lockPresentation()

    let checkoutViewController = CheckoutViewController()
    checkoutViewController.onDismiss = {
        GravitySDK.instance.unlockPresentation()
    }

    present(checkoutViewController, animated: true)
}

Пока блокировка активна, SDK может загрузить контент после trackView(...) или triggerEvent(...), но не будет показывать новую in-app кампанию поверх текущего интерфейса. Уже открытый Gravity-контент этим вызовом не закрывается.

Блокировка также применяется к переходам между шагами кампании через openStep. Ручная загрузка selector-контента через getContentBySelector(...) не блокируется: приложение продолжает само управлять показом manual rendering сценариев.

Если приложению нужно отслеживать состояние блокировки, подпишитесь на изменения:

GravitySDK.instance.setPresentationLockListener { locked in
    // Обновите состояние приложения, если это нужно вашему UI.
}

lockPresentation() и unlockPresentation() устанавливают один Boolean-флаг, счётчика вложенных блокировок нет. Если одновременно открываются несколько собственных слоёв UI, приложение должно само определить момент разблокировки. Пропущенная кампания не ставится в очередь и не показывается автоматически после unlockPresentation().

Listener вызывается на главном потоке при вызове lock/unlock, но не получает текущее состояние сразу при подписке. Для снятия подписки передайте nil.