Background: kiến thức cơ bản, ứng dụng hoạt động ở chế độ nền trên iOS và Android

Tác giả: IT Sectr Đã đăng: 2026-03-03 Thời gian đọc: 10 phút

Background là trạng thái vòng đời của ứng dụng trong đó ứng dụng tiếp tục chạy nhưng không hiển thị trên màn hình. Chúng tôi giải thích kiến thức cơ bản về hoạt động nền trên iOS và Android: giới hạn, thời gian chờ, tác vụ nền qua beginBackgroundTask, WorkManager và Service, cùng các phương pháp hay nhất để xử lý Background đúng cách.

Những Điểm Chính

  • Background — ứng dụng không hiển thị với người dùng nhưng có thể chạy mã trong thời gian giới hạn
  • Tác vụ nền iOS — beginBackgroundTask(expirationHandler:) cung cấp tới 30 giây để hoàn thành công việc
  • Android Service — Foreground Service với thông báo cho các hoạt động nền dài
  • WorkManager — API được khuyến nghị cho tác vụ nền trên Android với đảm bảo thực thi
  • Hạn chế — cả hai nền tảng đều thắt chặt quy tắc hoạt động nền để tiết kiệm pin

Background — kiến thức cơ bản về trạng thái nền

Background là trạng thái của ứng dụng trong đó nó tiếp tục tồn tại trong hệ điều hành, thực thi mã và tiêu thụ tài nguyên, nhưng không hiển thị trên màn hình thiết bị. Người dùng đang ở Màn Hình Chính, trong ứng dụng khác hoặc màn hình thiết bị bị khóa. Trên iOS, Background theo sau Inactive — chuỗi chuyển đổi: Active → Inactive → Background. Trên Android, onStop báo hiệu sự chuyển đổi của Activity sang Background.

Cả hai nền tảng đều áp đặt các hạn chế nghiêm ngặt đối với hoạt động nền. iOS cung cấp một cửa sổ giới hạn (thường là 30 giây) để thực thi mã sau khi vào Background, sau đó ứng dụng chuyển sang Suspended. Android linh hoạt hơn: Foreground Service với thông báo hiển thị có thể chạy vô thời hạn, nhưng Background Service thông thường bị giới hạn trong vài phút. Nhiệm vụ chính của nhà phát triển là lưu trạng thái đúng cách và lên lịch tiếp tục công việc thông qua API tác vụ nền của hệ thống.

Hệ thống có thể kết thúc ứng dụng nền bất kỳ lúc nào khi thiếu bộ nhớ. Khi kết thúc, tất cả dữ liệu chưa lưu sẽ bị mất. Do đó, việc lưu trạng thái trong applicationDidEnterBackground (iOS) hoặc onStop (Android) là cực kỳ quan trọng. Sau khi kết thúc, lần khởi chạy tiếp theo bắt đầu từ Not Running với khởi động nguội và khôi phục trạng thái đã lưu.

Background so với Suspended

Điều quan trọng là phân biệt Background và Suspended. Background — ứng dụng đang tích cực thực thi mã. Suspended — ứng dụng ở trong bộ nhớ nhưng không thực thi mã — nó bị đóng băng. Trên iOS, ứng dụng chuyển từ Background sang Suspended sau khi hoàn thành các tác vụ nền. Android không có Suspended — tiến trình tồn tại (bao gồm Background) hoặc đã kết thúc (Not Running). Tuy nhiên, Android có thể tạm dừng thực thi luồng qua LMK (Low Memory Killer).

Đặc điểmiOS BackgroundAndroid Background
Mã được thực thiCó, tới 30 giâyCó, phụ thuộc vào API
Giao diện hiển thịKhôngKhông
Thời gian chờ mặc định~30 giây (beginBackgroundTask)Vài phút (Service)
Công việc không giới hạnChỉ danh mục đặc biệt (âm thanh, VoIP, định vị)Foreground Service với thông báo
Đảm bảo thực thiKhông — hệ thống có thể kết thúc bất kỳ lúc nàoWorkManager đảm bảo thực thi
Yêu cầu quyềnCó — capabilities trong Info.plistCó — quyền FOREGROUND_SERVICE
Trạng thái tiếp theoSuspended → Not RunningNot Running (hoặc khởi động lại)

