Реализация управления согласиями (Consent Management) по категориям данных
Consent Management — это не одна кнопка «Согласен». Это система, которая отслеживает, на что именно пользователь дал согласие, когда, на какую версию документа, и что делать, если он его отзовёт.
Без этой системы невозможно ни соответствовать GDPR/CCPA, ни доказать compliance при аудите.
Почему одного «Принять» недостаточно
Регуляторы требуют гранулярного согласия: пользователь должен иметь возможность согласиться на аналитику, но отказаться от рекламного профилирования. Принуждение принять всё или ничего — нарушение принципа свободы согласия по GDPR. ICO (Великобритания) и CNIL (Франция) уже штрафовали за это.
Технически это означает: отдельный boolean на каждую категорию, не одно поле consent_accepted.
Архитектура Consent Manager
enum class ConsentPurpose(val id: String) {
NECESSARY("necessary"),
ANALYTICS("analytics"),
MARKETING("marketing"),
PERSONALIZATION("personalization"),
THIRD_PARTY_SHARING("third_party_sharing"),
LOCATION_TRACKING("location_tracking"),
PUSH_MARKETING("push_marketing")
}
data class ConsentRecord(
val purpose: ConsentPurpose,
val granted: Boolean,
val grantedAt: Long?, // null если не выдано
val revokedAt: Long?, // null если не отозвано
val policyVersion: String, // версия политики, под которую давалось согласие
val collectionMethod: String // "explicit_ui", "imported", "default_opt_in"
)
class ConsentManager(
private val store: ConsentStore,
private val server: ConsentSyncService
) {
fun grant(purpose: ConsentPurpose) {
val record = ConsentRecord(
purpose = purpose,
granted = true,
grantedAt = System.currentTimeMillis(),
revokedAt = null,
policyVersion = PolicyVersionProvider.current(),
collectionMethod = "explicit_ui"
)
store.save(record)
server.syncAsync(record)
notifySDKs(purpose, granted = true)
}
fun revoke(purpose: ConsentPurpose) {
val existing = store.get(purpose)?.copy(
granted = false,
revokedAt = System.currentTimeMillis()
) ?: return
store.save(existing)
server.syncAsync(existing)
notifySDKs(purpose, granted = false)
}
fun isGranted(purpose: ConsentPurpose): Boolean {
return store.get(purpose)?.granted == true
}
}
Синхронизация с SDK
При изменении согласия — немедленное обновление всех аффектированных SDK:
private fun notifySDKs(purpose: ConsentPurpose, granted: Boolean) {
when (purpose) {
ANALYTICS -> {
FirebaseAnalytics.getInstance(context)
.setAnalyticsCollectionEnabled(granted)
amplitude.setOptOut(!granted)
}
MARKETING -> {
MobileAds.setRequestConfiguration(
RequestConfiguration.Builder()
.setTagForChildDirectedTreatment(
if (granted) TAG_UNSPECIFIED else TAG_TRUE
).build()
)
}
PUSH_MARKETING -> {
if (!granted) {
// Отписываем от маркетинговых топиков FCM
FirebaseMessaging.getInstance()
.unsubscribeFromTopic("marketing_campaigns")
}
}
else -> {}
}
}
Экран управления согласиями
Доступен из настроек профиля в любое время — не только при первом запуске. Структура:
Управление данными
├── Необходимые (не отключаемые)
│ └── Аутентификация и безопасность
├── Аналитика использования [ВКЛ] ←→
│ └── Помогает нам улучшать приложение
├── Персонализация [ВЫК] ←→
│ └── Рекомендации на основе ваших действий
├── Маркетинговые коммуникации [ВЫК] ←→
│ └── Email и push о новинках
└── Передача партнёрам [ВЫК] ←→
└── Рекламные сети и аналитика
Отзыв согласия работает немедленно. Нельзя добавлять friction («Уверены?» → «Точно уверены?») — это тёмный паттерн.
Повторное получение согласия
При выходе новой версии Privacy Policy — нужно оценить, затрагивает ли изменение ранее выданные согласия. Если добавляется новая категория обработки — согласие на неё нужно получить заново. Если меняется формулировка без изменения сути — достаточно уведомления.
Механизм: при запуске приложения проверяем policyVersion в хранимых записях согласия. Если версия устарела — показываем обновлённый экран только для изменившихся категорий.
Хранение и аудит
Записи согласия нельзя удалять при удалении аккаунта — они нужны для доказательства compliance при проверке. Хранятся отдельно от пользовательских данных, с retention согласно требованиям (обычно 5–7 лет для юридически значимых документов).
Сроки: полная система Consent Management с UI, SDK-оркестрацией и серверной синхронизацией: 2–3 дня. Стоимость рассчитывается индивидуально.







