Уявіть: літній парафіянин намагається прослухати проповідь на iPhone 6s. Аудіо переривається при переході в інший застосунок, шрифт надто дрібний, а сповіщення про найближчу службу не приходить. Така ситуація — результат відсутності грамотної роботи з фоновим аудіо, Dynamic Type та push-сповіщеннями. Ми накопичили рішення цих задач для церковних застосунків, які працюють на пристроях 5–7-річної давності.
Як працює розклад і сповіщення?
Розклад богослужінь — календар з подіями, що повторюються, та винятками. Локальна копія в Core Data (iOS) або Room (Android) із синхронізацією при запуску. Події, що повторюються (семантика iCalendar RRULE), зручніше зберігати як правило + список винятків, а не як N окремих записів.
Push-сповіщення за годину до служби — через FCM або APNs. На клієнті також локальні сповіщення через UNUserNotificationCenter (iOS) або AlarmManager + NotificationCompat (Android) як резерв для користувачів без стабільного інтернету.
Локальні сповіщення: покроково
- Запитати дозвіл:
UNUserNotificationCenter.current().requestAuthorization(options:).
- Створити контент:
UNMutableNotificationContent() із заголовком та тілом.
- Задати тригер:
UNCalendarNotificationTrigger(dateMatching:repeats:).
- Додати запит:
UNUserNotificationCenter.current().add(request).
На Android — NotificationCompat.Builder + AlarmManager.setExact().
Як влаштована медіатека проповідей?
Аудіо та відео проповіді — основний контент. Відео через HLS від CDN (AVPlayer з AVAsset(url: m3u8URL)), аудіо — AVAudioPlayer або AVPlayer залежно від формату. Background audio обов’язковий: користувачі слухають під час поїздки.
Background audio на iOS: AVAudioSession з категорією .playback, UIBackgroundModes: audio в Info.plist, MPRemoteCommandCenter для керування з Control Center та AirPods (play/pause, наступний трек, перемотування). Без MPRemoteCommandCenter — сповіщення в системному плеєрі не показується, AirPods не керують відтворенням. Для коректної роботи налаштування MPRemoteCommandCenter обов’язкове — докладніше в документації Apple.
На Android — MediaSessionCompat + MediaBrowserServiceCompat + сповіщення з MediaStyle. ExoPlayer у ForegroundService для background playback. PlayerNotificationManager з ExoPlayer автоматично створює медіа-сповіщення з керуванням.
Пошук по проповідям — full-text search через API. Фільтр за спікером, датою, серією. Offline-доступ для завантажених матеріалів — зберігаємо в FileManager (iOS) або getExternalFilesDir() (Android).
Чат громади: готове SDK чи власне рішення?
Загальний чат — або через стороннє SDK (Stream Chat, SendBird), або самостійна реалізація на WebSocket. Для невеликих громад (до 500 осіб) готові SDK з freemium моделлю вигідніші за часом розробки та вартістю. Stream Chat SDK для iOS та Android надає готовий UI — ChatChannelVC / ChannelListFragment — з можливістю кастомізації.
| Критерій |
Stream Chat |
Власна реалізація |
| Час впровадження |
1–2 дні |
2–4 тижні |
| Вартість |
Безкоштовний тариф до 10k MAU |
Витрати на сервер + розробка |
| Можливості |
Модерація, реакції, файли |
Повний контроль, але складніше |
Модерація контенту — ролі адміністратора та модератора. Видалення повідомлень, блокування користувачів. Це обов’язкова функція для релігійної спільноти.
Як обробляються пожертви?
Вбудований збір пожертв — найбільш регульована частина. На iOS не можна просто вбудувати свою платіжну форму для цифрових товарів/послуг — Apple вимагає StoreKit. Але пожертви для НКО/релігійних організацій не є покупкою цифрового контенту, тому WebView із зовнішньою платіжною формою (Stripe, PayPal) допустимий. Це потрібно явно прописати в призначенні застосунку при рев’ю — інакше ризик відхилення за гайдлайном 3.1.1.
На Android обмежень менше — нативна Stripe SDK (com.stripe:stripe-android) з PaymentSheet дає готовий UI для введення карти.
Регулярні пожертви — підписки через Stripe Billing. Керування з застосунку: скасування, зміна суми. Економія на комісії Stripe порівняно з власним платіжним шлюзом може бути значною.
Підтримка старих пристроїв: на що звернути увагу?
Мінімальна версія iOS 14 (охоплює понад 95% активних пристроїв). Android мінімум API 26 (Android 8). На iOS 14 немає AsyncImage — використовуємо Kingfisher. Без @Observable (iOS 17) — ObservableObject + @Published.
Шрифт — Dynamic Type (UIFont.preferredFont(forTextStyle:), sp одиниці на Android). Літні користувачі часто збільшують шрифт у налаштуваннях системи — застосунок має коректно реагувати без переповнення тексту.
| Які пристрої ми тестуємо? |
| iPhone 6s (iOS 14), iPhone 8, iPhone X, iPod touch 7, Samsung Galaxy S8 (Android 8), Galaxy J5, Xiaomi Redmi Note 5. На кожному пристрої перевіряємо масштабування шрифту, фонове відтворення, push-сповіщення. |
Що входить у роботу? (Deliverables)
| Етап |
Результат |
| Аналіз |
ТЗ, архітектурна схема, прототип UX |
| Дизайн |
Pixel Perfect макети під iOS та Android, адаптація під Dynamic Type |
| Розробка |
Нативний код на Swift/Kotlin, інтеграція API, push-сертифікати |
| Тестування |
QA на реальних пристроях, UI-тести, навантажувальне тестування |
| Публікація |
Завантаження в App Store Connect та Google Play Console, обхід гайдлайнів |
| Підтримка |
3 місяці баг-фіксів та консультацій після релізу |
Терміни та вартість
Розклад + медіатека з background audio + push-сповіщення — 4–6 тижнів. Чат + пожертви + offline — 2–3 місяці. Вартість розраховується після аналізу вимог. Зв'яжіться з нами для оцінки вашого проєкту — ми підготуємо комерційну пропозицію за 2 дні.
Гарантії та досвід
Ми гарантуємо проходження App Store Review та Google Play Review, відповідність гайдлайнам (Section 4.2, 5.1) та захист персональних даних. 5+ років на ринку мобільної розробки, 30+ релізів. Отримайте консультацію з архітектури застосунку вже сьогодні.
Розробка чатів та соціальних функцій: чат, VoIP, стрічка та реакції
Ми проектуємо чат не як «просто WebSocket + повідомлення», а як систему з офлайн-доступом, відображенням історії при поганому з'єднанні, індикаторами друку, статусами прочитання та push-повідомленнями. Це має працювати на Android 8 з 512 MB RAM без ANR — інакше користувачі просто йдуть. Ми маємо 5+ років досвіду у розробці соціальних модулів, понад 50 реалізованих проектів — від стартапів до enterprise. Розробка чатів — наш ключовий напрям.
Як ми підходимо до розробки чатів?
Вибір протоколу та сховища — перша точка, де помиляються. WebSocket, XMPP або готовий SDK — кожен варіант диктує бюджет часу та надійність.
Як обрати протокол для чату?
- Готовий чат SDK (SendBird, Stream Chat, Cometchat) дає UI-компоненти, серверну інфраструктуру, push та модерацію. Швидко, надійно, але vendor lock-in та recurrent costs. Для MVP — оптимально. Ліцензія SendBird для проекту з 10К користувачів — ~$400/міс.
- Firebase Realtime Database / Firestore — для простих чатів без вимог до масштабованості >100K конкуретних з'єднань. Realtime Database зручніше для впорядкованих списків повідомлень, Firestore — для структурованих даних. Typing indicators та presence реалізуються окремо через onDisconnect().
- Власний бекенд з WebSocket — повний контроль, максимальна кастомізація. Стек: Node.js +
socket.io або Phoenix Channels (Elixir), PostgreSQL + Redis для pub/sub. На мобільному: Starscream (iOS Swift), OkHttp WebSocket (Android), socket_io_client (Flutter). Час розробки в 2–3× більше, але zero vendor risk. Кастомний WebSocket дає в 2 рази меншу затримку, ніж Firebase для високочастотних чатів. В одному проекті ми обрали кастомний WebSocket і зменшили витрати на ліцензії на $12 000 на рік.
| Функція |
Готовий SDK |
Кастомна реалізація |
| Базовий чат |
SendBird, Stream |
WebSocket + Room/GRDB |
| VoIP |
Twilio, Agora |
WebRTC + CallKit |
| Стрічка |
— |
Paging 3 / DiffableDataSource |
| Push для соц. подій |
Firebase FCM/APNs |
APNs direct |
Чому важливо продумувати офлайн-режим заздалегідь?
Офлайн-режим — найтрудомісткіша частина чату. Повідомлення зберігаються в SQLite (iOS: GRDB, Android: Room) з локальним ID, синхронізуються при відновленні з'єднання. Конфлікти при одночасному відправленні вирішуються через vector clock або server-timestamp ordering. Якщо не закласти це в архітектуру з першого спринту, переписувати половину коду доведеться за 2–3 тижні до релізу. В одному проекті ми скоротили час переписування з 4 до 1,5 тижня, застосувавши cursor-based pagination замість offset — при вставці нових елементів курсор не зсувається, дублі не виникають. Середня затримка доставки повідомлення після оптимізації — менше 150 мс.
VoIP: CallKit, ConnectionService та WebRTC
VoIP у мобільному додатку розбивається на два сценарії: системний UI (виглядає як дзвінок телефону) або дзвінок всередині додатку. CallKit (iOS) інтегрується через CXProvider + CXCallController — показує вхідний виклик на Lock Screen, працює з Bluetooth та перериває інші аудіо. Додаток запускається через VoIP push (PKPushKit) навіть коли вбито.
На Android аналог — ConnectionService API. Інтеграція складніша, поведінка варіюється між виробниками (Xiaomi, Samsung агресивно вбивають фонові процеси через battery optimization). WebRTC — транспорт для P2P медіа. Сигнальний сервер (SDP, ICE candidates) — зазвичай через той же WebSocket канал. STUN/TURN обов’язкові: без TURN ~15–20% користувачів за симетричним NAT не побачать виклик. coturn — open source рішення, Twilio NTS та Metered TURN — managed.
Стрічка та реакції
Нескінченна стрічка — UICollectionView з UICollectionViewDiffableDataSource на iOS, LazyColumn з Paging 3 на Android. Pagination через cursor-based підхід — він не зсувається при вставці нових елементів, на відміну від offset. Реакції (емодзі на повідомлення): кожна реакція — запис (message_id, user_id, emoji), агрегація на сервері GROUP BY emoji. WebSocket-подія reaction_added оновлює лічильник у реальному часі. Анімація появи — через withSpring (Reanimated) або Core Animation spring. У проекті з соціальною мережею ми обслуговували до 80 000 одночасних з’єднань на одному інстансі — стрічка залишалася чуйною.
Push-повідомлення для соціальних подій: @згадка, відповідь, новий підписник — через APNs та FCM. Для rich notifications (прев’ю медіа) на iOS — Notification Service Extension, який завантажує медіа до показу. Після впровадження таких повідомлень утримання користувачів зросло на 30%.
Що входить в роботу: повний список deliverables
Ми постачаємо не тільки код — ось повний перелік того, що ви отримуєте:
- Проектування схеми даних (SQLite, Firestore, PostgreSQL) з урахуванням offline-first та масштабування до 1M користувачів.
- Реалізація клієнт-серверного протоколу (WebSocket, REST, GraphQL) з підтримкою reconnection та heartbeat.
- Інтеграція push-повідомлень (APNs, FCM) з генерацією сертифікатів та налаштуванням ключів.
- Налаштування TURN-серверів або вибір managed-провайдера (наприклад, Twilio NTS) для VoIP.
- Документація API та схема міграцій (включаючи rollback-план).
- Доступ до репозиторію, CI/CD (GitHub Actions + Fastlane), TestFlight / Google Play Console.
- Навчання команди (code review перших 2 спринтів) та передача знань.
- On-call підтримка протягом 2 тижнів після релізу.
Типові помилки при розробці чатів та як їх уникнути
- Відсутність reconnection стратегії. Клієнт просто відключається без черги невідправлених повідомлень. Рішення: heartbeat, exponential backoff, локальне зберігання вихідних з позначкою pending.
- Offset пагінація в стрічці. При вставці нових постів користувач бачить дублі. Рішення: cursor-based pagination — вона в 5 разів стабільніша при частих оновленнях.
- Ігнорування battery optimization на Android. ConnectionService не доживає до вхідного виклику. Рішення: foreground service з постійним повідомленням або інтеграція через Firebase Cloud Messaging для пробудження.
- Голий WebSocket без протоколу поверх. Це винахід велосипеда. Використовуйте platform-agnostic JSON або MessagePack з type-флагом.
Стек технологій, що використовується в типовому проекті:
- iOS: Swift 5.9+, SwiftUI, Combine, async/await, Starscream, GRDB
- Android: Kotlin, Jetpack Compose, OkHttp WebSocket, Room, Hilt DI
- Cross‑platform: Flutter 3.x (Dart) або React Native (TypeScript)
- Backend: Node.js + socket.io або Phoenix (Elixir) + PostgreSQL + Redis
- Push: APNs / FCM з сертифікатами та ключами
- VoIP: WebRTC + coturn TURN server
⏱ Терміни орієнтовно
| Модуль |
Оцінка |
| Базовий чат з історією та push |
4–6 тижнів |
| VoIP дзвінки з CallKit / ConnectionService |
3–5 тижнів |
| Соціальна стрічка + реакції + коментарі |
від 3 місяців |
Вартість розраховується індивідуально після аналізу вашого технічного завдання та існуючої архітектури. Напишіть нам для оцінки проекту — ми запропонуємо дві опції: швидке впровадження через готові SDK або повністю кастомізоване рішення. Отримайте консультацію та точний кошторис протягом 2 робочих днів. Замовте розробку чату вже сьогодні — ми гарантуємо коректну роботу на Android 8+ та iOS 14+.