Background trên iOS: Swift, beginBackgroundTask và BGTaskScheduler

Trên iOS, Background được xử lý thông qua phương thức ủy quyền applicationDidEnterBackground. Trong phương thức này, nhà phát triển cần lưu trạng thái người dùng, giải phóng tài nguyên và hoàn thành các tác vụ nền. Để thực thi mã sau khi vào Background, sử dụng beginBackgroundTask(expirationHandler:) — một API yêu cầu thêm thời gian từ hệ thống (thường 30 giây). Nếu tác vụ không hoàn thành trong thời gian này, expirationHandler được gọi và ứng dụng buộc phải chuyển sang Suspended.

Với iOS 13, Apple đã giới thiệu BGTaskScheduler — một API hiện đại để lên lịch các tác vụ nền. Không giống như beginBackgroundTask chỉ cấp thời gian để kết thúc sau khi vào nền, BGTaskScheduler cho phép lên lịch thực thi tác vụ trong tương lai — ví dụ: cập nhật nội dung một lần mỗi giờ hoặc tải phân tích lên vào ban đêm. BGTaskScheduler là cách tiếp cận được khuyến nghị cho các dự án mới vì nó hiệu quả hơn về pin.

swift
import UIKit
import BackgroundTasks

@main
class AppDelegate: UIResponder, UIApplicationDelegate {

    var backgroundTaskID: UIBackgroundTaskIdentifier = .invalid

    // Ứng dụng đã vào nền — bắt đầu tác vụ nền
    func applicationDidEnterBackground(_ application: UIApplication) {
        saveAppState()
        startBackgroundTask()
    }

    private func startBackgroundTask() {
        backgroundTaskID = UIApplication.shared.beginBackgroundTask { [weak self] in
            // Hết thời gian — buộc kết thúc
            self?.endBackgroundTask()
        }

        // Mô phỏng công việc nền (lưu dữ liệu lên máy chủ)
        DispatchQueue.global().async { [weak self] in
            uploadAnalyticsData()
            self?.endBackgroundTask()
        }
    }

    private func endBackgroundTask() {
        guard backgroundTaskID != .invalid else { return }
        UIApplication.shared.endBackgroundTask(backgroundTaskID)
        backgroundTaskID = .invalid
    }

    // Đăng ký BGTaskScheduler
    func application(
        _ application: UIApplication,
        didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?
    ) -> Bool {
        BGTaskScheduler.shared.register(
            forTaskWithIdentifier: "com.example.refresh",
            using: nil
        ) { task in
            handleAppRefresh(task: task as! BGAppRefreshTask)
        }
        return true
    }

    func scheduleAppRefresh() {
        let request = BGAppRefreshTaskRequest(identifier: "com.example.refresh")
        request.earliestBeginDate = Date(timeIntervalSinceNow: 3600)
        try? BGTaskScheduler.shared.submit(request)
    }

    func handleAppRefresh(task: BGAppRefreshTask) {
        scheduleAppRefresh()
        task.expirationHandler = { task.setTaskCompleted(success: false) }
        fetchLatestData { result in
            task.setTaskCompleted(success: result)
        }
    }
}

Mã hiển thị xử lý Background đầy đủ trên iOS. applicationDidEnterBackground bắt đầu một tác vụ nền qua beginBackgroundTask với thời gian chờ và expirationHandler. Đồng thời, BGTaskScheduler được đăng ký để cập nhật nội dung định kỳ. beginBackgroundTask được sử dụng cho các tác vụ tắt ngay lập tức, BGTaskScheduler được sử dụng cho lập kế hoạch dài hạn. Cả hai API đều yêu cầu quản lý đúng mã định danh tác vụ.

Background trên Android: Kotlin, Service, WorkManager

Trên Android, Background được quản lý qua nhiều API. Service truyền thống cho phép thực thi mã ở nền, nhưng từ Android 8+ (API 26), Background Service bị giới hạn: hệ thống kết thúc nó vài phút sau khi ứng dụng vào nền. Foreground Service với thông báo liên tục có thể chạy vô thời hạn. WorkManager là giải pháp được khuyến nghị cho các tác vụ nền với đảm bảo thực thi ngay cả sau khi khởi động lại thiết bị.

