Контекст экранов и события
Импорт для примеров: package:gravity_sdk/gravity_sdk.dart. Методы с автопоказом дополнительно используют BuildContext из Flutter.
PageContext
const productContext = PageContext(
type: ContextType.product,
data: ['sku-123'],
location: 'app://product/sku-123',
attributes: {'screen_variant': 'standard'},
);
Типы: homepage, product, cart, category, search, other. SDK сериализует их как HOMEPAGE, PRODUCT, CART, CATEGORY, SEARCH и OTHER.
data задаёт контекст выбора/таргетинга и не заменяет состав корзины в событии. Общие правила для каждого типа: Контекст страницы. Не меняйте регистр SKU, категорий и lng относительно товарного фида.
SDK добавляет в attributes служебные app_version, sdk_version и app_platform. Для iOS значение платформы — iOS. Таргетинг по платформе и версиям.
Просмотр экрана
trackView() передаёт просмотр и может автоматически показать in-app кампанию:
await GravitySDK.instance.trackView(
context: context,
pageContext: productContext,
);
Вызывайте после появления экрана, например через addPostFrameCallback, как в быстром старте. Не отправляйте просмотр из build(): перестроение виджета не означает новый визит.
BuildContext должен относиться к актуальному экрану внутри MaterialApp/Navigator; для SnackBar нужен ScaffoldMessenger. SDK проверяет context.mounted, но уход на другой маршрут не всегда размонтирует старый экран. Управляйте моментом вызова в логике навигации приложения.
Чтобы отправить просмотр без встроенного показа:
final details = await GravitySDK.instance.trackViewNoShow(
pageContext: productContext,
);
details — nullable-ответ headless. Если нужно только собирать просмотры/события, задайте isFetchContentOnTrack: false; влияние флага описано в Конфигурации.
Пользовательские действия
Отправляйте событие после успешного действия: изменения корзины, завершения заказа или авторизации. triggerEvent() может показывать in-app; triggerEventNoShow() не показывает UI и не требует BuildContext.
Добавление и удаление товара
await GravitySDK.instance.triggerEventNoShow(
events: [
AddToCartEvent(
value: 1990,
productId: 'sku-123',
quantity: 1,
currency: 'RUB',
cart: [
CartItem(productId: 'sku-123', quantity: 1, itemPrice: 1990),
],
customProps: {'list': 'recommendations'},
),
],
pageContext: productContext,
);
RemoveFromCartEvent принимает те же поля. value и itemPrice — денежные значения, quantity — целое количество. Используйте согласованный с аналитикой проекта смысл value. Не подменяйте SKU внутренним ID приложения, если фид использует другой идентификатор.
Покупка
await GravitySDK.instance.triggerEventNoShow(
events: [
PurchaseEvent(
uniqueTransactionId: 'ORDER-2026-1001-42',
value: 3980,
currency: 'RUB',
cart: [
CartItem(productId: 'sku-123', quantity: 2, itemPrice: 1990),
],
customProps: {'delivery': 'pickup'},
eventTime: DateTime.utc(2026, 10, 1, 10, 15),
),
],
pageContext: const PageContext(
type: ContextType.other,
data: [],
location: 'app://order/success',
),
);
uniqueTransactionId — устойчивый уникальный ID конкретного заказа. При повторной попытке доставки одного заказа не создавайте новый ID. Это особенно важно для офлайн-доставки.
Синхронизация корзины
final cartEvent = SyncCartEvent(
value: 3980,
currency: 'RUB',
cart: [
CartItem(productId: 'sku-123', quantity: 2, itemPrice: 1990),
],
);
Передавайте актуальный состав корзины; пустая корзина — cart: [].
Вход и регистрация
LoginEvent и SignUpEvent используют cuid/cuidType или hashedEmail. Полный пример хеширования и отправки — в Идентификации пользователя.
Произвольное событие
final customEvent = CustomEvent(
type: 'delivery-selected-v1',
name: 'Delivery selected',
customProps: {'method': 'pickup', 'store_id': 'store-12'},
);
type и name согласуйте с настройкой событий/кампаний проекта. CustomEvent также принимает cuid, cuidType и cart. Не используйте его для повторного клика по встроенной кнопке SDK, который уже учтён её tracking.
customProps и eventTime
Эти поля доступны всем типам TriggerEvent в 0.24.0:
customProps—Map<String, String>?. Числа и boolean преобразуйте в строки; вложенные объекты полем не поддерживаются.eventTime—DateTime?. SDK отправляет время в UTC. Если оно не задано, SDK фиксирует время вызова события, в том числе до ожидания сессии и доставки из очереди.
Не присваивайте событию время очередной попытки отправки. Для сохранённых ранее действий передавайте их фактическое время.
Ошибки и результат вызова
Возврат triggerEvent()/triggerEventNoShow() не подтверждает доставку: при временной ошибке запрос может остаться в очереди. NoShow возвращает null также при отсутствии контента, выключенной его загрузке, устаревшем ответе или обработанной ошибке.
Методы трекинга обрабатывают ошибки запроса внутри SDK. Вызов до initialize() выбрасывает исключение. Для запросов getContentBy* приложение отдельно обрабатывает сетевые ошибки и fallback.