targetSdkVersion — API нивото на Android, под което приложението е тествано и оптимизирано. Този параметър се посочва в build.gradle и определя кои behavioural changes (промени в поведението на системата) ще бъдат приложени към приложението по време на работа. Ако targetSdkVersion е по-ниско от API нивото на устройството, Android изключва behavioural changes, въведени в по-новите версии, запазвайки съвместимост за старите приложения. Според Android Developers, Google Play изисква targetSdkVersion да не е по-старо от 1 година от текущото API ниво.
Основни точки
targetSdkVersion — целочислен параметър в build.gradle, който декларира API нивото, на което приложението е тествано. Системата Android използва този параметър, за да реши кои behavioural changes да приложи към приложението по време на изпълнение. Ако targetSdkVersion = 33, Android прилага всички behavioural changes, въведени до API 33 включително, но не прилага промените от API 34+. Ако targetSdkVersion = 34 — прилагат се промени до API 34, и така нататък.
Ключовата разлика между targetSdkVersion и minSdkVersion — механизмът на действие. minSdk се проверява еднократно при инсталиране и блокира инсталирането, ако условието не е изпълнено. targetSdkVersion влияе на runtime поведението на системата на всяко устройство, независимо от версията на Android, на която приложението се изпълнява. Едно и също приложение с targetSdk 31 ще се държи различно на Android 13, 14 и 15, защото behavioural changes над 31 са изключени.
Механизмът targetSdkVersion — е инструмент за обратна съвместимост, вграден в Android. Без него всяка актуализация на операционната система би развалила хиляди стари приложения. Google въведе този механизъм в Android 2.1 (API Level 7) и оттогава го използва като стандартен начин за въвеждане на нови правила за сигурност, поверителност и управление на ресурси, без да нарушава работата на съществуващите приложения.
// build.gradle.kts — targetSdkVersion в defaultConfig
android {
namespace = "com.example.myapp"
compileSdk = 36
defaultConfig {
applicationId = "com.example.myapp"
minSdk = 26
targetSdk = 36 // Тествано под Android 16
versionCode = 1
versionName = "1.0.0"
}
}
// Проверка на текущия targetSdk в кода
fun isUsingScopedStorage(): Boolean {
// Context.getApplicationInfo().targetSdkVersion съдържа targetSdk на приложението
return context.applicationInfo.targetSdkVersion >= VERSION_CODES.Q
}В примера targetSdk = 36 включва всички behavioural changes на Android 16. Кодът проверява targetSdkVersion чрез context.applicationInfo.targetSdkVersion — това позволява динамично определяне кой режим на съвместимост е включен. Помощната функция е полезна за библиотеки, които трябва да се адаптират към targetSdk на извикващото приложение.
Behavioural changes — това са модификации на поведението на системата Android, които се прилагат само към приложения с targetSdkVersion >= определено API ниво. Всяко ново major издание на Android въвежда behavioural changes и ако приложението не актуализира targetSdk, тези промени не влизат в сила. Такъв механизъм позволява на разработчиците да актуализират приложението със свое собствено темпо, а не синхронно с излизането на нова версия на операционната система.
Scoped Storage (API 29) — една от най-значимите behavioural changes. Приложенията с targetSdk 29+ не могат да получат директен File достъп до общите директории Pictures, Downloads, Music, Documents. Вместо това се използва MediaStore за мултимедия, SAF (Storage Access Framework) за произволни файлове и getExternalFilesDir() за собствено съхранение. Старите приложения с targetSdk 28 и по-ниски продължават да работят със стария Full Storage Access, но това създава заплаха за сигурността.
POST_NOTIFICATIONS (API 33) — runtime разрешение за изпращане на известия. Приложенията с targetSdk 33+ трябва да поискат разрешение Manifest.permission.POST_NOTIFICATIONS от потребителя чрез стандартен диалогов прозорец. Ако разрешението не бъде дадено, NotificationManager.silent() не показва известия на потребителя. На Android 13+ без това разрешение push известията и локалните нотификации просто не се показват, което може значително да намали ангажираността на потребителите.
| API ниво | Behavioural Change | Необходими действия при актуализация |
|---|---|---|
| 29 | Scoped Storage | Преминаване към MediaStore и SAF за файлове извън sandbox |
| 30 | Package Visibility | Добавяне на <queries> в манифеста за взаимодействие с пакети |
| 31 | Foreground Service Notification | Показване на известие в рамките на 10 секунди след стартиране на услугата |
| 33 | POST_NOTIFICATIONS | Runtime искане на разрешение за изпращане на известия |
| 34 | Foreground Service Types | Деклариране на тип foreground услуга в манифеста |
| 35 | Privacy Sandbox | Ограничаване на рекламните идентификатори (Advertising ID) |
Стойността на targetSdkVersion на приложението може да се получи чрез ADB: командата adb shell dumpsys package com.example.myapp | grep targetSdk показва targetSdk=34. В кода context.getApplicationInfo().targetSdkVersion връща цяло число. За аналитика е полезно да логвате targetSdk заедно с android.os.Build.VERSION.SDK_INT, за да разберете кои behavioural changes са действително активни във всяка сесия.
Google Play поставя задължителни изисквания за targetSdkVersion за всички публикувани приложения. От август 2024 г. минималният targetSdk = 33 (Android 13). От август 2025 г. — targetSdk = 34. Очаква се от август 2026 г. Google да изисква targetSdk = 35 (Android 15). Новите приложения и актуализациите на съществуващите трябва да отговарят на тези изисквания, в противен случай конзолата блокира публикуването. Това е политика на Google Play, а не ограничение на Android Runtime: приложение с targetSdk 34 може да работи на Android 16, но не може да бъде публикувано в Play Store.
Android App Bundle (AAB) — задължителният формат за публикуване от август 2021 г. APK вече не се приема в Google Play (изключение — приложения с размер > 150 MB и някои legacy проекти). Форматът AAB позволява на Google да генерира оптимизирани APK за всяко API ниво и плътност на екрана, което намалява размера на изтегляне с 15-30%. За проверка на targetSdk Google Play анализира AAB манифеста и при несъответствие показва грешка с минималната изисквана стойност.
| Период | Минимален targetSdk | Версия на Android | Забележка |
|---|---|---|---|
| Август 2024 | 33 | Android 13 | Tiramisu — задължителен POST_NOTIFICATIONS |
| Август 2025 | 34 | Android 14 | Upside Down Cake — foreground service types |
| Август 2026 | 35 | Android 15 | Vanilla Ice Cream — Privacy Sandbox |
| Август 2027 (план) | 36 | Android 16 | Baklava — T+ |
Google Play Console проверява targetSdkVersion не само при качване на нов AAB, но и при актуализиране на съществуващо приложение. Ако вашето приложение има targetSdk 33 и Google повиши минималния праг до 34 — няма да можете да пуснете никаква актуализация, докато не повишите targetSdk. За приложения, които дълго време не са актуализирани, Google Play може автоматично да ги премахне от публикуване (unpublish).
Актуализирането на targetSdkVersion — не е просто промяна на число в build.gradle. Всяка behavioural change може да развали съществуващата функционалност, ако кодът не бъде подготвен предварително. Препоръчва се да започнете подготовката 3-6 месеца преди крайния срок на Google Play, особено ако приложението е голямо и използва много системни API.
Процес стъпка по стъпка: Стъпка 1 — проучете behavioural changes за новото API ниво в документацията на Android Developers (страница "Behavioural Changes by API Level"). Стъпка 2 — създайте клон targetSdk-update и променете targetSdk на новата стойност. Стъпка 3 — пуснете приложението на емулатор или устройство с новото API ниво и проверете всяка функционалност, свързана с промените. Стъпка 4 — поправете грешките: добавете разрешения, променете работата с файлове, актуализирайте манифеста.
Стъпка 5 — тествайте на стари устройства. Повишаването на targetSdk не засяга устройства с API ниво по-ниско от новия targetSdk, но behavioural changes се прилагат на всички устройства с API Level >= targetSdk. Ако сте повишили targetSdk от 33 на 34, на устройства с API 34+ ще се включат behavioural changes на API 34. На устройства с API 33 нищо няма да се промени.
// Подготовка за targetSdk 35: Privacy Sandbox
import android.os.Build
import android.os.Build.VERSION_CODES
import com.google.android.gms.ads.identifier.AdvertisingIdClient
class AdsManager {
fun getAdvertisingId(context: android.content.Context): String? {
// Privacy Sandbox ограничава Advertising ID от API 35
if (Build.VERSION.SDK_INT >= VERSION_CODES.VANILLA_ICE_CREAM) {
// API 35+ — идентификаторът е недостъпен, използваме MeasurementManager
return null
}
return try {
val adInfo = AdvertisingIdClient.getAdvertisingIdInfo(context)
adInfo.getId()
} catch (e: Exception) {
null
}
}
// Проверка: кои behavioural changes са активни
fun getActiveChanges(context: android.content.Context): List<String> {
val sdkInt = Build.VERSION.SDK_INT
val targetSdk = context.applicationInfo.targetSdkVersion
return buildList {
if (sdkInt >= VERSION_CODES.Q && targetSdk >= VERSION_CODES.Q)
add("ScopedStorage")
if (sdkInt >= VERSION_CODES.TIRAMISU && targetSdk >= VERSION_CODES.TIRAMISU)
add("PostNotifications")
if (sdkInt >= VERSION_CODES.UPSIDE_DOWN_CAKE && targetSdk >= VERSION_CODES.UPSIDE_DOWN_CAKE)
add("FgsTypes")
}
}
}Класът AdsManager показва подготовката за Privacy Sandbox (API 35). Advertising ID престава да бъде достъпен от API 35 при targetSdk 35+. Функцията getActiveChanges демонстрира правилния модел за проверка на behavioural changes: трябва едновременно да проверявате SDK_INT на устройството и targetSdk на приложението. Само когато и двете условия са изпълнени, промяната е действително активна.
Android 15 (API 35, Vanilla Ice Cream) въвежда няколко критични behavioural changes, които разработчиците трябва да вземат предвид при актуализиране на targetSdk до 35. Първата — Privacy Sandbox for Android. Това е инициатива на Google за замяна на Advertising ID с по-лични API: Topics API (интереси на потребителя), Protected Audience (ремаркетинг) и Attribution Reporting (конверсии). От API 35 Advertising ID престава да бъде стабилен идентификатор и може да връща нулева стойност.
Втората промяна — Foreground Service Types (API 34, продължено в API 35). От API 34 всяко приложение с targetSdk 34+ трябва да посочи типа на foreground услугата в манифеста: dataSync, systemExempted, shortService, location, mediaPlayback и други. Без това системата генерира ForegroundServiceTypeNotAllowedException. В API 35 е добавен новият тип health и е затегната проверката на съществуващите типове. Всички foreground услуги трябва да бъдат прегледани.
Третата промяна — ограничение на SCHEDULE_EXACT_ALARM. От API 35 приложенията с targetSdk 35+ не могат да използват SCHEDULE_EXACT_ALARM без изричното разрешение на потребителя. Системата показва диалогов прозорец и потребителят трябва да одобри точното планиране. За будилници и таймери това означава допълнителна стъпка в UX. Алтернатива — използване на неточни аларми с резерв от 10 минути.
// Android 15 (API 35): проверка на SCHEDULE_EXACT_ALARM
import android.app.AlarmManager
import android.os.Build
import android.provider.Settings
class AlarmScheduler {
fun canScheduleExactAlarms(context: android.content.Context): Boolean {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.VANILLA_ICE_CREAM) {
// API 35+: изисква се разрешение от потребителя
val alarmManager = context.getSystemService(
android.content.Context.ALARM_SERVICE
) as AlarmManager
return alarmManager.canScheduleExactAlarms()
}
// Под API 35 — точните аларми са достъпни без разрешение
return true
}
fun requestExactAlarmPermission(activity: android.app.Activity) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.VANILLA_ICE_CREAM) {
val intent = android.content.Intent(
Settings.ACTION_REQUEST_SCHEDULE_EXACT_ALARM
).apply {
data = android.net.Uri.fromParts(
"package", activity.packageName, null
)
}
activity.startActivity(intent)
}
}
}Privacy Sandbox и ограничението на алармите — две от най-критичните behavioural changes на API 35. За рекламните SDK ще е необходима миграция към Topics API и Attribution Reporting. За приложения с будилници и напомняния — адаптация на UX към диалоговия прозорец за разрешение. Игнорирането на тези промени ще доведе до срив на приложението в runtime на Android 15 или до неработеща рекламна монетизация.
Разликата между targetSdkVersion и compileSdkVersion — една от най-честите теми на объркване сред Android разработчиците. compileSdkVersion — това е версията на SDK, срещу която се компилира кодът. Тя определя кои API са налични по време на компилиране, но не влияе на runtime поведението. targetSdkVersion — това е версията, под която приложението е тествано, тя определя кои behavioural changes се прилагат в runtime. compileSdk може и трябва да бъде по-високо или равно на targetSdk.
Правилото е просто: compileSdk >= targetSdk >= minSdk. compileSdk обикновено е равно на последното стабилно API ниво (през 2026 г. — 36). targetSdk трябва да бъде възможно най-високо сред версиите, под които сте тествали. minSdk трябва да бъде възможно най-ниско за максимално покритие. Повишаването на compileSdk не изисква тестване на behavioural changes — то само отваря достъп до нови API за компилатора. Повишаването на targetSdk изисква пълен цикъл на тестване на всички behavioural changes.
| Параметър | Момент на действие | Влияе на | Може да бъде по-висок от другите |
|---|---|---|---|
| compileSdkVersion | Компилиране | Наличност на API за код | Да, винаги по-висок от targetSdk |
| targetSdkVersion | Runtime | Behavioural changes | Да, но по-нисък от compileSdk |
| minSdkVersion | Инсталиране | Съвместимост на устройства | Не, винаги най-нисък |
На практика: ако искате да използвате ново API от Android 16 (API 36), но behavioural changes на API 36 все още не сте тествали, задайте compileSdk = 36, targetSdk = 35. Кодът ще се компилира с новите API, но behavioural changes на API 36 няма да бъдат приложени. Щом тествате всички промени — повишете targetSdk до 36.
Често задавани въпроси
targetSdkVersion — API ниво, под което приложението е тествано. Android го използва за прилагане на behavioural changes — промени в поведението, въведени в тази версия. Ако targetSdk е по-ниско от API нивото на устройството, behavioural changes не се прилагат. Google Play изисква targetSdk да не е по-старо от 1 година от текущото API ниво за публикуване на нови версии и актуализации.
targetSdkVersion влияе на runtime поведението: включва behavioural changes на определено API ниво. compileSdkVersion влияе само на компилирането: определя кои API са налични за компилатора. compileSdk може да бъде по-високо от targetSdk, но не и обратното. Повишаването на compileSdk не изисква тестване, повишаването на targetSdk изисква проверка на всички behavioural changes.
Android 15 (API 35) въвежда ключови behavioural changes: Privacy Sandbox с ограничение на Advertising ID, Foreground Service Types със задължителна декларация, ограничение на SCHEDULE_EXACT_ALARM с диалогов прозорец за разрешение, затягане на Scoped Storage и автоматичен преход към удостоверяване без идентификационни данни. Приложенията с targetSdk 35+ трябва да преминат пълен цикъл на тестване под API 35.
Ако не актуализирате targetSdkVersion, Google Play ще блокира публикуването на нови версии на приложението. Всяка година Google повишава минималния targetSdk: от август 2025 г. — targetSdk 34+, от август 2026 г. се очаква targetSdk 35+. Приложенията, които не отговарят на изискванията, се премахват от магазина. Освен това не се прилагат behavioural changes за сигурност, което прави приложението уязвимо.
Проверка на targetSdkVersion чрез ADB: adb shell dumpsys package com.example.myapp | grep targetSdk. В Android Studio отворете APK Analyzer: Build → Analyze APK → AndroidManifest.xml → uses-sdk. В кода: context.applicationInfo.targetSdkVersion. В Google Play Console targetSdk се показва на страницата на изданието на приложението в секцията Artifact Details.
Обобщение
Ще разработим мобилно приложение под ключ
IT Sectr създава iOS и Android приложения за стартъпи и бизнеси от 2017 г. Ще ви консултираме и ще предложим най-доброто решение.
Прочетете също