Android, không giống như iOS, hỗ trợ các tiến trình nền chạy dài. Foreground Service được sử dụng cho các tác vụ người dùng cần thấy — phát nhạc, định vị, theo dõi tập luyện. JobScheduler và WorkManager được sử dụng cho các tác vụ có thể trì hoãn: đồng bộ dữ liệu, tải nhật ký lên, cập nhật bộ nhớ đệm. Sự khác biệt chính: Android cho phép lên lịch tác vụ với các điều kiện — Wi-Fi, sạc, thiết bị không hoạt động — giúp tiết kiệm pin và lưu lượng.

kotlin
import android.app.Service
import android.content.Intent
import android.os.IBinder
import androidx.work.*

// 1. Foreground Service cho công việc nền dài hạn
class SyncService : Service() {

    override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
        val notification = createNotification()
        startForeground(NOTIFICATION_ID, notification)
        performBackgroundWork()
        return START_STICKY
    }

    private fun performBackgroundWork() {
        Thread {
            // Đồng bộ dữ liệu với máy chủ
            syncDataToServer()
            stopForeground(STOP_FOREGROUND_REMOVE)
            stopSelf()
        }.start()
    }

    override fun onBind(intent: Intent?): IBinder? = null
}

// 2. WorkManager cho các tác vụ nền bị trì hoãn
class DataSyncWorker(
    private val context: Context,
    private val params: WorkerParameters
) : CoroutineWorker(context, params) {

    override suspend fun doWork(): Result {
        return try {
            // Tải phân tích lên máy chủ
            uploadAnalytics()
            Result.success()
        } catch (e: Exception) {
            if (runAttemptCount < 3) Result.retry() else Result.failure()
        }
    }
}

// Lên lịch tác vụ WorkManager
fun scheduleBackgroundSync(context: Context) {
    val constraints = Constraints.Builder()
        .setRequiredNetworkType(NetworkType.CONNECTED)
        .setRequiresBatteryNotLow(true)
        .build()

    val request = OneTimeWorkRequestBuilder<DataSyncWorker>()
        .setConstraints(constraints)
        .setBackoffCriteria(BackoffPolicy.EXPONENTIAL, 30, TimeUnit.SECONDS)
        .build()

    WorkManager.getInstance(context).enqueue(request)
}

Mã hiển thị hai cách tiếp cận cho hoạt động nền trên Android. SyncService — Foreground Service với thông báo cho công việc nền tức thời và dài hạn. DataSyncWorker — WorkManager cho các tác vụ trì hoãn với điều kiện (Wi-Fi, sạc). WorkManager đảm bảo thực thi ngay cả sau khi khởi động lại thiết bị và hỗ trợ backoff hàm mũ cho các lần thử lại. Foreground Service yêu cầu thông báo liên tục trên thanh trạng thái.

Hạn chế hoạt động nền trên iOS và Android

Cả hai nền tảng di động đều liên tục thắt chặt các quy tắc hoạt động nền. Trên iOS, mỗi thế hệ hệ điều hành mới đều giảm thời gian thực thi nền và thêm các hạn chế mới. Trên Android, Google đang giới thiệu các chế độ tiết kiệm pin ngày càng nghiêm ngặt (Doze, App Standby). Các nhà phát triển phải cập nhật các hạn chế hiện tại để tránh ứng dụng bị hệ thống kết thúc sớm.

Trên iOS, bắt đầu từ iOS 13, hệ thống vô hiệu hóa các tác vụ nền cho các ứng dụng lạm dụng thời gian nền. Mỗi ứng dụng nhận được các giới hạn nhất định dựa trên hành vi của người dùng. BGTaskScheduler lên lịch thực thi vào thời điểm tối ưu — ví dụ: khi thiết bị được kết nối Wi-Fi và đang sạc. Các ứng dụng sử dụng BGTaskScheduler đúng cách sẽ nhận được nhiều thời gian nền hơn.

Trên Android, bắt đầu từ Android 9 (API 28), hoạt động nền bị hạn chế bởi chế độ Doze, được kích hoạt khi thiết bị không hoạt động. Ứng dụng trong Doze không thể thực hiện tác vụ nền, mạng bị ngắt kết nối, JobScheduler và WorkManager trì hoãn tác vụ cho đến khi thoát Doze. Foreground Service là cách duy nhất để vượt qua Doze, nhưng lạm dụng dẫn đến ứng dụng bị người dùng chặn và thu hồi quyền.

