Реализация невосстанавливаемых покупок (Non-Consumable IAP) для iOS

Non-consumable IAP — категория, где каждая ошибка в логике восстановления покупок превращается в жалобу в App Store и чарджбек. Пользователь купил «безлимитный режим» или «убрать рекламу», переустановил приложение — и не получил своё. Поддержка Apple не поможет: восстановление non-consumable это отв

Разработка и поддержка любых видов мобильных приложений:

Информационные и развлекательные мобильные приложения
Новостные приложения, игры, справочники, онлайн-каталоги, погодные, фитнес и здоровье, туристические, образовательные, социальные сети и мессенджеры, квиз, блоги и подкасты, форумы, агрегаторы
Мобильные приложения электронной коммерции
Интернет-магазины, B2B-приложения, маркетплейсы, онлайн-обменники, кэшбэк-сервисы, биржи, дропшиппинг-платформы, программы лояльности, доставка еды и товаров, платежные системы
Мобильные приложения для управления бизнес-процессами
CRM-системы, ERP-системы, управление проектами, инструменты для команды продаж, учет финансов, управление производством, логистика и доставка, управление персоналом, системы мониторинга данных
Мобильные приложения электронных услуг
Доски объявлений, онлайн-школы, онлайн-кинотеатры, платформы предоставления электронных услуг, платформы кешбека, видеохостинги, тематические порталы, платформы онлайн-бронирования и записи, платформы онлайн-торговли

Это лишь некоторые из типы мобильных приложений, с которыми мы работаем, и каждый из них может иметь свои специфические особенности и функциональность, а также быть адаптированным под конкретные потребности и цели клиента.

Услуги, которые мы предлагаем
Показано 1 из 1Все 1734 услуг
Реализация невосстанавливаемых покупок (Non-Consumable IAP) для iOS
Средний
~2-3 дня

Наши компетенции:

Часто задаваемые вопросы

Последние работы

  • image_mobile-applications_feedme_467_0.webp
    Разработка мобильного приложения для компании FEEDME
    895
  • image_mobile-applications_xoomer_471_0.webp
    Разработка мобильного приложения для компании XOOMER
    782
  • image_mobile-applications_rhl_428_0.webp
    Разработка мобильного приложения для компании RHL
    1216
  • image_mobile-applications_zippy_411_0.webp
    Разработка мобильного приложения для компании ZIPPY
    1079
  • image_mobile-applications_affhome_429_0.webp
    Разработка мобильного приложения для компании Affhome
    1002
  • image_mobile-applications_flavors_409_0.webp
    Разработка мобильного приложения для компании FLAVORS
    597

Non-consumable IAP — категория, где каждая ошибка в логике восстановления покупок превращается в жалобу в App Store и чарджбек. Пользователь купил «безлимитный режим» или «убрать рекламу», переустановил приложение — и не получил своё. Поддержка Apple не поможет: восстановление non-consumable это ответственность разработчика. Наш опыт пяти лет и более двадцати проектов с IAP показывает, что корректная реализация с первого раза экономит до 40% времени на баг-фиксах. Согласно документации StoreKit, правильное восстановление критически важно.

Что чаще всего идёт не так

Самая распространённая ошибка — вызывать SKPaymentQueue.default().restoreCompletedTransactions() только по нажатию кнопки «Восстановить». Правильно: при каждом запуске проверять originalTransaction через SKReceiptRefreshRequest или серверную валидацию. Без этого пользователь, вернувшийся через полгода с новым iPhone, окажется без оплаченного контента.

Второй кейс — неправильная обработка SKPaymentTransactionObserver. Если updatedTransactions не вызывает finishTransaction(_:) для всех состояний (.purchased, .restored, .failed), транзакция зависает в очереди и при следующем запуске приложения повторно триггерит observer. Видели проекты, где это приводило к двойному открытию paid-контента после рестарта.

Третья проблема — отсутствие серверной валидации. Локальная проверка receipt через ASN.1 парсинг сложна и уязвима: злоумышленник может подменить receipt в файловой системе. Серверная верификация через эндпоинт Apple /verifyReceipt (или альтернативный) даёт гарантию подлинности.

Как устроена правильная реализация

Архитектура non-consumable IAP строится вокруг StoreKit 2 (iOS 15+) или StoreKit 1 с поддержкой iOS 13–14. Сравним два подхода:

Аспект StoreKit 2 StoreKit 1 (Legacy)
Минимальная версия iOS 15.0 3.0
API стиль async/await Delegate + completion handlers
Восстановление покупок Автоматическое через Transaction.currentEntitlements Ручное restoreCompletedTransactions()
Проверка подписи Встроенная VerificationResult Требуется ReceiptValidator
Сложность кода Низкая Средняя

StoreKit 2 радикально упрощает код: он в 2 раза сокращает количество строк по сравнению с StoreKit 1.

// Запрос продуктов let products = try await Product.products(for: ["com.app.premium_unlock"]) // Покупка let result = try await products.first?.purchase() switch result { case .success(let verification): switch verification { case .verified(let transaction): // unlock контент await transaction.finish() case .unverified: // receipt подделан — не разблокируем break } case .pending: // SCA или родительский контроль — ждём break case .userCancelled: break } 

Transaction.currentEntitlements — async sequence, который при каждом запуске приложения возвращает все активные покупки. Итерируем его в @main или в AppDelegate.applicationDidFinishLaunching и восстанавливаем состояние без кнопки «Восстановить».

Для iOS 13–14 остаётся StoreKit 1 с SKPaymentTransactionObserver. Там нужен отдельный ReceiptValidator — либо локальная верификация через openssl (сложно, но без сетевых запросов), либо серверная через Apple /verifyReceipt endpoint (deprecated, но работает). Рекомендуем серверную: локальная требует embedding Apple root certificate и корректной ASN.1-парсинга.

Как избежать проблем с восстановлением покупок?

Ключевое — делать восстановление автоматическим при каждом запуске, а не только по кнопке. В StoreKit 2 это достигается подпиской на Transaction.updates. В StoreKit 1 — вызовом restoreCompletedTransactions() и сохранением originalTransaction.transactionIdentifier в UserDefaults или Keychain. Без автоматизации пользователи с новыми устройствами останутся без контента.

Почему серверная валидация критична?

Для приложений с бэкендом: при покупке клиент отправляет appStoreReceiptURL на сервер, сервер запрашивает Apple Sandbox/Production и сохраняет original_transaction_id в базе. При восстановлении на новом устройстве — запрос к своему API по apple_id пользователя. Это единственный способ гарантировать «покупка на одном устройстве, доступ на другом» в рамках одного Apple ID. Средняя экономия от правильной реализации — до $10,000 в год на поддержку.

Пошаговый план внедрения StoreKit 2

  1. Настройте продукты в App Store Connect (локализация, цены).
  2. Реализуйте запрос продуктов через Product.products(for:).
  3. Добавьте обработку покупки с проверкой VerificationResult.
  4. Подпишитесь на Transaction.updates для автоматического восстановления.
  5. Интегрируйте серверную верификацию через /verifyReceipt.
  6. Протестируйте в Sandbox на сценарий «покупка → удаление → восстановление».
Типичная ошибка восстановления
// НЕПРАВИЛЬНО: восстановление только по кнопке func restorePurchases() { SKPaymentQueue.default().restoreCompletedTransactions() } // ПРАВИЛЬНО: автоматическое восстановление при старте Task { for await result in Transaction.currentEntitlements { if case .verified(let transaction) = result { // разблокировать контент } } } 

Процесс работы и что входит

Наша реализация IAP под ключ включает:

  • Настройку продуктов в App Store Connect (создание, локализация, цены — конкретные суммы рассчитываются индивидуально).
  • Интеграцию StoreKit 2 с fallback на StoreKit 1 для максимальной совместимости.
  • Серверную верификацию receipt с сохранением original_transaction_id.
  • Тестирование в Sandbox и на реальных устройствах с чек-листом сценариев.
  • Документацию по поддержке и доступам.
  • Гарантию прохождения App Review (соблюдение параграфа 3.1.1 App Store Review Guidelines).

Тестирование

В Xcode Simulator StoreKit работает через локальный .storekit файл — можно тестировать без реальных продуктов. Для device-тестирования нужен Sandbox Account в App Store Connect. Важно проверять сценарий: покупка → удаление → переустановка → восстановление. Этот путь ломается чаще всего. Получите консультацию по вашему проекту — оценим риски и предложим оптимальное решение.

Сроки реализации — от 2 до 3 дней: настройка продуктов в App Store Connect, интеграция StoreKit 2 с fallback на StoreKit 1, покрытие тестами на Sandbox, прохождение ревью (App Review требует кнопку «Restore Purchases» в интерфейсе). Закажите интеграцию IAP под ключ — гарантируем корректную работу на всех устройствах и версиях iOS.