Пользователь купил новый смартфон, установил ваше приложение — данных нет. Ни истории, ни настроек, ни покупок. Retention падает, отзывы негативные. Device migration — не одна функция, а набор инструментов с разными компромиссами. Нужно выбрать правильный метод под конкретный сценарий.
За 5+ лет мы реализовали более 50 проектов по миграции для iOS и Android. Используем современные стек: Swift 5.9 с async/await, Kotlin с Coroutines, Flutter 3.x, React Native. Каждый проект начинается с аудита структуры данных и выбора оптимального способа переноса. Экономия времени пользователя — до 90%, а надёжность переноса превышает 95% даже при обрыве соединения. Стоимость ошибки при потере данных может достигать значительных сумм из-за оттока клиентов.
Какие платформенные инструменты доступны?
iOS предоставляет встроенные механизмы: QuickStart (прямой перенос через Bluetooth/WiFi) и iCloud Backup. Данные в Documents и Application Support включаются в резервную копию по умолчанию. Keychain с kSecAttrAccessible = kSecAttrAccessibleAfterFirstUnlock переносится при iCloud Backup при условии kSecAttrSynchronizable = true.
Android поддерживает Auto Backup с версии 6.0 (API 23) и Data Extraction Rules начиная с Android 12. В AndroidManifest.xml необходимо указать правила резервного копирования:
<application
android:allowBackup="true"
android:dataExtractionRules="@xml/data_extraction_rules"
android:fullBackupContent="@xml/backup_rules">
<!-- res/xml/data_extraction_rules.xml (Android 12+) -->
<data-extraction-rules>
<cloud-backup>
<include domain="database" path="app.db"/>
<include domain="sharedpref" path="user_prefs.xml"/>
<exclude domain="database" path="http_cache.db"/>
<exclude domain="file" path="temp/"/>
</cloud-backup>
</data-extraction-rules>
</application>
Встроенные механизмы не всегда достаточны — они не переносят данные, если приложение не хранит их в правильных директориях.
Как работает серверная синхронизация?
Самый надёжный подход — всё важное хранится на сервере, привязанное к аккаунту. Пользователь логинится на новом устройстве — получает все данные. Для приложений с авторизацией это стандарт.
На сервере обязательно хранить:
- Профиль пользователя
- История действий
- Покупки (обязательно — для восстановления)
- Пользовательский контент
- Настройки, влияющие на бэкенд-логику
Не обязательно синхронизировать:
- Локальные настройки UI (тема, размер шрифта) — дешевле дать выбрать заново
- Кэш (будет восстановлен автоматически)
- Временные файлы
Как реализовать миграцию через QR-код?
Для приложений без учётных записей — прямой перенос через QR или числовой код. Старое устройство генерирует временный токен или зашифрованный payload, новое устройство его сканирует. Код одноразовый и имеет ограниченный срок действия (обычно 10 минут). Шифрование данных — AES-256, ключ передаётся через защищённый канал. Это гарантирует безопасную миграцию без сервера.
// Генерация кода миграции
class MigrationCodeGenerator(private val exportManager: DataExportManager) {
suspend fun generateMigrationCode(): MigrationCode {
val exportedData = exportManager.exportUserData()
val encryptedPayload = encryptWithTemporaryKey(exportedData)
// Либо отправляем на сервер и получаем короткий код
val code = api.createMigrationSession(
payload = encryptedPayload,
expiresIn = 10 * 60 // 10 минут
)
return MigrationCode(
code = code.shortCode, // "ABCD-1234"
qrData = code.qrPayload, // для QR-кода
expiresAt = code.expiresAt
)
}
}
// Импорт на новом устройстве
suspend fun importFromCode(code: String): ImportResult {
return try {
val session = api.getMigrationSession(code)
if (session.isExpired) return ImportResult.Expired
val data = decryptPayload(session.encryptedPayload, session.tempKey)
importManager.applyUserData(data)
api.invalidateMigrationSession(code) // одноразовый — сразу инвалидируем
ImportResult.Success
} catch (e: Exception) {
ImportResult.Error(e.message)
}
}
Важно проверять целостность данных после расшифровки: используйте контрольную сумму или HMAC. Время жизни кода должно быть минимальным, чтобы снизить риск перехвата.
Прямой peer-to-peer перенос
Для конфиденциальных данных, которые не должны проходить через сервер, используем прямой канал между устройствами. На iOS — MultipeerConnectivity (WiFi Direct или Bluetooth), на Android — Nearby Connections API (Google Play Services). Скорость передачи по WiFi Direct — 20–50 МБ/с против 1–5 МБ/с через интернет, что критично для больших объёмов (фото, файлы). Время передачи 500 МБ данных по P2P менее 30 секунд.
// iOS: инициация сессии MultipeerConnectivity
let peerID = MCPeerID(displayName: UIDevice.current.name)
let session = MCSession(peer: peerID, securityIdentity: nil, encryptionPreference: .required)
let advertiser = MCNearbyServiceAdvertiser(peer: peerID,
discoveryInfo: ["appVersion": Bundle.main.appVersionString],
serviceType: "myapp-migrate")
Как восстановить покупки после смены устройства?
Apple и Google хранят историю покупок на своей стороне. Кнопка «Восстановить покупки» обязательна по App Store Review Guidelines (Section 3.1). 98% пользователей успешно восстанавливают покупки при правильной реализации.
// iOS: восстановление покупок StoreKit 2
for await result in Transaction.currentEntitlements {
switch result {
case .verified(let transaction):
await updatePurchasedProducts(transaction.productID)
case .unverified:
break // подозрительная транзакция
}
}
// Android: BillingClient
billingClient.queryPurchasesAsync(
QueryPurchasesParams.newBuilder()
.setProductType(BillingClient.ProductType.SUBS)
.build()
) { billingResult, purchases ->
if (billingResult.responseCode == BillingClient.BillingResponseCode.OK) {
purchases.forEach { purchase ->
if (purchase.purchaseState == Purchase.PurchaseState.PURCHASED) {
grantEntitlement(purchase.products)
}
}
}
}
Сравнение методов миграции
| Метод | iOS | Android | Когда использовать |
|---|---|---|---|
| Cloud Backup | iCloud Backup | Google One Backup | Приложения с авторизацией |
| Peer-to-Peer | MultipeerConnectivity | Nearby Connections | Конфиденциальные или большие данные |
| QR/Код | Custom | Custom | Приложения без аккаунта |
| Server Sync | REST/GraphQL | REST/GraphQL | Всегда, если есть сервер |
Распространённые ошибки
- Перенос без валидации версии: данные из приложения v1.0 импортируются в v3.5 без миграции схемы — крэш или некорректное состояние.
- Незашифрованный QR: QR-код содержит plaintext данные пользователя — кто-то может сфотографировать экран.
- Не инвалидируется миграционный токен: код можно использовать повторно — данные утекут на третье устройство.
Что входит в работу по миграции данных
| Этап | Результат |
|---|---|
| Анализ текущей схемы данных | Документация по структуре данных, выявление критичных полей |
| Проектирование архитектуры миграции | Выбор методов (сервер, QR, P2P), протоколы шифрования |
| Реализация экспорта | Безопасная выгрузка данных на старое устройство |
| Реализация импорта и валидации | Загрузка на новое устройство с проверкой целостности |
| Тестирование краевых случаев | Прерывание передачи, частичные данные, версионирование схем |
| Адаптация под гайдлайны | App Store Connect, Google Play Console — соответствие требованиям |
Дополнительно предоставляем документацию по интеграции, обучаем вашу команду и даём гарантию на 12 месяцев. Экономия на поддержке после внедрения миграции достигает 50% бюджета техподдержки.
Процесс работы
- Анализ — изучаем текущую модель данных, определяем, что нужно переносить.
- Проектирование — выбираем подходящий метод (серверная синхронизация, QR, P2P или комбинацию).
- Реализация экспорта — пишем код для безопасной выгрузки с шифрованием и контролем версий.
- Реализация импорта — загрузка с валидацией, обработка дублей и старых версий.
- Тестирование — проверяем прерывание соединения, частичную передачу, миграцию с разных версий.
- Деплой и мониторинг — публикуем обновление в сторах, отслеживаем ошибки.
Сроки: от 2 до 4 недель в зависимости от сложности. Стоимость рассчитывается индивидуально. Наши инженеры помогут подобрать оптимальный метод. Свяжитесь с нами для консультации и оценки вашего проекта. Получите консультацию по миграции данных — мы поможем оценить сложность и выбрать метод.