Hạn chếiOSAndroid
Thời gian chờ tác vụ nền~30 giây (beginBackgroundTask)Vài phút (JobScheduler)
Nền không giới hạnÂm thanh, VoIP, định vị, BluetoothForeground Service + thông báo
Tiết kiệm pinLow Power Mode — vô hiệu hóa tác vụ nềnDoze, App Standby, Tối ưu pin
Lên lịchBGTaskScheduler (iOS 13+)WorkManager (Android Jetpack)
Sau khi khởi động lạiChỉ thông báo pushWorkManager giữ lại tác vụ
Thời gian thực thi tối đa~30 phút (âm thanh)Không giới hạn (Foreground Service)

Phương pháp hay nhất cho hoạt động nền

Quy tắc đầu tiên — giảm thiểu tiêu thụ tài nguyên ở nền. Hầu hết các tác vụ nền có thể được trì hoãn đến khi thiết bị đang sạc và kết nối Wi-Fi. Sử dụng BGTaskScheduler (iOS) và WorkManager (Android) để lên lịch tác vụ với điều kiện. Không chạy tính toán nặng ở nền — điều này làm hao pin và dẫn đến giảm tốc CPU.

Quy tắc thứ hai — luôn chỉ định expirationHandler cho beginBackgroundTask. Nếu ứng dụng không hoàn thành tác vụ trong thời gian cho phép, hệ thống sẽ buộc chuyển nó sang Suspended hoặc kết thúc. ExpirationHandler là cơ hội cuối cùng để lưu dữ liệu và kết thúc công việc đúng cách. Trên Android, sử dụng setForegroundAsync trong WorkManager để chuyển đổi tác vụ thông thường thành tiền cảnh nếu cần thêm thời gian.

Quy tắc thứ ba — kiểm tra các hạn chế hoạt động nền trước khi khởi chạy. Trên iOS, sử dụng UIApplication.shared.backgroundTimeRemaining để kiểm tra thời gian còn lại. Trên Android, kiểm tra ActivityManager.isBackgroundRestricted() — nếu true, ứng dụng không thể chạy tác vụ nền và bạn nên đề xuất người dùng gỡ bỏ hạn chế trong cài đặt. Điều này đặc biệt quan trọng đối với ứng dụng có chức năng nền quan trọng — báo thức, lịch, đồng bộ hóa.

Quy tắc thứ tư — kiểm tra tác vụ nền trên thiết bị thực. Trình mô phỏng và giả lập không tái tạo các hạn chế hoạt động nền thực tế. Trên iOS, sử dụng Debug → Simulate Background Fetch trong Xcode. Trên Android, sử dụng adb shell am broadcast -a android.intent.action.ACTION_BOOT_COMPLETED để kiểm tra WorkManager sau khi khởi động lại. Kiểm tra thực tế trên thiết bị có pin yếu sẽ phát hiện hầu hết các vấn đề hoạt động nền.

swift
import UIKit

final class BackgroundTaskManager {
    static let shared = BackgroundTaskManager()
    private var tasks: [String: UIBackgroundTaskIdentifier] = [:]

    func startTask(name: String, expiration: @escaping () -> Void) {
        let remaining = UIApplication.shared.backgroundTimeRemaining
        print("Thời gian còn lại ở nền: \(remaining) giây")

        let task = UIApplication.shared.beginBackgroundTask { [weak self] in
            print("Hết thời gian cho tác vụ: \(name)")
            expiration()
            self?.endTask(name: name)
        }

        tasks[name] = task
    }

    func endTask(name: String) {
        guard let task = tasks.removeValue(forKey: name),
              task != .invalid
        else { return }
        UIApplication.shared.endBackgroundTask(task)
    }
}

Mã hiển thị một trình quản lý tác vụ nền theo dõi thời gian còn lại và quản lý mã định danh. backgroundTimeRemaining trả về số giây trước khi kết thúc bắt buộc — nếu giá trị là vô hạn, ứng dụng đang chạy không giới hạn (âm thanh, định vị). Trình quản lý cho phép khởi chạy nhiều tác vụ nền với các tên khác nhau và hoàn thành mỗi tác vụ đúng cách. Cách tiếp cận này ngăn rò rỉ tác vụ nền và đảm bảo hệ thống không kết thúc ứng dụng do các tác vụ chưa đóng.

Câu Hỏi Thường Gặp

Ứng dụng iOS có thể chạy nền vĩnh viễn không?

Có, cho một số danh mục giới hạn: âm thanh (AVAudioSession danh mục .playback), VoIP (PushKit), định vị (CLLocationManager với allowsBackgroundLocationUpdates), Bluetooth (chế độ nền trung tâm), cập nhật nền (BGTaskScheduler). Tất cả các trường hợp khác — tối đa 30 giây. Trong iOS 16+, Apple đã thắt chặt yêu cầu ngay cả đối với các danh mục được phép.

beginBackgroundTask khác BGTaskScheduler như thế nào?

beginBackgroundTask là API đồng bộ để kéo dài thời gian sống của ứng dụng khoảng 30 giây sau khi vào nền. Nó được gọi trong applicationDidEnterBackground. BGTaskScheduler là API bất đồng bộ để lên lịch tác vụ trong tương lai thông qua các trình kích hoạt hệ thống (thời gian, vị trí, cập nhật nội dung). BGTaskScheduler là cách tiếp cận hiện đại, được Apple khuyến nghị cho iOS 13+.

Tại sao Android giết Background Service của tôi?

Bắt đầu từ Android 8 (API 26), Background Service bị kết thúc vài phút sau khi ứng dụng vào nền. Giải pháp: sử dụng Foreground Service với thông báo cho các hoạt động dài hoặc WorkManager cho các tác vụ trì hoãn. Kiểm tra Tối ưu Pin cho ứng dụng của bạn trong cài đặt — nếu nó được tối ưu hóa, hệ thống có thể trì hoãn hoặc hủy bỏ các tác vụ nền.

Làm thế nào để kiểm tra Background trên trình mô phỏng iOS?

Nhấn Cmd+Shift+H để về Màn Hình Chính. Trong Xcode, sử dụng Debug → Simulate Background Fetch. Để kiểm tra beginBackgroundTask, mở bảng điều khiển (Shift+Cmd+C) và gọi e UIApplication.shared.backgroundTimeRemaining. Trong Xcode 15+, kịch bản Background Execution có sẵn trong tab Diagnostics của trình mô phỏng.

Process death trên Android là gì?

Process Death là việc hệ thống kết thúc tiến trình Android khi thiếu tài nguyên hoặc khi không hoạt động ở nền. Không giống như iOS, Android không có Suspended — tiến trình hoặc còn sống (có thể ở nền) hoặc đã chết (Not Running). Process Death là hành vi bình thường của hệ điều hành và ứng dụng phải khôi phục trạng thái đúng cách sau đó thông qua SavedStateHandle, onSaveInstanceState hoặc DataStore.

Tổng Kết

  • Background — ứng dụng không hiển thị trên màn hình nhưng chạy mã, khác với Suspended (bị đóng băng)
  • iOS — beginBackgroundTask (tới 30 giây) và BGTaskScheduler để lên lịch tác vụ tương lai
  • Android — Foreground Service cho hoạt động dài, WorkManager cho tác vụ trì hoãn có đảm bảo
  • Hạn chế — cả hai nền tảng thắt chặt quy tắc: Doze, Low Power Mode, App Standby
  • Lưu trữ — applicationDidEnterBackground và onStop là cơ hội cuối trước Suspended/Not Running
  • Lên lịch — BGTaskScheduler và WorkManager hoạt động với điều kiện (Wi-Fi, sạc, thời gian)
  • Foreground Service — cách duy nhất cho hoạt động nền không giới hạn trên cả hai nền tảng

Chúng tôi sẽ phát triển ứng dụng di động chìa khóa trao tay

IT Sectr tạo các ứng dụng iOS và Android cho các công ty khởi nghiệp và doanh nghiệp từ năm 2017. Chúng tôi sẽ tư vấn và đề xuất giải pháp tốt nhất cho bạn.

Thảo luận dự án

Đọc thêm